三木社区

 找回密码
 立即注册
搜索
热搜: 活动 交友 discuz
查看: 230|回复: 0
打印 上一主题 下一主题

C++插件-传递包装对象

[复制链接]

1562

主题

1564

帖子

4904

积分

博士

Rank: 8Rank: 8

积分
4904
跳转到指定楼层
楼主
发表于 2017-8-8 08:12:08 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
除了包装并返回 C++ 对象,你可以使用 Node 的 node::ObjectWrap::Unwrap 帮助函数来解包。在下面的 addon.cc 中,我们介绍了一个 add() 函数,它能获取2个 MyObject对象:
  1. // addon.cc
  2. #include <node.h>
  3. #include <node_object_wrap.h>
  4. #include "myobject.h"

  5. using namespace v8;

  6. void CreateObject(const FunctionCallbackInfo<Value>& args) {
  7.   Isolate* isolate = Isolate::GetCurrent();
  8.   HandleScope scope(isolate);
  9.   MyObject::NewInstance(args);
  10. }

  11. void Add(const FunctionCallbackInfo<Value>& args) {
  12.   Isolate* isolate = Isolate::GetCurrent();
  13.   HandleScope scope(isolate);

  14.   MyObject* obj1 = node::ObjectWrap::Unwrap<MyObject>(
  15.       args[0]->ToObject());
  16.   MyObject* obj2 = node::ObjectWrap::Unwrap<MyObject>(
  17.       args[1]->ToObject());

  18.   double sum = obj1->value() + obj2->value();
  19.   args.GetReturnValue().Set(Number::New(isolate, sum));
  20. }

  21. void InitAll(Handle<Object> exports) {
  22.   MyObject::Init();

  23.   NODE_SET_METHOD(exports, "createObject", CreateObject);
  24.   NODE_SET_METHOD(exports, "add", Add);
  25. }

  26. NODE_MODULE(addon, InitAll)
复制代码
介绍 myobject.h 里的一个公开方法,它能在解包后使用私有变量:
  1. // myobject.h
  2. #ifndef MYOBJECT_H
  3. #define MYOBJECT_H

  4. #include <node.h>
  5. #include <node_object_wrap.h>

  6. class MyObject : public node::ObjectWrap {
  7. public:
  8.   static void Init();
  9.   static void NewInstance(const v8::FunctionCallbackInfo<v8::Value>& args);
  10.   inline double value() const { return value_; }

  11. private:
  12.   explicit MyObject(double value = 0);
  13.   ~MyObject();

  14.   static void New(const v8::FunctionCallbackInfo<v8::Value>& args);
  15.   static v8::Persistent<v8::Function> constructor;
  16.   double value_;
  17. };

  18. #endif
复制代码
myobject.cc 的实现方法和之前的类似:
  1. // myobject.cc
  2. #include <node.h>
  3. #include "myobject.h"

  4. using namespace v8;

  5. Persistent<Function> MyObject::constructor;

  6. MyObject::MyObject(double value) : value_(value) {
  7. }

  8. MyObject::~MyObject() {
  9. }

  10. void MyObject::Init() {
  11.   Isolate* isolate = Isolate::GetCurrent();

  12.   // Prepare constructor template
  13.   Local<FunctionTemplate> tpl = FunctionTemplate::New(isolate, New);
  14.   tpl->SetClassName(String::NewFromUtf8(isolate, "MyObject"));
  15.   tpl->InstanceTemplate()->SetInternalFieldCount(1);

  16.   constructor.Reset(isolate, tpl->GetFunction());
  17. }

  18. void MyObject::New(const FunctionCallbackInfo<Value>& args) {
  19.   Isolate* isolate = Isolate::GetCurrent();
  20.   HandleScope scope(isolate);

  21.   if (args.IsConstructCall()) {
  22.     // Invoked as constructor: `new MyObject(...)`
  23.     double value = args[0]->IsUndefined() ? 0 : args[0]->NumberValue();
  24.     MyObject* obj = new MyObject(value);
  25.     obj->Wrap(args.This());
  26.     args.GetReturnValue().Set(args.This());
  27.   } else {
  28.     // Invoked as plain function `MyObject(...)`, turn into construct call.
  29.     const int argc = 1;
  30.     Local<Value> argv[argc] = { args[0] };
  31.     Local<Function> cons = Local<Function>::New(isolate, constructor);
  32.     args.GetReturnValue().Set(cons->NewInstance(argc, argv));
  33.   }
  34. }

  35. void MyObject::NewInstance(const FunctionCallbackInfo<Value>& args) {
  36.   Isolate* isolate = Isolate::GetCurrent();
  37.   HandleScope scope(isolate);

  38.   const unsigned argc = 1;
  39.   Handle<Value> argv[argc] = { args[0] };
  40.   Local<Function> cons = Local<Function>::New(isolate, constructor);
  41.   Local<Object> instance = cons->NewInstance(argc, argv);

  42.   args.GetReturnValue().Set(instance);
  43. }
复制代码
测试:
  1. // test.js
  2. var addon = require('./build/Release/addon');

  3. var obj1 = addon.createObject(10);
  4. var obj2 = addon.createObject(20);
  5. var result = addon.add(obj1, obj2);

  6. console.log(result); // 30
复制代码


回复

使用道具 举报

Archiver|手机版|小黑屋|三木电子社区 ( 辽ICP备11000133号-4 )

辽公网安备 21021702000620号

GMT+8, 2025-6-27 00:12 , Processed in 0.026678 second(s), 23 queries .

Powered by Discuz! X3.3

© 2001-2017 Comsenz Inc.

快速回复 返回顶部 返回列表