15 #ifndef SHAKA_EMBEDDED_MAPPING_BACKING_OBJECT_FACTORY_H_ 16 #define SHAKA_EMBEDDED_MAPPING_BACKING_OBJECT_FACTORY_H_ 18 #include <glog/logging.h> 38 using NativeCtor = void (*)(
const v8::FunctionCallbackInfo<v8::Value>&);
39 #elif defined(USING_JSC) 40 using NativeCtor = JSObjectRef (*)(JSContextRef, JSObjectRef, size_t,
41 const JSValueRef*, JSValueRef*);
54 virtual ReturnVal<JsValue>
GetIndex(Handle<JsObject> that,
size_t index) = 0;
55 virtual void SetIndex(Handle<JsObject> that,
size_t index,
56 Handle<JsValue> value) = 0;
59 template <
typename This,
typename T>
63 bool (This::*
get)(
size_t, T*)
const,
64 void (This::*
set)(
size_t, T))
65 : type_name_(type_name), get_(
get), set_(set) {}
67 ReturnVal<JsValue>
GetIndex(Handle<JsObject> that,
size_t index)
override {
71 nullptr,
"indexer", type_name_);
76 if (!((obj.
get())->*get_)(index, &value))
81 void SetIndex(Handle<JsObject> that,
size_t index,
82 Handle<JsValue> given)
override {
86 nullptr,
"indexer", type_name_);
91 nullptr,
"indexer", type_name_,
92 "Indexer on '" + type_name_ +
"' is read-only.");
103 ((obj.
get())->*set_)(index, std::move(value));
107 const std::string type_name_;
108 bool (This::*get_)(size_t, T*)
const;
109 void (This::*set_)(size_t, T);
118 struct RefTypeTraits<JSClassRef> {
124 static constexpr
const bool AcquireWithRaw =
true;
126 static JSClassRef Duplicate(JSClassRef arg) {
128 return JSClassRetain(arg);
133 static void Release(JSClassRef arg) {
161 const std::string&
name()
const {
175 #if defined(USING_JSC) 176 JSClassRef GetClass()
const {
177 return class_definition_;
185 bool DerivedFrom(
const std::string&
name)
const;
201 ReturnVal<JsValue>
GetIndex(Handle<JsObject> that,
size_t index);
209 void SetIndex(Handle<JsObject> that,
size_t index, Handle<JsValue> value);
215 template <
typename Callback>
217 LocalVar<JsFunction> js_function =
223 template <
typename Ret,
typename... Args>
225 LocalVar<JsFunction> js_function =
235 template <
typename Prop>
237 AddReadWriteProperty(
"on" +
to_string(type), member);
240 template <
typename This,
typename Prop>
242 #ifndef ALLOW_STRUCT_FIELDS 245 "Cannot store Structs in fields");
249 return that.get()->*member;
251 LocalVar<JsFunction> js_getter =
253 LocalVar<JsFunction> setter;
257 template <
typename This,
typename Prop>
259 #ifndef ALLOW_STRUCT_FIELDS 262 "Cannot store Structs in fields");
265 auto getter = [=](
RefPtr<This> that) -> Prop& {
return that->*member; };
266 LocalVar<JsFunction> js_getter =
269 that->*member = std::move(value);
271 LocalVar<JsFunction> js_setter =
277 template <
typename Derived = void,
typename This = void,
278 typename GetProp =
void>
280 GetProp (This::*
get)()
const) {
282 type_name_,
"get_" + name, MakeMemFn<Derived>(
get));
283 LocalVar<JsFunction> setter;
287 template <
typename Derived = void,
typename This = void,
288 typename GetProp = void,
typename SetProp = void,
289 typename SetPropRet =
void>
291 SetPropRet (This::*
set)(SetProp)) {
294 "Getter and setter must use the same type.");
295 static_assert(std::is_same<void, SetPropRet>::value ||
297 "Setter can only return void.");
299 type_name_,
"get_" + name, MakeMemFn<Derived>(
get));
301 type_name_,
"set_" + name, MakeMemFn<Derived>(
set));
305 template <
typename T>
307 LocalVar<JsValue> js_value =
ToJsValue(value);
312 template <
typename This,
typename T>
314 void (This::*
set)(
size_t, T) =
nullptr) {
319 void NotImplemented(
const std::string& name);
322 template <
typename Derived,
typename This>
323 using get_this =
typename std::conditional<std::is_same<Derived, void>::value,
326 template <
typename Derived,
typename Callback>
327 struct MakeMemFnImpl;
328 template <
typename Derived,
typename This,
typename Ret,
typename... Args>
329 struct MakeMemFnImpl<Derived, Ret (This::*)(Args...)> {
330 using ArgThis = get_this<Derived, This>;
331 using type = std::function<Ret(RefPtr<ArgThis>, Args...)>;
332 static type Make(Ret (This::*callback)(Args...)) {
334 return ((that.
get())->*(callback))(std::move(args)...);
338 template <
typename Derived,
typename This,
typename Ret,
typename... Args>
339 struct MakeMemFnImpl<Derived, Ret (This::*)(Args...) const> {
340 using ArgThis = get_this<Derived, This>;
341 using type = std::function<Ret(RefPtr<ArgThis>, Args...)>;
342 static type Make(Ret (This::*callback)(Args...)
const) {
344 return ((that.
get())->*(callback))(std::move(args)...);
349 template <
typename Derived,
typename Callback>
352 return MakeMemFnImpl<Derived, Callback>::Make(callback);
355 const std::string type_name_;
357 std::unique_ptr<impl::IndexerHandler> indexer_;
358 Global<JsFunction> constructor_;
359 Global<JsObject> prototype_;
361 Global<v8::FunctionTemplate> class_definition_;
362 #elif defined(USING_JSC) 363 JSClassDefinition definition_;
364 util::CFRef<JSClassRef> class_definition_;
376 template <
typename T>
405 template <
typename T,
typename Base =
void>
415 #endif // SHAKA_EMBEDDED_MAPPING_BACKING_OBJECT_FACTORY_H_ void AddMemberFunction(const std::string &name, Callback callback)
ReturnVal< JsFunction > CreateStaticFunction(const std::string &target, const std::string &name, Func &&callback)
ReturnVal< JsValue > JsUndefined()
virtual ~IndexerHandler()
bool FromJsValue(Handle< JsValue > source, T *dest)
void AddGenericProperty(const std::string &name, GetProp(This::*get)() const, SetPropRet(This::*set)(SetProp))
void AddReadWriteProperty(const std::string &name, Prop This::*member)
ReturnVal< JsValue > GetConstructor() const
void AddGenericProperty(const std::string &name, GetProp(This::*get)() const)
void SetIndex(Handle< JsObject > that, size_t index, Handle< JsValue > given) override
ReturnVal< JsValue > GetIndex(Handle< JsObject > that, size_t index) override
ReturnVal< JsValue > ToJsValue(T &&source)
ReturnVal< JsValue > RawToJsValue(Handle< T > source)
BackingObjectFactoryRegistry(BackingObjectFactoryBase *base)
IndexerHandlerImpl(const std::string &type_name, bool(This::*get)(size_t, T *) const, void(This::*set)(size_t, T))
virtual void SetIndex(Handle< JsObject > that, size_t index, Handle< JsValue > value)=0
virtual ReturnVal< JsValue > GetIndex(Handle< JsObject > that, size_t index)=0
void AddIndexer(bool(This::*get)(size_t, T *) const, void(This::*set)(size_t, T)=nullptr)
impl::get_const_reference_at_t< I, Choices... > get(const variant< Choices... > &variant)
static BackingObjectFactoryRegistry< T > * Instance()
const std::string & name() const
void AddListenerField(js::EventType type, Prop member)
static BackingObjectFactoryBase * CheckedInstance()
void SetMemberRaw(Handle< JsObject > object, const std::string &name, Handle< JsValue > value)
std::string ConvertToString(Handle< JsValue > value)
void AddConstant(const std::string &name, T value)
void AddReadOnlyProperty(const std::string &name, Prop This::*member)
const BackingObjectFactoryBase * base() const
void AddStaticFunction(const std::string &name, Ret(*callback)(Args...))
ReturnVal< JsFunction > CreateMemberFunction(const std::string &target, const std::string &name, Func &&callback)
void SetGenericPropertyRaw(Handle< JsObject > object, const std::string &name, Handle< JsFunction > getter, Handle< JsFunction > setter)