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 #ifndef FRAMEWORKS_BRIDGE_DECLARATIVE_FRONTEND_ENGINE_JSI_JSI_TYPES_H 17 #define FRAMEWORKS_BRIDGE_DECLARATIVE_FRONTEND_ENGINE_JSI_JSI_TYPES_H 18 19 #include "ecmascript/napi/include/jsnapi.h" 20 21 #include "frameworks/bridge/declarative_frontend/engine/jsi/jsi_declarative_engine.h" 22 #include "frameworks/bridge/declarative_frontend/engine/jsi/jsi_fwd.h" 23 #include "frameworks/bridge/declarative_frontend/engine/jsi/jsi_value_conversions.h" 24 25 #define FAKE_PTR_FOR_FUNCTION_ACCESS(klass) \ 26 const klass* operator->() const \ 27 { \ 28 return this; \ 29 } 30 31 namespace OHOS::Ace::Framework { 32 33 using JsiFunctionCallback = panda::Local<panda::JSValueRef> (*)(panda::JsiRuntimeCallInfo*); 34 35 template<typename T> 36 class JsiType { 37 public: 38 JsiType() = default; 39 JsiType(const JsiType& rhs); 40 JsiType(JsiType&& rhs); 41 virtual ~JsiType() = default; 42 43 explicit JsiType(panda::Local<T> val); 44 explicit JsiType(const panda::CopyableGlobal<T>& other); 45 46 template<typename S> 47 explicit JsiType(panda::Local<S> val); 48 49 JsiType& operator=(const JsiType& rhs); 50 JsiType& operator=(JsiType&& rhs); 51 52 template<typename S> Cast(const JsiType<S> & that)53 static JsiType<T> Cast(const JsiType<S>& that) 54 { 55 return JsiType<T>(that.GetHandle()); 56 } 57 58 template<class... Args> 59 static JsiType<T> New(Args&&... args); 60 61 void SetWeakCallback(void *ref, panda::WeakRefClearCallBack callback); 62 const panda::CopyableGlobal<T>& GetHandle() const; 63 const panda::CopyableGlobal<T>& operator->() const; 64 Local<T> GetLocalHandle() const; 65 bool IsEmpty() const; 66 bool IsWeak() const; 67 void Reset(); 68 operator panda::CopyableGlobal<T>() const; 69 70 const EcmaVM* GetEcmaVM() const; 71 72 private: 73 panda::CopyableGlobal<T> handle_; 74 }; 75 76 class JsiValue : public JsiType<panda::JSValueRef> { 77 public: 78 JsiValue() = default; 79 explicit JsiValue(const panda::CopyableGlobal<panda::JSValueRef>& val); 80 explicit JsiValue(panda::Local<panda::JSValueRef> val); 81 ~JsiValue() override = default; 82 83 bool IsEmpty() const; 84 bool IsFunction() const; 85 bool IsNumber() const; 86 bool IsString() const; 87 bool IsBoolean() const; 88 bool IsObject() const; 89 bool IsArray() const; 90 bool IsUint8ClampedArray() const; 91 bool IsUndefined() const; 92 bool IsNull() const; 93 std::string ToString() const; 94 bool ToBoolean() const; 95 96 template<typename T> 97 T ToNumber() const; 98 99 static JsiRef<JsiValue> Undefined(); 100 static JsiRef<JsiValue> Null(); 101 static JsiRef<JsiValue> True(); 102 static JsiRef<JsiValue> False(); 103 104 FAKE_PTR_FOR_FUNCTION_ACCESS(JsiValue) 105 }; 106 107 /** 108 * @brief A wrapper around a panda::StringRef 109 * 110 */ 111 class JsiString : public JsiValue { 112 public: 113 explicit JsiString(const char* str); 114 explicit JsiString(JsiValue str); 115 static JsiString New(const char* str); 116 FAKE_PTR_FOR_FUNCTION_ACCESS(JsiString) 117 }; 118 119 /** 120 * @brief A wrapper around a panda::ArrayRef 121 * 122 */ 123 class JsiArray : public JsiType<panda::ArrayRef> { 124 public: 125 JsiArray(); 126 explicit JsiArray(panda::Local<panda::ArrayRef> val); 127 explicit JsiArray(const panda::CopyableGlobal<panda::ArrayRef>& val); 128 ~JsiArray() override = default; 129 JsiRef<JsiValue> GetValueAt(size_t index) const; 130 void SetValueAt(size_t index, JsiRef<JsiValue> value) const; 131 JsiRef<JsiValue> GetProperty(const char* prop) const; 132 size_t Length() const; 133 bool IsArray() const; 134 FAKE_PTR_FOR_FUNCTION_ACCESS(JsiArray) 135 }; 136 137 /** 138 * @brief A wrapper around a panda::ArrayBufferRef 139 * 140 */ 141 class JsiArrayBuffer : public JsiType<panda::ArrayBufferRef> { 142 public: 143 JsiArrayBuffer() = default; 144 explicit JsiArrayBuffer(panda::Local<panda::ArrayBufferRef> val); 145 explicit JsiArrayBuffer(const panda::CopyableGlobal<panda::ArrayBufferRef>& val); 146 int32_t ByteLength() const; 147 void* GetBuffer() const; 148 void Detach() const; 149 bool IsDetach() const; 150 ~JsiArrayBuffer() override = default; 151 FAKE_PTR_FOR_FUNCTION_ACCESS(JsiArrayBuffer) 152 }; 153 154 /** 155 * @brief A wrapper around a panda::Uint8ClampedArrayRef 156 * 157 */ 158 class JsiUint8ClampedArray : public JsiType<panda::Uint8ClampedArrayRef> { 159 public: 160 JsiUint8ClampedArray() = default; 161 explicit JsiUint8ClampedArray(panda::Local<panda::Uint8ClampedArrayRef> val); 162 explicit JsiUint8ClampedArray(const panda::CopyableGlobal<panda::Uint8ClampedArrayRef>& val); 163 ~JsiUint8ClampedArray() override = default; 164 JsiRef<JsiArrayBuffer> GetArrayBuffer() const; 165 FAKE_PTR_FOR_FUNCTION_ACCESS(JsiUint8ClampedArray) 166 }; 167 168 /** 169 * @brief A wrapper around panda::ObjectRef 170 * 171 */ 172 class JsiObject : public JsiType<panda::ObjectRef> { 173 public: 174 JsiObject(); 175 explicit JsiObject(panda::Local<panda::ObjectRef> val); 176 explicit JsiObject(const panda::CopyableGlobal<panda::ObjectRef>& val); 177 bool IsUndefined() const; 178 ~JsiObject() override = default; 179 enum InternalFieldIndex { INSTANCE = 0 }; 180 181 template<typename T> 182 T* Unwrap() const; 183 184 template<typename T> 185 void Wrap(T* data) const; 186 187 JsiRef<JsiArray> GetPropertyNames() const; 188 JsiRef<JsiValue> GetProperty(const char* prop) const; 189 bool HasProperty(const char* prop) const; 190 JsiRef<JsiValue> ToJsonObject(const char* value) const; 191 192 template<typename T> 193 void SetProperty(const char* prop, const T value) const; 194 void SetPropertyJsonObject(const char* prop, const char* value) const; 195 void SetPropertyObject(const char* prop, JsiRef<JsiValue> value) const; 196 197 FAKE_PTR_FOR_FUNCTION_ACCESS(JsiObject) 198 }; 199 200 /** 201 * @brief A wrapper around panda::FunctionRef 202 * 203 */ 204 class JsiFunction : public JsiType<panda::FunctionRef> { 205 public: 206 JsiFunction(); 207 explicit JsiFunction(panda::Local<panda::FunctionRef> val); 208 explicit JsiFunction(const panda::CopyableGlobal<panda::FunctionRef>& val); 209 ~JsiFunction() override = default; 210 211 JsiRef<JsiValue> Call(JsiRef<JsiValue> thisVal, int argc = 0, JsiRef<JsiValue> argv[] = nullptr) const; 212 static panda::Local<panda::FunctionRef> New(JsiFunctionCallback func); 213 214 FAKE_PTR_FOR_FUNCTION_ACCESS(JsiFunction) 215 }; 216 217 class JsiObjTemplate : public JsiObject { 218 public: 219 JsiObjTemplate() = default; 220 explicit JsiObjTemplate(panda::Local<panda::ObjectRef> val); 221 explicit JsiObjTemplate(const panda::CopyableGlobal<panda::ObjectRef>& val); 222 ~JsiObjTemplate() override = default; 223 224 void SetInternalFieldCount(int32_t count) const; 225 JsiRef<JsiObject> NewInstance() const; 226 static panda::Local<panda::JSValueRef> New(); 227 228 FAKE_PTR_FOR_FUNCTION_ACCESS(JsiObjTemplate) 229 }; 230 231 struct JsiExecutionContext { 232 panda::ecmascript::EcmaVM* vm_ = nullptr; 233 }; 234 235 class JsiCallbackInfo { 236 public: 237 JsiCallbackInfo(panda::JsiRuntimeCallInfo* info); 238 ~JsiCallbackInfo() = default; 239 JsiCallbackInfo(const JsiCallbackInfo&) = delete; 240 JsiCallbackInfo& operator=(const JsiCallbackInfo&) = delete; 241 242 JsiRef<JsiValue> operator[](size_t index) const; 243 JsiRef<JsiObject> This() const; 244 int Length() const; 245 246 template<typename T> 247 void SetReturnValue(T* instance) const; 248 249 template<typename T> 250 void SetReturnValue(JsiRef<T> val) const; 251 252 void ReturnSelf() const; 253 GetReturnValue()254 std::variant<void*, panda::CopyableGlobal<panda::JSValueRef>> GetReturnValue() 255 { 256 return retVal_; 257 } 258 GetExecutionContext()259 JsiExecutionContext GetExecutionContext() const 260 { 261 return JsiExecutionContext { info_->GetVM() }; 262 } 263 GetVm()264 panda::ecmascript::EcmaVM* GetVm() const 265 { 266 return info_->GetVM(); 267 } 268 269 private: 270 panda::JsiRuntimeCallInfo* info_ = nullptr; 271 272 mutable std::variant<void*, panda::CopyableGlobal<panda::JSValueRef>> retVal_; 273 }; 274 275 class JsiGCMarkCallbackInfo { 276 public: 277 template<typename T> Mark(const JsiRef<T> & val)278 void Mark(const JsiRef<T>& val) const 279 {} 280 }; 281 282 class JsiDate : public JsiType<panda::DateRef> { 283 public: 284 JsiDate() = default; 285 explicit JsiDate(panda::Local<panda::DateRef> val); 286 explicit JsiDate(const panda::CopyableGlobal<panda::DateRef>& val); 287 ~JsiDate() override = default; 288 289 static JsiRef<JsiValue> New(double value); 290 FAKE_PTR_FOR_FUNCTION_ACCESS(JsiDate) 291 }; 292 293 class JsiException { 294 public: 295 template<typename... Args> 296 static void Throw(const char* format, Args... args); 297 template<typename... Args> 298 static void ThrowRangeError(const char* format, Args... args); 299 template<typename... Args> 300 static void ThrowReferenceError(const char* format, Args... args); 301 template<typename... Args> 302 static void ThrowSyntaxError(const char* format, Args... args); 303 template<typename... Args> 304 static void ThrowTypeError(const char* format, Args... args); 305 template<typename... Args> 306 static void ThrowEvalError(const char* format, Args... args); 307 }; 308 309 } // namespace OHOS::Ace::Framework 310 311 #include "jsi_types.inl" 312 313 #endif // FRAMEWORKS_BRIDGE_DECLARATIVE_FRONTEND_ENGINE_JSI_JSI_TYPES_H 314