如何将包装的C ++对象传递给Javascriptcallback?
和我解释这一点一样。
我正在尝试使用C ++编写一个Node.js模块,它包装并公开libhdf5中的一些类。
我目前对libhdf5的两个类感兴趣。 第一个是File
,它打开一个hdf5文件。 第二个是Group
,代表该文件中的组。 您从File对象获取组对象。
我写了一些代码,我创build了一个File
对象,并试图从中获取一个Group
。 我正在尝试使我的Node.js模块尽可能Javascripty,所以我想使用callback返回组。 所以,我试图编写我的模块,以便它的使用是这样的:
var hdf5 = require('hdf5'); var file = new hdf5.File('/tmp/example.h5'); file.getGroup('foobar', function (err, group) { console.log(group); });
所以,在我的File
包装器的C ++代码中,我有一个映射到getGroup
函数的函数,它会调用给定的匿名函数,传入任何错误以及新的Group
对象包装器。
鉴于这听起来像是什么Node.js文档显示为包装对象的工厂 ,我已经模拟了我的Group
代码后的例子。
所以,我有我的Group
包装编码,但坚持试图实例化它。 我还不知道如何偏离使用v8 Arguments
类的函数参数。 正因为如此,我似乎无法传递我需要的一些参数,我的v8持久化构造函数(因为我从C ++实例化这个,而不是从JS-land)。
请有人看看我的代码为libhdf5,并给我一个指示,如何实现这一目标? 我觉得我快到了,但是我只是想念一些东西。
这里是我的Group
包装,突出构造函数: https : //github.com/ryancole/node-hdf5/blob/master/src/h5_group.cc#L57-72
这里是我的File
包装,线高亮在哪里我需要通过我的参数,作为参数(或无论是我需要改变这个工作: https : //github.com/ryancole/node- HDF5 /斑点/主/ SRC / h5_file.cc#L110
在此先感谢,并感谢您阅读此墙的文字。 🙂
你几乎在那里。 您不需要将Arguments
传递给Group::Instantiate
。 只要通过你所需要的,并使用构造函数来创buildGroup
的新实例。 例如:
Handle<Value> Group::Instantiate(const std::string& name) { HandleScope scope; Local<v8::Value> argv[1] = { Local<v8::Value>::New(String::New(name.c_str())) }; return scope.Close(Constructor->NewInstance(1, argv)); }
Group::New
方法完成了其余的构build工作。
Handle<Value> Group::New(const Arguments& args) { HandleScope scope; if (!args[0]->IsString()) { return ThrowException(Exception::TypeError(String::New("First argument must be a string"))); } const std::string name(*(String::Utf8Value(args[0]->ToString()))); Group * const group = new Group(name); bar->Wrap(args.This()); return args.This(); }
在File::OpenGroup
你可以这样做:
Handle<Value> File::OpenGroup (const Arguments& args) { HandleScope scope; if (args.Length() != 2 || !args[0]->IsString() || !args[1]->IsFunction()) { ThrowException(Exception::SyntaxError(String::New("expected name, callback"))); return scope.Close(Undefined()); } const std::string name(*(String::Utf8Value(args[0]->ToString()))); Local<Function> callback = Local<Function>::Cast(args[1]); const unsigned argc = 2; Local<Value> argv[argc] = { Local<Value>::New(Null()), Local<Value>::New(Group::Instantiate(name)) }; callback->Call(Context::GetCurrent()->Global(), argc, argv); return scope.Close(Undefined()); }
HTH