• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1/*
2 * Copyright (c) 2021 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 *     http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16#include "bindings_implementation.h"
17
18namespace OHOS::Ace::Framework {
19
20template<typename T, template<typename> typename ImplDetail>
21thread_local std::unordered_map<int, std::unique_ptr<IFunctionBinding>> JSClassImpl<T, ImplDetail>::functions_;
22template<typename T, template<typename> typename ImplDetail>
23thread_local std::unordered_map<int, std::unique_ptr<IFunctionBinding>> JSClassImpl<T, ImplDetail>::getFunctions_;
24template<typename T, template<typename> typename ImplDetail>
25thread_local std::unordered_map<int, std::unique_ptr<IFunctionBinding>> JSClassImpl<T, ImplDetail>::setFunctions_;
26template<typename T, template<typename> typename ImplDetail>
27thread_local int JSClassImpl<T, ImplDetail>::nextFreeId_ = 0;
28template<typename T, template<typename> typename ImplDetail>
29thread_local std::string JSClassImpl<T, ImplDetail>::jsName;
30
31template<typename C, template<typename> typename ImplDetail>
32void JSClassImpl<C, ImplDetail>::Declare(const char* name)
33{
34    jsName = name;
35    ImplDetail<C>::Declare(name);
36}
37
38template<typename C, template<typename> typename ImplDetail>
39template<typename Base, typename R, typename... Args>
40void JSClassImpl<C, ImplDetail>::Method(const char* name, R (Base::*func)(Args...), MethodOptions options)
41{
42    static_assert(std::is_base_of_v<Base, C>, "Trying to bind an unrelated method!");
43    functions_.emplace(nextFreeId_, new FunctionBinding(name, options, func));
44    ImplDetail<C>::Method(name, func, nextFreeId_++);
45}
46
47template<typename C, template<typename> typename ImplDetail>
48template<typename R, typename... Args>
49void JSClassImpl<C, ImplDetail>::StaticMethod(const char* name, R (*func)(Args...), MethodOptions options)
50{
51    ImplDetail<C>::StaticMethod(name, new StaticFunctionBinding(name, options, func));
52}
53
54template<typename C, template<typename> typename ImplDetail>
55void JSClassImpl<C, ImplDetail>::StaticMethod(const char* name, JSFunctionCallback func)
56{
57    ImplDetail<C>::StaticMethod(name, new StaticFunctionBinding(name, MethodOptions::NONE, func));
58}
59
60template<typename C, template<typename> typename ImplDetail>
61template<typename T>
62void JSClassImpl<C, ImplDetail>::CustomMethod(const char* name, MemberFunctionCallback<T> callback)
63{
64    static_assert(std::is_base_of_v<T, C>, "Trying to bind an unrelated method!");
65    functions_.emplace(nextFreeId_, new FunctionBinding(name, MethodOptions::NONE, callback));
66    ImplDetail<C>::CustomMethod(name, callback, nextFreeId_++);
67}
68
69template<typename C, template<typename> typename ImplDetail>
70void JSClassImpl<C, ImplDetail>::CustomMethod(const char* name, FunctionCallback callback)
71{
72    ImplDetail<C>::CustomMethod(name, callback);
73}
74
75template<typename C, template<typename> typename ImplDetail>
76template<typename T>
77void JSClassImpl<C, ImplDetail>::CustomMethod(const char* name, JSMemberFunctionCallback<T> callback)
78{
79    functions_.emplace(nextFreeId_, new FunctionBinding(name, MethodOptions::NONE, callback));
80    ImplDetail<C>::CustomMethod(name, callback, nextFreeId_++);
81}
82
83template<typename C, template<typename> typename ImplDetail>
84template<typename T>
85void JSClassImpl<C, ImplDetail>::CustomProperty(const char* name, MemberFunctionGetCallback<T> getter,
86    MemberFunctionSetCallback<T> setter)
87{
88    int getFuncId;
89    int setFuncId;
90    getFunctions_.emplace(nextFreeId_, new FunctionBinding(name, MethodOptions::NONE, getter));
91    setFunctions_.emplace(nextFreeId_, new FunctionBinding(name, MethodOptions::NONE, setter));
92
93    static_assert(std::is_base_of_v<T, C>, "Trying to bind an unrelated method!");
94    functions_.emplace(nextFreeId_, new FunctionBinding(name, MethodOptions::NONE, getter));
95    getFuncId = nextFreeId_++;
96    functions_.emplace(nextFreeId_, new FunctionBinding(name, MethodOptions::NONE, setter));
97    setFuncId = nextFreeId_++;
98
99
100    ImplDetail<C>::CustomProperty(name, getter, getFuncId, setFuncId);
101}
102
103template<typename C, template<typename> typename ImplDetail>
104void JSClassImpl<C, ImplDetail>::CustomProperty(const char* name, FunctionGetCallback getter,
105    FunctionSetCallback setter)
106{
107    ImplDetail<C>::CustomProperty(name, getter, setter);
108}
109
110template<typename C, template<typename> typename ImplDetail>
111template<typename T>
112void JSClassImpl<C, ImplDetail>::CustomProperty(const char* name, JSMemberFunctionCallback<T> getter,
113    JSMemberFunctionCallback<T> setter)
114{
115    int getFuncId;
116    int setFuncId;
117    getFunctions_.emplace(nextFreeId_, new FunctionBinding(name, MethodOptions::NONE, getter));
118    setFunctions_.emplace(nextFreeId_, new FunctionBinding(name, MethodOptions::NONE, setter));
119    functions_.emplace(nextFreeId_, new FunctionBinding(name, MethodOptions::NONE, getter));
120    getFuncId = nextFreeId_++;
121    functions_.emplace(nextFreeId_, new FunctionBinding(name, MethodOptions::NONE, setter));
122    setFuncId = nextFreeId_++;
123
124    ImplDetail<C>::CustomProperty(name, getter, getFuncId, setFuncId);
125}
126
127template<typename C, template<typename> typename ImplDetail>
128void JSClassImpl<C, ImplDetail>::CustomStaticMethod(const char* name, FunctionCallback callback)
129{
130    ImplDetail<C>::CustomStaticMethod(name, callback);
131}
132
133template<typename C, template<typename> typename ImplDetail>
134void JSClassImpl<C, ImplDetail>::ExoticGetter(ExoticGetterCallback callback)
135{
136    ImplDetail<C>::ExoticGetter(callback);
137}
138
139template<typename C, template<typename> typename ImplDetail>
140void JSClassImpl<C, ImplDetail>::ExoticSetter(ExoticSetterCallback callback)
141{
142    ImplDetail<C>::ExoticSetter(callback);
143}
144
145template<typename C, template<typename> typename ImplDetail>
146void JSClassImpl<C, ImplDetail>::ExoticHasProperty(ExoticHasPropertyCallback callback)
147{
148    ImplDetail<C>::ExoticHasProperty(callback);
149}
150
151template<typename C, template<typename> typename ImplDetail>
152template<typename T>
153void JSClassImpl<C, ImplDetail>::StaticConstant(const char* name, T value)
154{
155    ImplDetail<C>::StaticConstant(name, value);
156}
157
158template<typename C, template<typename> typename ImplDetail>
159void JSClassImpl<C, ImplDetail>::Bind(BindingTarget bindTarget, FunctionCallback ctor)
160{
161    ImplDetail<C>::Bind(bindTarget, ctor);
162}
163
164template<typename C, template<typename> typename ImplDetail>
165void JSClassImpl<C, ImplDetail>::Bind(
166    BindingTarget bindTarget, JSFunctionCallback ctor, JSDestructorCallback<C> dtor, JSGCMarkCallback<C> gcMark)
167{
168    ImplDetail<C>::Bind(bindTarget, ctor, dtor, gcMark);
169}
170
171template<typename C, template<typename> typename ImplDetail>
172template<typename... Args>
173void JSClassImpl<C, ImplDetail>::Bind(
174    BindingTarget bindTarget, JSDestructorCallback<C> dtor, JSGCMarkCallback<C> gcMark)
175{
176    ImplDetail<C>::template Bind<Args...>(bindTarget, dtor, gcMark);
177}
178
179template<typename C, template<typename> typename ImplDetail>
180template<typename Base>
181void JSClassImpl<C, ImplDetail>::Inherit()
182{
183    static_assert(std::is_base_of_v<Base, C>, "Calling Inherit() on unrelated classes!");
184    ImplDetail<C>::template Inherit<Base>();
185}
186
187template<typename C, template<typename> typename ImplDetail>
188template<typename Base>
189void JSClassImpl<C, ImplDetail>::InheritAndBind(
190    BindingTarget bindTarget, JSFunctionCallback ctor, JSDestructorCallback<C> dtor, JSGCMarkCallback<C> gcMark)
191{
192    static_assert(std::is_base_of_v<Base, C>, "Calling Inherit() on unrelated classes!");
193    ImplDetail<C>::template InheritAndBind<Base>(bindTarget, ctor, dtor, gcMark);
194}
195
196template<typename C, template<typename> typename ImplDetail>
197IFunctionBinding* JSClassImpl<C, ImplDetail>::GetFunctionBinding(int id)
198{
199    return functions_[id].get();
200}
201
202template<typename C, template<typename> typename ImplDetail>
203IFunctionBinding* JSClassImpl<C, ImplDetail>::GetGetFunctionBinding(int id)
204{
205    return getFunctions_[id].get();
206}
207
208template<typename C, template<typename> typename ImplDetail>
209IFunctionBinding* JSClassImpl<C, ImplDetail>::GetSetFunctionBinding(int id)
210{
211    return setFunctions_[id].get();
212}
213
214template<typename C, template<typename> typename ImplDetail>
215const char* JSClassImpl<C, ImplDetail>::JSName()
216{
217    return jsName.c_str();
218}
219
220template<typename C, template<typename> typename ImplDetail>
221JSRef<JSObject> JSClassImpl<C, ImplDetail>::NewInstance()
222{
223    return JSRef<JSObject>::Make(ImplDetail<C>::NewInstance());
224}
225
226}; // namespace OHOS::Ace::Framework
227