@nativescript/canvas 2.0.0-rc.5 → 2.0.0-rc.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (40) hide show
  1. package/Canvas/common.d.ts +7 -4
  2. package/Canvas/common.js +260 -194
  3. package/Canvas/common.js.map +1 -1
  4. package/Canvas/index.ios.js.map +1 -1
  5. package/TextDecoder/index.d.ts +1 -0
  6. package/TextDecoder/index.js +17 -0
  7. package/TextDecoder/index.js.map +1 -1
  8. package/WebGPU/GPUDevice.js +2 -2
  9. package/WebGPU/GPUDevice.js.map +1 -1
  10. package/angular/esm2022/index.mjs +4 -4
  11. package/angular/fesm2022/nativescript-canvas-angular.mjs +4 -4
  12. package/helpers.d.ts +3 -0
  13. package/helpers.js +9 -0
  14. package/helpers.js.map +1 -1
  15. package/package.json +1 -1
  16. package/platforms/android/canvas-release.aar +0 -0
  17. package/platforms/ios/CanvasNative.xcframework/Info.plist +5 -5
  18. package/platforms/ios/CanvasNative.xcframework/ios-arm64/CanvasNative.framework/CanvasNative +0 -0
  19. package/platforms/ios/CanvasNative.xcframework/ios-arm64/CanvasNative.framework/Headers/canvas_native.h +10 -0
  20. package/platforms/ios/CanvasNative.xcframework/ios-arm64/CanvasNative.framework/Modules/CanvasNative.swiftmodule/Project/arm64-apple-ios.swiftsourceinfo +0 -0
  21. package/platforms/ios/CanvasNative.xcframework/ios-arm64/CanvasNative.framework/Modules/CanvasNative.swiftmodule/arm64-apple-ios.abi.json +11881 -10901
  22. package/platforms/ios/CanvasNative.xcframework/ios-arm64/dSYMs/CanvasNative.framework.dSYM/Contents/Resources/DWARF/CanvasNative +0 -0
  23. package/platforms/ios/CanvasNative.xcframework/ios-arm64/dSYMs/CanvasNative.framework.dSYM/Contents/Resources/Relocations/aarch64/CanvasNative.yml +994 -994
  24. package/platforms/ios/CanvasNative.xcframework/ios-arm64_x86_64-simulator/CanvasNative.framework/CanvasNative +0 -0
  25. package/platforms/ios/CanvasNative.xcframework/ios-arm64_x86_64-simulator/CanvasNative.framework/Headers/canvas_native.h +10 -0
  26. package/platforms/ios/CanvasNative.xcframework/ios-arm64_x86_64-simulator/CanvasNative.framework/Modules/CanvasNative.swiftmodule/Project/arm64-apple-ios-simulator.swiftsourceinfo +0 -0
  27. package/platforms/ios/CanvasNative.xcframework/ios-arm64_x86_64-simulator/CanvasNative.framework/Modules/CanvasNative.swiftmodule/Project/x86_64-apple-ios-simulator.swiftsourceinfo +0 -0
  28. package/platforms/ios/CanvasNative.xcframework/ios-arm64_x86_64-simulator/CanvasNative.framework/Modules/CanvasNative.swiftmodule/arm64-apple-ios-simulator.abi.json +11881 -10901
  29. package/platforms/ios/CanvasNative.xcframework/ios-arm64_x86_64-simulator/CanvasNative.framework/Modules/CanvasNative.swiftmodule/x86_64-apple-ios-simulator.abi.json +11881 -10901
  30. package/platforms/ios/CanvasNative.xcframework/ios-arm64_x86_64-simulator/CanvasNative.framework/_CodeSignature/CodeResources +10 -10
  31. package/platforms/ios/CanvasNative.xcframework/ios-arm64_x86_64-simulator/dSYMs/CanvasNative.framework.dSYM/Contents/Resources/DWARF/CanvasNative +0 -0
  32. package/platforms/ios/CanvasNative.xcframework/ios-arm64_x86_64-simulator/dSYMs/CanvasNative.framework.dSYM/Contents/Resources/Relocations/aarch64/CanvasNative.yml +993 -993
  33. package/platforms/ios/CanvasNative.xcframework/ios-arm64_x86_64-simulator/dSYMs/CanvasNative.framework.dSYM/Contents/Resources/Relocations/x86_64/CanvasNative.yml +1037 -1037
  34. package/platforms/ios/src/cpp/CanvasJSIModule.cpp +172 -2
  35. package/platforms/ios/src/cpp/CanvasJSIModule.h +6 -0
  36. package/platforms/ios/src/cpp/Helpers.h +44 -0
  37. package/platforms/ios/src/cpp/PromiseCallback.h +42 -20
  38. package/platforms/ios/src/cpp/TextDecoderImpl.cpp +142 -0
  39. package/platforms/ios/src/cpp/TextDecoderImpl.h +2 -0
  40. package/platforms/ios/src/cpp/webgpu/GPUQueueImpl.cpp +1 -0
@@ -199,6 +199,18 @@ void CanvasJSIModule::install(v8::Isolate *isolate) {
199
199
  v8::FunctionTemplate::New(isolate, &AddFontData)->GetFunction(
200
200
  context).ToLocalChecked()).FromJust();
201
201
 
202
+ canvasMod->Set(context, ConvertToV8String(isolate, "__base64Encode"),
203
+ v8::FunctionTemplate::New(isolate, &Base64Encode)->GetFunction(
204
+ context).ToLocalChecked()).FromJust();
205
+
206
+ canvasMod->Set(context, ConvertToV8String(isolate, "__base64Decode"),
207
+ v8::FunctionTemplate::New(isolate, &Base64Decode)->GetFunction(
208
+ context).ToLocalChecked()).FromJust();
209
+
210
+ canvasMod->Set(context, ConvertToV8String(isolate, "__base64DecodeAsync"),
211
+ v8::FunctionTemplate::New(isolate, &Base64DecodeAsync)->GetFunction(
212
+ context).ToLocalChecked()).FromJust();
213
+
202
214
  global->Set(context,
203
215
  ConvertToV8String(isolate, "CanvasModule"), canvasMod).FromJust();
204
216
 
@@ -238,7 +250,6 @@ void CanvasJSIModule::AddFontFamily(const v8::FunctionCallbackInfo<v8::Value> &a
238
250
 
239
251
  void CanvasJSIModule::AddFontData(const v8::FunctionCallbackInfo<v8::Value> &args) {
240
252
  auto isolate = args.GetIsolate();
241
- auto context = isolate->GetCurrentContext();
242
253
  auto aliasValue = args[0];
243
254
  auto dataValue = args[1];
244
255
 
@@ -279,9 +290,168 @@ void CanvasJSIModule::AddFontData(const v8::FunctionCallbackInfo<v8::Value> &arg
279
290
 
280
291
  }
281
292
 
293
+ void CanvasJSIModule::Base64Encode(const v8::FunctionCallbackInfo<v8::Value> &args) {
294
+ auto isolate = args.GetIsolate();
295
+ auto dataValue = args[0];
296
+
297
+ auto data = ConvertFromV8StringView(isolate, dataValue);
298
+
299
+ if (data.empty()) {
300
+ args.GetReturnValue().SetEmptyString();
301
+ } else {
302
+ auto encoded = canvas_native_helper_base64_encode((const uint8_t *) data.data(),
303
+ data.size());
304
+ if (encoded == nullptr) {
305
+ args.GetReturnValue().SetEmptyString();
306
+ return;
307
+ }
308
+ auto returnValue = new OneByteStringResource(encoded);
309
+ auto ret = v8::String::NewExternalOneByte(isolate, returnValue);
310
+ v8::Local<v8::Value> value;
311
+ if (ret.ToLocal(&value)) {
312
+ args.GetReturnValue().Set(value);
313
+ } else {
314
+ args.GetReturnValue().SetEmptyString();
315
+ }
316
+
317
+ }
318
+ }
319
+
320
+ void CanvasJSIModule::Base64Decode(const v8::FunctionCallbackInfo<v8::Value> &args) {
321
+ auto isolate = args.GetIsolate();
322
+ auto dataValue = args[0];
323
+
324
+ auto data = ConvertFromV8StringView(isolate, dataValue);
325
+
326
+ if (data.empty()) {
327
+ args.GetReturnValue().SetEmptyString();
328
+ } else {
329
+ auto decoded = canvas_native_helper_base64_decode((const uint8_t *) data.data(),
330
+ data.size());
331
+ if (decoded == nullptr) {
332
+ args.GetReturnValue().SetEmptyString();
333
+ return;
334
+ }
335
+ auto returnValue = new OneByteStringResource(decoded);
336
+ auto ret = v8::String::NewExternalOneByte(isolate, returnValue);
337
+ v8::Local<v8::Value> value;
338
+ auto decoded_clone = canvas_native_u8_buffer_clone(decoded);
339
+ auto buffer_ptr = canvas_native_u8_buffer_get_bytes(decoded_clone);
340
+ auto buffer_len = canvas_native_u8_buffer_get_length(decoded_clone);
341
+ auto buffer = v8::ArrayBuffer::NewBackingStore((void *) buffer_ptr, buffer_len,
342
+ [](void *data,
343
+ size_t length,
344
+ void *deleter_data) {
345
+ if (deleter_data !=
346
+ nullptr) {
347
+ canvas_native_u8_buffer_release(
348
+ (U8Buffer *) deleter_data);
349
+ }
350
+ },
351
+ (void *) decoded_clone);
352
+
353
+ if (ret.ToLocal(&value)) {
354
+ v8::Local<v8::Value> retArgs[2] = {value,
355
+ v8::ArrayBuffer::New(isolate, std::move(buffer))};
356
+ args.GetReturnValue().Set(v8::Array::New(isolate, retArgs, 2));
357
+ } else {
358
+ args.GetReturnValue().Set(v8::Array::New(isolate));
359
+ }
360
+
361
+ }
362
+ }
363
+
364
+ void CanvasJSIModule::Base64DecodeAsync(const v8::FunctionCallbackInfo<v8::Value> &args) {
365
+ auto isolate = args.GetIsolate();
366
+ auto dataValue = args[0];
367
+
368
+ auto resolver = v8::Promise::Resolver::New(isolate->GetCurrentContext()).ToLocalChecked();
369
+ args.GetReturnValue().Set(resolver->GetPromise());
370
+
371
+ v8::String::Utf8Value utf8(isolate, dataValue);
372
+ std::string data(*utf8);
373
+
374
+ auto callback = new PromiseCallback{
375
+ isolate,
376
+ resolver,
377
+ [](bool done, void *data) {
378
+ auto async_data = static_cast<PromiseCallback *>(data);
379
+ auto func = async_data->inner_;
380
+ if (func != nullptr && func->isolate_ != nullptr) {
381
+ v8::Isolate *isolate = func->isolate_;
382
+ v8::Locker locker(isolate);
383
+ v8::Isolate::Scope isolate_scope(
384
+ isolate);
385
+ v8::HandleScope handle_scope(
386
+ isolate);
387
+ v8::Local<v8::Promise::Resolver> callback = func->callback_.Get(
388
+ isolate);
389
+ v8::Local<v8::Context> context = callback->GetCreationContextChecked();
390
+ v8::Context::Scope context_scope(
391
+ context);
392
+
393
+ auto funcData = func->getData();
394
+
395
+ if (funcData == nullptr) {
396
+ callback->Resolve(context, v8::String::Empty(isolate));
397
+ } else {
398
+ auto decoded = static_cast<U8Buffer *>(funcData);
399
+
400
+ auto returnValue = new OneByteStringResource(decoded);
401
+ auto ret = v8::String::NewExternalOneByte(isolate, returnValue);
402
+ v8::Local<v8::Value> value;
403
+ auto decoded_clone = canvas_native_u8_buffer_clone(decoded);
404
+
405
+ func->setData(nullptr);
406
+
407
+ auto buffer_ptr = canvas_native_u8_buffer_get_bytes(decoded_clone);
408
+ auto buffer_len = canvas_native_u8_buffer_get_length(decoded_clone);
409
+ auto buffer = v8::ArrayBuffer::NewBackingStore((void *) buffer_ptr,
410
+ buffer_len,
411
+ [](void *data,
412
+ size_t length,
413
+ void *deleter_data) {
414
+ if (deleter_data !=
415
+ nullptr) {
416
+ canvas_native_u8_buffer_release(
417
+ (U8Buffer *) deleter_data);
418
+ }
419
+ },
420
+ (void *) decoded_clone);
421
+
422
+ if (ret.ToLocal(&value)) {
423
+ v8::Local<v8::Value> retArgs[2] = {value,
424
+ v8::ArrayBuffer::New(isolate,
425
+ std::move(
426
+ buffer))};
427
+ callback->Resolve(context,
428
+ v8::Array::New(isolate, retArgs, 2)).IsJust();
429
+ } else {
430
+ callback->Resolve(context, v8::Array::New(isolate)).IsJust();
431
+ }
432
+ }
433
+ }
434
+
435
+ delete static_cast<PromiseCallback *>(data);
436
+ }
437
+ };
438
+ callback->prepare();
439
+
440
+ std::thread thread(
441
+ [callback](std::string data) {
442
+ if (callback->inner_ != nullptr) {
443
+ auto decoded = canvas_native_helper_base64_decode((const uint8_t *) data.data(),
444
+ data.size());
445
+ callback->inner_->setData(decoded);
446
+ callback->inner_->execute(true, callback);
447
+ }
448
+ }, std::move(data));
449
+ thread.detach();
450
+
451
+ }
452
+
282
453
  void CanvasJSIModule::Create2DContext(const v8::FunctionCallbackInfo<v8::Value> &args) {
283
454
  auto isolate = args.GetIsolate();
284
- auto context = isolate->GetCurrentContext();
285
455
  auto ptr = args[0].As<v8::BigInt>()->Int64Value();
286
456
 
287
457
  auto context_2d = static_cast<CanvasRenderingContext2D *>((void *) ptr);
@@ -48,5 +48,11 @@ public:
48
48
  static void AddFontFamily(const v8::FunctionCallbackInfo<v8::Value> &args);
49
49
 
50
50
  static void AddFontData(const v8::FunctionCallbackInfo<v8::Value> &args);
51
+
52
+ static void Base64Encode(const v8::FunctionCallbackInfo<v8::Value> &args);
53
+
54
+ static void Base64Decode(const v8::FunctionCallbackInfo<v8::Value> &args);
55
+
56
+ static void Base64DecodeAsync(const v8::FunctionCallbackInfo<v8::Value> &args);
51
57
  };
52
58
 
@@ -112,6 +112,50 @@ ConvertFromV8String(v8::Isolate *isolate, const v8::Local<v8::Value> &value) {
112
112
  return {*result};
113
113
  }
114
114
 
115
+ inline static std::string_view
116
+ ConvertFromV8StringView(v8::Isolate *isolate, const v8::Local<v8::Value> &value) {
117
+ if (value.IsEmpty()) {
118
+ return {};
119
+ }
120
+
121
+ if (value->IsStringObject()) {
122
+ v8::Local<v8::String> obj = value.As<v8::StringObject>()->ValueOf();
123
+ return ConvertFromV8StringView(isolate, obj);
124
+ }
125
+
126
+ v8::String::Utf8Value result(isolate, value);
127
+
128
+ const char *val = *result;
129
+
130
+ if (val == nullptr) {
131
+ return {};
132
+ }
133
+
134
+ return {*result};
135
+ }
136
+
137
+ inline static std::string_view
138
+ ConvertFromV8StringViewValue(v8::Isolate *isolate, v8::Local<v8::Value> value) {
139
+ if (value.IsEmpty()) {
140
+ return {};
141
+ }
142
+
143
+ if (value->IsStringObject()) {
144
+ v8::Local<v8::String> obj = value.As<v8::StringObject>()->ValueOf();
145
+ return ConvertFromV8StringViewValue(isolate, obj);
146
+ }
147
+
148
+ v8::String::Utf8Value result(isolate, value);
149
+
150
+ const char *val = *result;
151
+
152
+ if (val == nullptr) {
153
+ return {};
154
+ }
155
+
156
+ return {*result};
157
+ }
158
+
115
159
 
116
160
  static void SetFastMethod(v8::Isolate *isolate,
117
161
  v8::Local<v8::Template> that,
@@ -35,6 +35,7 @@ struct PromiseCallback {
35
35
  CompleteCallback completeCallbackWrapper_;
36
36
  bool isPrepared_ = false;
37
37
  void* data;
38
+ mutable std::mutex mtx;
38
39
 
39
40
  Inner(v8::Isolate *isolate, v8::Local<v8::Promise::Resolver> callback,
40
41
  CompleteCallback completeCallback) : isolate_(isolate),
@@ -45,25 +46,37 @@ struct PromiseCallback {
45
46
  this->completeCallbackWrapper_ = [](bool success, void *data){
46
47
  if(data != nullptr){
47
48
  auto* callback = static_cast<PromiseCallback*>(data);
48
- auto inner = callback->inner_.get();
49
- if(inner == nullptr || inner->current_queue != nullptr){
49
+ if(callback->inner_ == nullptr || callback->inner_->current_queue == nullptr){
50
50
  return;
51
51
  }
52
52
 
53
- inner->current_queue->addOperation([success, data, inner, callback](){
54
- inner->completeCallback_(success, data);
53
+ callback->inner_->current_queue->addOperation([success, data, callback](){
54
+ callback->inner_->completeCallback_(success, data);
55
55
  // delete callback;
56
56
  });
57
57
  }
58
58
  };
59
59
  }
60
60
 
61
+ void setData(void* newData) {
62
+ std::lock_guard<std::mutex> lock(mtx);
63
+ data = newData;
64
+ }
65
+
66
+
67
+ void* getData() {
68
+ std::lock_guard<std::mutex> lock(mtx);
69
+ return data;
70
+ }
71
+
61
72
  void prepare(){
73
+ std::lock_guard<std::mutex> lock(mtx);
62
74
  current_queue = new NSOperationQueueWrapper(true);
63
75
  isPrepared_ = true;
64
76
  }
65
77
 
66
78
  void execute(bool complete, PromiseCallback* callback){
79
+ std::lock_guard<std::mutex> lock(mtx);
67
80
  completeCallbackWrapper_(complete, callback);
68
81
  }
69
82
 
@@ -76,15 +89,13 @@ struct PromiseCallback {
76
89
  std::shared_ptr<Inner> inner_;
77
90
 
78
91
  void prepare(){
79
- auto inner = this->inner_.get();
80
- if(inner == nullptr){return;}
81
- inner->prepare();
92
+ if( this->inner_ == nullptr){return;}
93
+ this->inner_->prepare();
82
94
  }
83
95
 
84
96
  void execute(bool complete) {
85
- auto inner = this->inner_.get();
86
- if (inner == nullptr) { return; }
87
- inner->execute(complete, this);
97
+ if (this->inner_ == nullptr) { return; }
98
+ this->inner_->execute(complete, this);
88
99
  }
89
100
 
90
101
  explicit PromiseCallback(std::shared_ptr<Inner> inner) : inner_(std::move(inner)) {}
@@ -106,6 +117,7 @@ struct PromiseCallback {
106
117
  void *data = nullptr;
107
118
  CompleteCallback completeCallback_;
108
119
  bool isPrepared_ = false;
120
+ mutable std::mutex mtx;
109
121
 
110
122
  Inner(v8::Isolate *isolate, v8::Local<v8::Promise::Resolver> callback,
111
123
  CompleteCallback completeCallback) : isolate_(isolate),
@@ -135,13 +147,25 @@ struct PromiseCallback {
135
147
  isPrepared_ = true;
136
148
  }
137
149
 
138
- void execute(bool complete) const {
150
+ void execute(bool complete, [[maybe_unused]] PromiseCallback *callback) const {
139
151
  if (!isPrepared_) { return; }
140
152
  write(fd_[1],
141
153
  &complete,
142
154
  sizeof(bool));
143
155
  }
144
156
 
157
+ void setData(void *newData) {
158
+ std::lock_guard<std::mutex> lock(mtx);
159
+ data = newData;
160
+ }
161
+
162
+
163
+ void *getData() {
164
+ std::lock_guard<std::mutex> lock(mtx);
165
+ return data;
166
+ }
167
+
168
+
145
169
 
146
170
  ~Inner() {
147
171
  if (!isPrepared_) {
@@ -155,11 +179,10 @@ struct PromiseCallback {
155
179
  };
156
180
 
157
181
  void prepare() const {
158
- auto inner = this->inner_.get();
159
- if (inner == nullptr) { return; }
160
- inner->prepare();
161
- auto looper = inner->looper_;
162
- auto fd = inner->fd_[0];
182
+ if (inner_ == nullptr) { return; }
183
+ inner_->prepare();
184
+ auto looper = inner_->looper_;
185
+ auto fd = inner_->fd_[0];
163
186
  auto data = new PromiseCallback(this->inner_);
164
187
  ALooper_addFd(looper,
165
188
  fd,
@@ -175,13 +198,12 @@ struct PromiseCallback {
175
198
  return 0;
176
199
  }, (void *) data);
177
200
 
178
- inner->isPrepared_ = true;
201
+ inner_->isPrepared_ = true;
179
202
  }
180
203
 
181
204
  void execute(bool complete) const {
182
- auto inner = this->inner_.get();
183
- if (inner == nullptr) { return; }
184
- inner->execute(complete);
205
+ if (this->inner_ == nullptr) { return; }
206
+ this->inner_->execute(complete, nullptr);
185
207
  }
186
208
 
187
209
  std::shared_ptr<Inner> inner_;
@@ -52,6 +52,12 @@ v8::Local<v8::FunctionTemplate> TextDecoderImpl::GetCtor(v8::Isolate *isolate) {
52
52
  tmpl->Set(
53
53
  ConvertToV8String(isolate, "decode"),
54
54
  v8::FunctionTemplate::New(isolate, &Decode));
55
+
56
+ tmpl->Set(
57
+ ConvertToV8String(isolate, "decodeAsync"),
58
+ v8::FunctionTemplate::New(isolate, &DecodeAsync));
59
+
60
+
55
61
  cache->TextDecoderTmpl =
56
62
  std::make_unique<v8::Persistent<v8::FunctionTemplate>>(isolate, ctorTmpl);
57
63
  return ctorTmpl;
@@ -185,3 +191,139 @@ void TextDecoderImpl::Decode(const v8::FunctionCallbackInfo<v8::Value> &args) {
185
191
 
186
192
  args.GetReturnValue().SetEmptyString();
187
193
  }
194
+
195
+ struct DecodeAsyncData {
196
+ v8::Persistent<v8::Object>* buffer;
197
+ uint8_t* data;
198
+ size_t size;
199
+ };
200
+
201
+ void TextDecoderImpl::DecodeAsync(const v8::FunctionCallbackInfo<v8::Value> &args) {
202
+ auto isolate = args.GetIsolate();
203
+
204
+ auto resolver = v8::Promise::Resolver::New(isolate->GetCurrentContext()).ToLocalChecked();
205
+ args.GetReturnValue().Set(resolver->GetPromise());
206
+
207
+ auto context = isolate->GetCurrentContext();
208
+
209
+ auto value = args[0];
210
+ if (value->IsNull() ||
211
+ value->IsUndefined() ||
212
+ !value->IsObject()) {
213
+
214
+ auto msg = v8::Exception::Error(ConvertToV8String(isolate, "Failed to execute 'decode' on 'TextDecoder': The provided value is not of type '(ArrayBuffer or ArrayBufferView)'"));
215
+
216
+ resolver->Reject(context, msg);
217
+
218
+ return;
219
+ }
220
+
221
+ TextDecoderImpl *ptr = GetPointer(args.This());
222
+ if (ptr == nullptr) {
223
+ resolver->Resolve(context, v8::String::Empty(isolate));
224
+ return;
225
+ }
226
+
227
+ if(!value->IsArrayBufferView() && !value->IsArrayBuffer()){
228
+
229
+ auto msg = v8::Exception::Error(ConvertToV8String(isolate, "Failed to execute 'decode' on 'TextDecoder': The provided value is not of type '(ArrayBuffer or ArrayBufferView)'"));
230
+
231
+ resolver->Reject(context, msg);
232
+ return;
233
+ }
234
+
235
+
236
+ auto callback = new PromiseCallback{
237
+ isolate,
238
+ resolver,
239
+ [](bool done, void *data) {
240
+ auto async_data = static_cast<PromiseCallback *>(data);
241
+ auto func = async_data->inner_;
242
+ if (func != nullptr && func->isolate_ != nullptr) {
243
+ v8::Isolate *isolate = func->isolate_;
244
+ v8::Locker locker(isolate);
245
+ v8::Isolate::Scope isolate_scope(
246
+ isolate);
247
+ v8::HandleScope handle_scope(
248
+ isolate);
249
+ v8::Local<v8::Promise::Resolver> callback = func->callback_.Get(
250
+ isolate);
251
+ v8::Local<v8::Context> context = callback->GetCreationContextChecked();
252
+ v8::Context::Scope context_scope(
253
+ context);
254
+
255
+ auto funcData = func->getData();
256
+
257
+ if (funcData == nullptr) {
258
+ callback->Resolve(context, v8::String::Empty(isolate));
259
+ } else {
260
+ auto decoded = static_cast<CCow *>(funcData);
261
+
262
+ auto returnValue = new OneByteStringResource(decoded);
263
+ auto ret = v8::String::NewExternalOneByte(isolate, returnValue);
264
+ v8::Local<v8::Value> value;
265
+ func->setData(nullptr);
266
+
267
+
268
+ if (ret.ToLocal(&value)){
269
+ callback->Resolve(context, value).IsJust();
270
+ } else {
271
+ callback->Resolve(context, v8::String::Empty(isolate)).IsJust();
272
+ }
273
+ }
274
+ }
275
+
276
+ delete static_cast<PromiseCallback *>(data);
277
+ }
278
+ };
279
+ callback->prepare();
280
+
281
+
282
+ auto buf = value.As<v8::Object>();
283
+
284
+ auto bufferPer = new v8::Persistent<v8::Object>(isolate, buf);
285
+
286
+ uint8_t* data = nullptr;
287
+ size_t size;
288
+
289
+ if (buf->IsArrayBuffer()) {
290
+ auto buffer = buf.As<v8::ArrayBuffer>();
291
+ data = static_cast<u_int8_t *>(buffer->GetBackingStore()->Data());
292
+ size = buffer->ByteLength();
293
+ }
294
+
295
+
296
+ if (buf->IsArrayBufferView()) {
297
+ auto buffer = buf.As<v8::ArrayBufferView>();
298
+
299
+ auto store = buffer->Buffer()->GetBackingStore();
300
+ data = static_cast<uint8_t *>(store->Data()) + buffer->ByteOffset();
301
+
302
+ size = buffer->ByteLength();
303
+ }
304
+
305
+ DecodeAsyncData asyncData{
306
+ bufferPer,
307
+ data,
308
+ size
309
+ };
310
+
311
+
312
+ std::thread thread(
313
+ [callback, asyncData, ptr]() {
314
+ if (callback->inner_ != nullptr) {
315
+
316
+ auto decoded = canvas_native_text_decoder_decode_as_cow(
317
+ ptr->GetTextDecoder(),
318
+ asyncData.data, asyncData.size);
319
+
320
+ callback->inner_->setData(decoded);
321
+ callback->inner_->execute(true, callback);
322
+ }
323
+ asyncData.buffer->Reset();
324
+ delete asyncData.buffer;
325
+
326
+ });
327
+ thread.detach();
328
+
329
+ }
@@ -29,6 +29,8 @@ public:
29
29
  static void Ctor(const v8::FunctionCallbackInfo<v8::Value> &args);
30
30
 
31
31
  static void Decode(const v8::FunctionCallbackInfo<v8::Value> &args);
32
+
33
+ static void DecodeAsync(const v8::FunctionCallbackInfo<v8::Value> &args);
32
34
 
33
35
  static void
34
36
  Encoding(v8::Local<v8::String> name, const v8::PropertyCallbackInfo<v8::Value> &info);
@@ -199,6 +199,7 @@ void GPUQueueImpl::CopyExternalImageToTexture(const v8::FunctionCallbackInfo<v8:
199
199
  auto textureVal = destinationObj->Get(context, ConvertToV8String(isolate,
200
200
  "texture")).ToLocalChecked();
201
201
  auto texture = GPUTextureImpl::GetPointer(textureVal.As<v8::Object>())->GetTexture();
202
+
202
203
 
203
204
  uint32_t mipLevel = 0;
204
205
  CanvasOrigin3d origin{0, 0, 0};