5.9 KiB
include/addon-tools.hpp
There is a C++ header file, addon-tools.hpp
, shipped with this package. It
introduces several useful macros and utilities. Also it includes Napi automatically,
so that you can replace:
#include <napi.h>
with
#include <addon-tools.hpp>
In gyp, the include directory should be set for your addon to know where to get it. An actual path to the directory is exported from the module and is accessible like this:
require('addon-tools-raub').include // a string
Helpers in addon-tools.hpp:
Usually all the helpers work within the context of JS call. In this case we
have CallbackInfo info
passed as an argument.
#define NAPI_ENV Napi::Env env = info.Env();
#define NAPI_HS Napi::HandleScope scope(env);
Return value
RET_VALUE(VAL)
- return a given Napi::Value.RET_UNDEFINED
- returnundefined
.RET_NULL
- returnnull
.RET_STR(VAL)
- returnNapi::String
, expectedVAL
isconst char *
.RET_NUM(VAL)
- returnNapi::Number
, expectedVAL
isdouble
.RET_EXT(VAL)
- returnNapi::External
, expectedVAL
isvoid *
.RET_BOOL(VAL)
- returnNapi::Boolean
, expectedVAL
isbool
.RET_FUN(VAL)
- returnNapi::Function
, expectedVAL
is anapi_value
.RET_OBJ(VAL)
- returnNapi::Object
, expectedVAL
is anapi_value
.
New JS value
JS_STR(VAL)
- create aNapi::String
value.JS_NUM(VAL)
- create aNapi::Number
value.JS_EXT(VAL)
- create aNapi::External
(from pointer) value.JS_BOOL(VAL)
- create aNapi::Boolean
value.
Method check
These checks throw JS TypeError if not passed. Here T
is always used as a typename
in error messages. C
is a
Napi::Value
check method, like IsObject()
. I
is the index of argument as in info[I]
,
starting from 0
.
REQ_ARGS(N)
- check if at leastN
arguments passedIS_ARG_EMPTY(I)
- check if argumentI
isundefined
ornull
CHECK_REQ_ARG(I, C, T)
- check if argumentI
is approved byC
check.CHECK_LET_ARG(I, C, T)
- check if argumentI
is approved byC
check or empty.CTOR_CHECK(T)
- check if method is called as a constructorSETTER_CHECK(C, T)
- check if settervalue
is approved byC
check.DES_CHECK
- within dynamic method check if the instance wasn't destroyed bydestroy()
.
Method arguments
The idea is to ease the transition from what inside the CallbackInfo
to
what you work with in C++.
Three types of argument retrieval are supported: REQ_
, USE_
and LET_
.
The difference:
REQ_
- 2 params, requires an argument to have a valueUSE_
- 3 params, allows the argument to be empty and have a defaultLET_
- 2 params, isUSE_
with a preset zero-default.
What it does, basically:
// REQ_DOUBLE_ARG(0, x)
double x = info[0].ToNumber().DoubleValue();
// USE_DOUBLE_ARG(0, x, 5.7)
double x = IS_ARG_EMPTY(0) ? 5.7 : info[0].ToNumber().DoubleValue();
// LET_DOUBLE_ARG(0, x)
double x = IS_ARG_EMPTY(0) ? 0.0 : info[0].ToNumber().DoubleValue();
That extrapolates well to all the helpers below:
REQ_STR_ARG
- JSstring
=> C++std::string
.USE_STR_ARG
LET_STR_ARG
- default:""
.REQ_INT32_ARG
- JSnumber
=> C++int32_t
.USE_INT32_ARG
LET_INT32_ARG
- default:0
.REQ_INT_ARG
- JSnumber
=> C++int32_t
.USE_INT_ARG
LET_INT_ARG
- default:0
.REQ_UINT32_ARG
- JSnumber
=> C++uint32_t
.USE_UINT32_ARG
LET_UINT32_ARG
- default:0
.REQ_UINT_ARG
- JSnumber
=> C++uint32_t
.USE_UINT_ARG
LET_UINT_ARG
- default:0
.REQ_BOOL_ARG
- JSBoolean
=> C++bool
.USE_BOOL_ARG
LET_BOOL_ARG
- default:false
.REQ_OFFS_ARG
- JSnumber
=> C++size_t
.USE_OFFS_ARG
LET_OFFS_ARG
- default:0
.REQ_DOUBLE_ARG
- JSnumber
=> C++double
.USE_DOUBLE_ARG
LET_DOUBLE_ARG
- default:0.0
.REQ_FLOAT_ARG
- JSnumber
=> C++float
.USE_FLOAT_ARG
LET_FLOAT_ARG
- default:0.f
.REQ_EXT_ARG
- JSnative
=> C++void*
.USE_EXT_ARG
LET_EXT_ARG
- default:nullptr
.REQ_FUN_ARG
- JSfunction
=> C++Napi::Function
.REQ_OBJ_ARG
- JSobject
=> C++Napi::Object
.USE_OBJ_ARG
LET_OBJ_ARG
- default:{}
.REQ_ARRV_ARG
- JSArrayBuffer
=> C++Napi::ArrayBuffer
.REQ_BUF_ARG
- JSBuffer
=> C++Napi::Buffer<uint8_t>
.
NAN_METHOD(test) {
REQ_UINT32_ARG(0, width);
REQ_UINT32_ARG(1, height);
LET_FLOAT_ARG(2, z);
// Variables created: unsigned int width, height; float z;
...
Setter argument
Works similar to method arguments. But there is always value
argument, from which a C++ value is extracted.
SETTER_STR_ARG
SETTER_INT32_ARG
SETTER_INT_ARG
SETTER_BOOL_ARG
SETTER_UINT32_ARG
SETTER_UINT_ARG
SETTER_OFFS_ARG
SETTER_DOUBLE_ARG
SETTER_FLOAT_ARG
SETTER_EXT_ARG
SETTER_FUN_ARG
SETTER_OBJ_ARG
SETTER_ARRV_ARG
JS_IMPLEMENT_SETTER(MyClass, x) { THIS_CHECK; SETTER_STR_ARG;
// Variable created: std::string v;
...
See also: Class Wrapping
JS Data to C++ Data
-
T *getArrayData(value, num = NULL)
- extracts TypedArray data of any type from the given JS value. Does not acceptArray
. Checks withIsArrayBuffer()
. Returnsnullptr
for empty JS values. For unacceptable values throws TypeError. -
T *getBufferData(value, num = NULL)
- extracts Buffer data from the given JS value. Checks withIsBuffer()
. Returnsnullptr
for empty JS values. For unacceptable values throws TypeError. -
void *getData(value)
- ifvalue
orvalue.data
is aTypedArray|Buffer
, callsgetArrayData
orgetArrayData
respectively. Returnsnullptr
in other cases.