@shopify/react-native-skia 1.5.0 → 1.5.2

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 (51) hide show
  1. package/android/cpp/jni/include/JniSkiaBaseView.h +0 -1
  2. package/android/cpp/jni/include/JniSkiaPictureView.h +0 -1
  3. package/android/cpp/rnskia-android/OpenGLContext.h +40 -0
  4. package/android/cpp/rnskia-android/RNSkAndroidPlatformContext.h +5 -5
  5. package/android/cpp/rnskia-android/RNSkAndroidVideo.cpp +2 -2
  6. package/android/cpp/rnskia-android/RNSkOpenGLCanvasProvider.cpp +49 -14
  7. package/android/cpp/rnskia-android/RNSkOpenGLCanvasProvider.h +5 -2
  8. package/android/cpp/rnskia-android/SkiaOpenGLSurfaceFactory.cpp +19 -133
  9. package/android/cpp/rnskia-android/SkiaOpenGLSurfaceFactory.h +30 -138
  10. package/cpp/api/JsiSkTypefaceFontProvider.h +1 -1
  11. package/cpp/api/JsiSkiaContext.h +6 -3
  12. package/cpp/jsi/JsiValue.cpp +1 -2
  13. package/cpp/rnskia/RNSkPlatformContext.h +2 -2
  14. package/cpp/rnskia/{SkiaContext.h → WindowContext.h} +5 -2
  15. package/ios/RNSkia-iOS/DisplayLink.mm +7 -0
  16. package/ios/RNSkia-iOS/MetalContext.h +46 -0
  17. package/ios/RNSkia-iOS/MetalContext.mm +33 -0
  18. package/ios/RNSkia-iOS/RNSkMetalCanvasProvider.mm +8 -28
  19. package/ios/RNSkia-iOS/RNSkiOSPlatformContext.h +1 -1
  20. package/ios/RNSkia-iOS/RNSkiOSPlatformContext.mm +8 -9
  21. package/ios/RNSkia-iOS/RNSkiOSView.mm +0 -2
  22. package/ios/RNSkia-iOS/SkiaMetalSurfaceFactory.h +28 -32
  23. package/ios/RNSkia-iOS/SkiaMetalSurfaceFactory.mm +18 -60
  24. package/ios/RNSkia-iOS/SkiaUIView.h +0 -2
  25. package/ios/RNSkia-iOS/ViewScreenshotService.mm +1 -8
  26. package/lib/commonjs/web/WithSkiaWeb.js +4 -1
  27. package/lib/commonjs/web/WithSkiaWeb.js.map +1 -1
  28. package/lib/module/web/WithSkiaWeb.js +4 -1
  29. package/lib/module/web/WithSkiaWeb.js.map +1 -1
  30. package/libs/ios/libskia.xcframework/ios-arm64_arm64e/libskia.a +0 -0
  31. package/libs/ios/libskia.xcframework/ios-arm64_arm64e_x86_64-simulator/libskia.a +0 -0
  32. package/libs/ios/libskottie.xcframework/Info.plist +5 -5
  33. package/libs/ios/libskottie.xcframework/ios-arm64_arm64e/libskottie.a +0 -0
  34. package/libs/ios/libskottie.xcframework/ios-arm64_arm64e_x86_64-simulator/libskottie.a +0 -0
  35. package/libs/ios/libskparagraph.xcframework/Info.plist +5 -5
  36. package/libs/ios/libskparagraph.xcframework/ios-arm64_arm64e/libskparagraph.a +0 -0
  37. package/libs/ios/libskparagraph.xcframework/ios-arm64_arm64e_x86_64-simulator/libskparagraph.a +0 -0
  38. package/libs/ios/libsksg.xcframework/ios-arm64_arm64e/libsksg.a +0 -0
  39. package/libs/ios/libsksg.xcframework/ios-arm64_arm64e_x86_64-simulator/libsksg.a +0 -0
  40. package/libs/ios/libskshaper.xcframework/Info.plist +5 -5
  41. package/libs/ios/libskshaper.xcframework/ios-arm64_arm64e/libskshaper.a +0 -0
  42. package/libs/ios/libskshaper.xcframework/ios-arm64_arm64e_x86_64-simulator/libskshaper.a +0 -0
  43. package/libs/ios/libskunicode_core.xcframework/ios-arm64_arm64e/libskunicode_core.a +0 -0
  44. package/libs/ios/libskunicode_core.xcframework/ios-arm64_arm64e_x86_64-simulator/libskunicode_core.a +0 -0
  45. package/libs/ios/libskunicode_libgrapheme.xcframework/ios-arm64_arm64e/libskunicode_libgrapheme.a +0 -0
  46. package/libs/ios/libskunicode_libgrapheme.xcframework/ios-arm64_arm64e_x86_64-simulator/libskunicode_libgrapheme.a +0 -0
  47. package/libs/ios/libsvg.xcframework/Info.plist +5 -5
  48. package/libs/ios/libsvg.xcframework/ios-arm64_arm64e/libsvg.a +0 -0
  49. package/libs/ios/libsvg.xcframework/ios-arm64_arm64e_x86_64-simulator/libsvg.a +0 -0
  50. package/package.json +3 -6
  51. package/src/web/WithSkiaWeb.tsx +3 -1
@@ -40,7 +40,7 @@ public:
40
40
  sk_sp<SkTypeface> typeface =
41
41
  JsiSkTypeface::fromValue(runtime, arguments[0]);
42
42
  SkString familyName(arguments[1].asString(runtime).utf8(runtime).c_str());
43
- auto result = getObject()->registerTypeface(typeface, familyName);
43
+ getObject()->registerTypeface(typeface, familyName);
44
44
  return jsi::Value::undefined();
45
45
  }
46
46
 
@@ -14,7 +14,7 @@
14
14
  #include "JsiSkRect.h"
15
15
  #include "JsiSkTypeface.h"
16
16
 
17
- #include "SkiaContext.h"
17
+ #include "WindowContext.h"
18
18
 
19
19
  #pragma clang diagnostic push
20
20
  #pragma clang diagnostic ignored "-Wdocumentation"
@@ -28,12 +28,15 @@ namespace RNSkia {
28
28
 
29
29
  namespace jsi = facebook::jsi;
30
30
 
31
- class JsiSkiaContext : public JsiSkWrappingSharedPtrHostObject<SkiaContext> {
31
+ class JsiSkiaContext : public JsiSkWrappingSharedPtrHostObject<WindowContext> {
32
32
  public:
33
33
  EXPORT_JSI_API_TYPENAME(JsiSkiaContext, SkiaContext)
34
34
 
35
35
  JSI_HOST_FUNCTION(getSurface) {
36
36
  auto surface = getObject()->getSurface();
37
+ if (surface == nullptr) {
38
+ return jsi::Value::null();
39
+ }
37
40
  return jsi::Object::createFromHostObject(
38
41
  runtime,
39
42
  std::make_shared<JsiSkSurface>(getContext(), std::move(surface)));
@@ -48,7 +51,7 @@ public:
48
51
  JSI_EXPORT_FUNC(JsiSkiaContext, present))
49
52
 
50
53
  JsiSkiaContext(std::shared_ptr<RNSkPlatformContext> context,
51
- std::shared_ptr<SkiaContext> ctx)
54
+ std::shared_ptr<WindowContext> ctx)
52
55
  : JsiSkWrappingSharedPtrHostObject(std::move(context), std::move(ctx)) {}
53
56
 
54
57
  /**
@@ -55,9 +55,8 @@ double JsiValue::getAsNumber() const {
55
55
 
56
56
  const std::string &JsiValue::getAsString() const {
57
57
  if (_type == PropType::Number) {
58
- return std::move(std::to_string(_numberValue));
58
+ return std::to_string(_numberValue);
59
59
  }
60
-
61
60
  if (_type != PropType::String) {
62
61
  throw std::runtime_error("Expected type string, got " +
63
62
  getTypeAsString(_type));
@@ -11,7 +11,7 @@
11
11
 
12
12
  #include "RNSkDispatchQueue.h"
13
13
  #include "RNSkVideo.h"
14
- #include "SkiaContext.h"
14
+ #include "WindowContext.h"
15
15
 
16
16
  #pragma clang diagnostic push
17
17
  #pragma clang diagnostic ignored "-Wdocumentation"
@@ -135,7 +135,7 @@ public:
135
135
  */
136
136
  virtual sk_sp<SkSurface> makeOffscreenSurface(int width, int height) = 0;
137
137
 
138
- virtual std::shared_ptr<SkiaContext>
138
+ virtual std::shared_ptr<WindowContext>
139
139
  makeContextFromNativeSurface(void *surface, int width, int height) = 0;
140
140
 
141
141
  /**
@@ -12,11 +12,14 @@
12
12
 
13
13
  namespace RNSkia {
14
14
 
15
- class SkiaContext {
15
+ class WindowContext {
16
16
  public:
17
- virtual ~SkiaContext() = default;
17
+ virtual ~WindowContext() = default;
18
18
  virtual sk_sp<SkSurface> getSurface() = 0;
19
19
  virtual void present() = 0;
20
+ virtual void resize(int width, int height) = 0;
21
+ virtual int getWidth() = 0;
22
+ virtual int getHeight() = 0;
20
23
  };
21
24
 
22
25
  } // namespace RNSkia
@@ -10,6 +10,13 @@
10
10
  _displayLink = [CADisplayLink displayLinkWithTarget:self
11
11
  selector:@selector(update:)];
12
12
 
13
+ if (@available(iOS 15.0, *)) {
14
+ CAFrameRateRange rate = CAFrameRateRangeMake(60, 120, 120);
15
+ _displayLink.preferredFrameRateRange = rate;
16
+ } else {
17
+ _displayLink.preferredFramesPerSecond = 60;
18
+ }
19
+
13
20
  // add the display link to the main run loop
14
21
  [_displayLink addToRunLoop:[NSRunLoop mainRunLoop]
15
22
  forMode:NSRunLoopCommonModes];
@@ -0,0 +1,46 @@
1
+ #pragma once
2
+
3
+ #include "SkiaMetalSurfaceFactory.h"
4
+ #include "WindowContext.h"
5
+
6
+ #include "include/core/SkSurface.h"
7
+
8
+ namespace RNSkia {
9
+ class RNSkiOSPlatformContext;
10
+ }
11
+
12
+ class MetalContext {
13
+
14
+ public:
15
+ MetalContext(const MetalContext &) = delete;
16
+ MetalContext &operator=(const MetalContext &) = delete;
17
+
18
+ static MetalContext &getInstance() {
19
+ static thread_local MetalContext instance;
20
+ return instance;
21
+ }
22
+
23
+ sk_sp<SkSurface> MakeOffscreen(int width, int height) {
24
+ return SkiaMetalSurfaceFactory::makeOffscreenSurface(_device, &_context,
25
+ width, height);
26
+ }
27
+
28
+ sk_sp<SkImage> MakeImageFromBuffer(void *buffer) {
29
+ CVPixelBufferRef sampleBuffer = (CVPixelBufferRef)buffer;
30
+ return SkiaMetalSurfaceFactory::makeTextureFromCVPixelBuffer(&_context,
31
+ sampleBuffer);
32
+ }
33
+
34
+ std::unique_ptr<RNSkia::WindowContext> MakeWindow(CALayer *window, int width,
35
+ int height) {
36
+ return SkiaMetalSurfaceFactory::makeContext(&_context, window, width,
37
+ height);
38
+ }
39
+
40
+ private:
41
+ friend class RNSkia::RNSkiOSPlatformContext;
42
+ id<MTLDevice> _device;
43
+ SkiaMetalContext _context;
44
+
45
+ MetalContext();
46
+ };
@@ -0,0 +1,33 @@
1
+ #include "MetalContext.h"
2
+
3
+ #import <MetalKit/MetalKit.h>
4
+
5
+ #pragma clang diagnostic push
6
+ #pragma clang diagnostic ignored "-Wdocumentation"
7
+
8
+ #import <include/gpu/ganesh/GrBackendSurface.h>
9
+ #import <include/gpu/ganesh/SkImageGanesh.h>
10
+ #import <include/gpu/ganesh/mtl/GrMtlBackendContext.h>
11
+ #import <include/gpu/ganesh/mtl/GrMtlBackendSurface.h>
12
+ #import <include/gpu/ganesh/mtl/GrMtlDirectContext.h>
13
+ #import <include/gpu/ganesh/mtl/GrMtlTypes.h>
14
+ #import <include/gpu/ganesh/mtl/SkSurfaceMetal.h>
15
+
16
+ #pragma clang diagnostic pop
17
+
18
+ MetalContext::MetalContext() {
19
+ _device = MTLCreateSystemDefaultDevice();
20
+ _context.commandQueue =
21
+ id<MTLCommandQueue>(CFRetain((GrMTLHandle)[_device newCommandQueue]));
22
+
23
+ GrMtlBackendContext backendContext = {};
24
+ backendContext.fDevice.reset((__bridge void *)_device);
25
+ backendContext.fQueue.reset((__bridge void *)_context.commandQueue);
26
+ GrContextOptions grContextOptions; // set different options here.
27
+
28
+ // Create the Skia Direct Context
29
+ _context.skContext = GrDirectContexts::MakeMetal(backendContext);
30
+ if (_context.skContext == nullptr) {
31
+ RNSkia::RNSkLogger::logToConsole("Couldn't create a Skia Metal Context");
32
+ }
33
+ }
@@ -1,6 +1,6 @@
1
1
  #import "RNSkMetalCanvasProvider.h"
2
+ #include "MetalContext.h"
2
3
  #import "RNSkLog.h"
3
- #import "SkiaMetalSurfaceFactory.h"
4
4
 
5
5
  #pragma clang diagnostic push
6
6
  #pragma clang diagnostic ignored "-Wdocumentation"
@@ -23,12 +23,6 @@ RNSkMetalCanvasProvider::RNSkMetalCanvasProvider(
23
23
  #pragma clang diagnostic ignored "-Wunguarded-availability-new"
24
24
  _layer = [CAMetalLayer layer];
25
25
  #pragma clang diagnostic pop
26
- _layer.framebufferOnly = NO;
27
- _layer.device = MTLCreateSystemDefaultDevice();
28
- _layer.opaque = false;
29
- _layer.contentsScale = _context->getPixelDensity();
30
- _layer.pixelFormat = MTLPixelFormatBGRA8Unorm;
31
- _layer.contentsGravity = kCAGravityBottomLeft;
32
26
  }
33
27
 
34
28
  RNSkMetalCanvasProvider::~RNSkMetalCanvasProvider() {}
@@ -36,16 +30,12 @@ RNSkMetalCanvasProvider::~RNSkMetalCanvasProvider() {}
36
30
  /**
37
31
  Returns the scaled width of the view
38
32
  */
39
- float RNSkMetalCanvasProvider::getScaledWidth() {
40
- return _width * _context->getPixelDensity();
41
- };
33
+ float RNSkMetalCanvasProvider::getScaledWidth() { return _width; };
42
34
 
43
35
  /**
44
36
  Returns the scaled height of the view
45
37
  */
46
- float RNSkMetalCanvasProvider::getScaledHeight() {
47
- return _height * _context->getPixelDensity();
48
- };
38
+ float RNSkMetalCanvasProvider::getScaledHeight() { return _height; };
49
39
 
50
40
  /**
51
41
  Render to a canvas
@@ -80,11 +70,8 @@ bool RNSkMetalCanvasProvider::renderToCanvas(
80
70
  if (currentDrawable == nullptr) {
81
71
  return false;
82
72
  }
83
-
84
- auto skSurface = SkiaMetalSurfaceFactory::makeWindowedSurface(
85
- currentDrawable.texture, _layer.drawableSize.width,
86
- _layer.drawableSize.height);
87
-
73
+ auto ctx = MetalContext::getInstance().MakeWindow(_layer, _width, _height);
74
+ auto skSurface = ctx->getSurface();
88
75
  SkCanvas *canvas = skSurface->getCanvas();
89
76
  cb(canvas);
90
77
 
@@ -92,22 +79,15 @@ bool RNSkMetalCanvasProvider::renderToCanvas(
92
79
  dContext->flushAndSubmit();
93
80
  }
94
81
 
95
- id<MTLCommandBuffer> commandBuffer(
96
- [ThreadContextHolder::ThreadSkiaMetalContext
97
- .commandQueue commandBuffer]);
98
- [commandBuffer presentDrawable:currentDrawable];
99
- [commandBuffer commit];
82
+ ctx->present();
100
83
  }
101
84
  return true;
102
85
  };
103
86
 
104
87
  void RNSkMetalCanvasProvider::setSize(int width, int height) {
105
- _width = width;
106
- _height = height;
107
88
  _layer.frame = CGRectMake(0, 0, width, height);
108
- _layer.drawableSize = CGSizeMake(width * _context->getPixelDensity(),
109
- height * _context->getPixelDensity());
110
-
89
+ _width = width * _context->getPixelDensity();
90
+ _height = height * _context->getPixelDensity();
111
91
  _requestRedraw();
112
92
  }
113
93
 
@@ -67,7 +67,7 @@ public:
67
67
 
68
68
  std::shared_ptr<RNSkVideo> createVideo(const std::string &url) override;
69
69
 
70
- std::shared_ptr<SkiaContext>
70
+ std::shared_ptr<WindowContext>
71
71
  makeContextFromNativeSurface(void *surface, int width, int height) override;
72
72
 
73
73
  virtual void performStreamOperation(
@@ -5,13 +5,13 @@
5
5
  #include <thread>
6
6
  #include <utility>
7
7
 
8
+ #include "MetalContext.h"
8
9
  #include "RNSkiOSVideo.h"
9
- #import "SkiaCVPixelBufferUtils.h"
10
- #import "SkiaMetalSurfaceFactory.h"
11
10
 
12
11
  #pragma clang diagnostic push
13
12
  #pragma clang diagnostic ignored "-Wdocumentation"
14
13
 
14
+ #import "include/core/SkColorSpace.h"
15
15
  #include "include/core/SkFontMgr.h"
16
16
  #include "include/core/SkSurface.h"
17
17
 
@@ -71,7 +71,7 @@ uint64_t RNSkiOSPlatformContext::makeNativeBuffer(sk_sp<SkImage> image) {
71
71
  if (image->colorType() != kBGRA_8888_SkColorType) {
72
72
  // on iOS, 32_BGRA is the only supported RGB format for CVPixelBuffers.
73
73
  image = image->makeColorTypeAndColorSpace(
74
- ThreadContextHolder::ThreadSkiaMetalContext.skContext.get(),
74
+ MetalContext::getInstance()._context.skContext.get(),
75
75
  kBGRA_8888_SkColorType, SkColorSpace::MakeSRGB());
76
76
  if (image == nullptr) {
77
77
  throw std::runtime_error(
@@ -149,11 +149,11 @@ RNSkiOSPlatformContext::createVideo(const std::string &url) {
149
149
  return std::make_shared<RNSkiOSVideo>(url, this);
150
150
  }
151
151
 
152
- std::shared_ptr<SkiaContext>
152
+ std::shared_ptr<WindowContext>
153
153
  RNSkiOSPlatformContext::makeContextFromNativeSurface(void *surface, int width,
154
154
  int height) {
155
- return SkiaMetalSurfaceFactory::makeContext((__bridge CALayer *)surface,
156
- width, height);
155
+ return MetalContext::getInstance().MakeWindow((__bridge CALayer *)surface,
156
+ width, height);
157
157
  }
158
158
 
159
159
  void RNSkiOSPlatformContext::raiseError(const std::exception &err) {
@@ -162,12 +162,11 @@ void RNSkiOSPlatformContext::raiseError(const std::exception &err) {
162
162
 
163
163
  sk_sp<SkSurface> RNSkiOSPlatformContext::makeOffscreenSurface(int width,
164
164
  int height) {
165
- return SkiaMetalSurfaceFactory::makeOffscreenSurface(width, height);
165
+ return MetalContext::getInstance().MakeOffscreen(width, height);
166
166
  }
167
167
 
168
168
  sk_sp<SkImage> RNSkiOSPlatformContext::makeImageFromNativeBuffer(void *buffer) {
169
- CVPixelBufferRef sampleBuffer = (CVPixelBufferRef)buffer;
170
- return SkiaMetalSurfaceFactory::makeTextureFromCVPixelBuffer(sampleBuffer);
169
+ return MetalContext::getInstance().MakeImageFromBuffer(buffer);
171
170
  }
172
171
 
173
172
  sk_sp<SkFontMgr> RNSkiOSPlatformContext::createFontMgr() {
@@ -1,5 +1,3 @@
1
- #pragma once
2
-
3
1
  #import <memory>
4
2
 
5
3
  #import "RNSkMetalCanvasProvider.h"
@@ -1,9 +1,11 @@
1
+ #pragma once
2
+
1
3
  #import <MetalKit/MetalKit.h>
2
4
 
3
5
  #include <memory>
4
6
 
5
7
  #include "RNSkLog.h"
6
- #include "SkiaContext.h"
8
+ #include "WindowContext.h"
7
9
 
8
10
  #pragma clang diagnostic push
9
11
  #pragma clang diagnostic ignored "-Wdocumentation"
@@ -20,35 +22,31 @@ using SkiaMetalContext = struct SkiaMetalContext {
20
22
  sk_sp<GrDirectContext> skContext = nullptr;
21
23
  };
22
24
 
23
- class ThreadContextHolder {
24
- public:
25
- static thread_local SkiaMetalContext ThreadSkiaMetalContext;
26
- };
27
-
28
25
  class SkiaMetalSurfaceFactory {
29
26
  friend class IOSSkiaContext;
30
27
 
31
28
  public:
32
- static sk_sp<SkSurface> makeWindowedSurface(id<MTLTexture> texture, int width,
29
+ static sk_sp<SkSurface> makeWindowedSurface(SkiaMetalContext *context,
30
+ id<MTLTexture> texture, int width,
33
31
  int height);
34
- static sk_sp<SkSurface> makeOffscreenSurface(int width, int height);
32
+ static sk_sp<SkSurface> makeOffscreenSurface(id<MTLDevice> device,
33
+ SkiaMetalContext *context,
34
+ int width, int height);
35
35
 
36
36
  static sk_sp<SkImage>
37
- makeTextureFromCVPixelBuffer(CVPixelBufferRef pixelBuffer);
38
-
39
- static std::shared_ptr<RNSkia::SkiaContext>
40
- makeContext(CALayer *texture, int width, int height);
37
+ makeTextureFromCVPixelBuffer(SkiaMetalContext *context,
38
+ CVPixelBufferRef pixelBuffer);
41
39
 
42
- private:
43
- static id<MTLDevice> device;
44
- static bool
45
- createSkiaDirectContextIfNecessary(SkiaMetalContext *threadContext);
40
+ static std::unique_ptr<RNSkia::WindowContext>
41
+ makeContext(SkiaMetalContext *context, CALayer *texture, int width,
42
+ int height);
46
43
  };
47
44
 
48
- class IOSSkiaContext : public RNSkia::SkiaContext {
45
+ class IOSSkiaContext : public RNSkia::WindowContext {
49
46
  public:
50
- IOSSkiaContext(CALayer *layer, int width, int height) {
51
- auto pd = 3;
47
+ IOSSkiaContext(SkiaMetalContext *context, CALayer *layer, int width,
48
+ int height)
49
+ : _context(context) {
52
50
  #pragma clang diagnostic push
53
51
  #pragma clang diagnostic ignored "-Wunguarded-availability-new"
54
52
  _layer = (CAMetalLayer *)layer;
@@ -56,12 +54,10 @@ public:
56
54
  _layer.framebufferOnly = NO;
57
55
  _layer.device = MTLCreateSystemDefaultDevice();
58
56
  _layer.opaque = false;
59
- _layer.contentsScale = pd;
57
+ _layer.contentsScale = 3;
60
58
  _layer.pixelFormat = MTLPixelFormatBGRA8Unorm;
61
59
  _layer.contentsGravity = kCAGravityBottomLeft;
62
-
63
- _layer.frame = CGRectMake(0, 0, width, height);
64
- _layer.drawableSize = CGSizeMake(width * pd, height * pd);
60
+ _layer.drawableSize = CGSizeMake(width, height);
65
61
  }
66
62
 
67
63
  ~IOSSkiaContext() {}
@@ -70,11 +66,6 @@ public:
70
66
  if (_skSurface) {
71
67
  return _skSurface;
72
68
  }
73
- // Create the Skia Direct Context if it doesn't exist
74
- if (!SkiaMetalSurfaceFactory::createSkiaDirectContextIfNecessary(
75
- &ThreadContextHolder::ThreadSkiaMetalContext)) {
76
- return nullptr;
77
- }
78
69
 
79
70
  // Get the next drawable from the CAMetalLayer
80
71
  _currentDrawable = [_layer nextDrawable];
@@ -86,7 +77,7 @@ public:
86
77
 
87
78
  // Get the texture from the drawable
88
79
  _skSurface = SkiaMetalSurfaceFactory::makeWindowedSurface(
89
- _currentDrawable.texture, _layer.drawableSize.width,
80
+ _context, _currentDrawable.texture, _layer.drawableSize.width,
90
81
  _layer.drawableSize.height);
91
82
  return _skSurface;
92
83
  }
@@ -96,15 +87,20 @@ public:
96
87
  dContext->flushAndSubmit();
97
88
  }
98
89
 
99
- id<MTLCommandBuffer> commandBuffer(
100
- [ThreadContextHolder::ThreadSkiaMetalContext
101
- .commandQueue commandBuffer]);
90
+ id<MTLCommandBuffer> commandBuffer([_context->commandQueue commandBuffer]);
102
91
  [commandBuffer presentDrawable:_currentDrawable];
103
92
  [commandBuffer commit];
104
93
  _skSurface = nullptr;
105
94
  }
106
95
 
96
+ void resize(int width, int height) override { _skSurface = nullptr; }
97
+
98
+ int getWidth() override { return _layer.frame.size.width; };
99
+
100
+ int getHeight() override { return _layer.frame.size.height; };
101
+
107
102
  private:
103
+ SkiaMetalContext *_context;
108
104
  sk_sp<SkSurface> _skSurface = nullptr;
109
105
  #pragma clang diagnostic push
110
106
  #pragma clang diagnostic ignored "-Wunguarded-availability-new"
@@ -21,8 +21,6 @@
21
21
 
22
22
  #pragma clang diagnostic pop
23
23
 
24
- thread_local SkiaMetalContext ThreadContextHolder::ThreadSkiaMetalContext;
25
-
26
24
  struct OffscreenRenderContext {
27
25
  id<MTLTexture> texture;
28
26
 
@@ -42,43 +40,14 @@ struct OffscreenRenderContext {
42
40
  }
43
41
  };
44
42
 
45
- id<MTLDevice> SkiaMetalSurfaceFactory::device = MTLCreateSystemDefaultDevice();
46
-
47
- bool SkiaMetalSurfaceFactory::createSkiaDirectContextIfNecessary(
48
- SkiaMetalContext *skiaMetalContext) {
49
- if (skiaMetalContext->skContext == nullptr) {
50
- skiaMetalContext->commandQueue =
51
- id<MTLCommandQueue>(CFRetain((GrMTLHandle)[device newCommandQueue]));
52
-
53
- GrMtlBackendContext backendContext = {};
54
- backendContext.fDevice.reset((__bridge void *)device);
55
- backendContext.fQueue.reset(
56
- (__bridge void *)skiaMetalContext->commandQueue);
57
- GrContextOptions grContextOptions; // set different options here.
58
-
59
- // Create the Skia Direct Context
60
- skiaMetalContext->skContext = GrDirectContexts::MakeMetal(backendContext);
61
- if (skiaMetalContext->skContext == nullptr) {
62
- RNSkia::RNSkLogger::logToConsole("Couldn't create a Skia Metal Context");
63
- return false;
64
- }
65
- }
66
- return true;
67
- }
68
-
69
- std::shared_ptr<RNSkia::SkiaContext>
70
- SkiaMetalSurfaceFactory::makeContext(CALayer *texture, int width, int height) {
71
- return std::make_shared<IOSSkiaContext>(texture, width, height);
43
+ std::unique_ptr<RNSkia::WindowContext>
44
+ SkiaMetalSurfaceFactory::makeContext(SkiaMetalContext *context,
45
+ CALayer *texture, int width, int height) {
46
+ return std::make_unique<IOSSkiaContext>(context, texture, width, height);
72
47
  }
73
48
 
74
- sk_sp<SkSurface>
75
- SkiaMetalSurfaceFactory::makeWindowedSurface(id<MTLTexture> texture, int width,
76
- int height) {
77
- // Get render context for current thread
78
- if (!SkiaMetalSurfaceFactory::createSkiaDirectContextIfNecessary(
79
- &ThreadContextHolder::ThreadSkiaMetalContext)) {
80
- return nullptr;
81
- }
49
+ sk_sp<SkSurface> SkiaMetalSurfaceFactory::makeWindowedSurface(
50
+ SkiaMetalContext *context, id<MTLTexture> texture, int width, int height) {
82
51
  GrMtlTextureInfo fbInfo;
83
52
  fbInfo.fTexture.retain((__bridge void *)texture);
84
53
 
@@ -86,8 +55,8 @@ SkiaMetalSurfaceFactory::makeWindowedSurface(id<MTLTexture> texture, int width,
86
55
  GrBackendRenderTargets::MakeMtl(width, height, fbInfo);
87
56
 
88
57
  auto skSurface = SkSurfaces::WrapBackendRenderTarget(
89
- ThreadContextHolder::ThreadSkiaMetalContext.skContext.get(), backendRT,
90
- kTopLeft_GrSurfaceOrigin, kBGRA_8888_SkColorType, nullptr, nullptr);
58
+ context->skContext.get(), backendRT, kTopLeft_GrSurfaceOrigin,
59
+ kBGRA_8888_SkColorType, nullptr, nullptr);
91
60
 
92
61
  if (skSurface == nullptr || skSurface->getCanvas() == nullptr) {
93
62
  RNSkia::RNSkLogger::logToConsole(
@@ -97,15 +66,11 @@ SkiaMetalSurfaceFactory::makeWindowedSurface(id<MTLTexture> texture, int width,
97
66
  return skSurface;
98
67
  }
99
68
 
100
- sk_sp<SkSurface> SkiaMetalSurfaceFactory::makeOffscreenSurface(int width,
101
- int height) {
102
- if (!SkiaMetalSurfaceFactory::createSkiaDirectContextIfNecessary(
103
- &ThreadContextHolder::ThreadSkiaMetalContext)) {
104
- return nullptr;
105
- }
106
- auto ctx = new OffscreenRenderContext(
107
- device, ThreadContextHolder::ThreadSkiaMetalContext.skContext,
108
- ThreadContextHolder::ThreadSkiaMetalContext.commandQueue, width, height);
69
+ sk_sp<SkSurface> SkiaMetalSurfaceFactory::makeOffscreenSurface(
70
+ id<MTLDevice> device, SkiaMetalContext *context, int width, int height) {
71
+
72
+ auto ctx = new OffscreenRenderContext(device, context->skContext,
73
+ context->commandQueue, width, height);
109
74
 
110
75
  // Create a GrBackendTexture from the Metal texture
111
76
  GrMtlTextureInfo info;
@@ -115,34 +80,27 @@ sk_sp<SkSurface> SkiaMetalSurfaceFactory::makeOffscreenSurface(int width,
115
80
 
116
81
  // Create a SkSurface from the GrBackendTexture
117
82
  auto surface = SkSurfaces::WrapBackendTexture(
118
- ThreadContextHolder::ThreadSkiaMetalContext.skContext.get(),
119
- backendTexture, kTopLeft_GrSurfaceOrigin, 0, kBGRA_8888_SkColorType,
120
- nullptr, nullptr,
83
+ context->skContext.get(), backendTexture, kTopLeft_GrSurfaceOrigin, 0,
84
+ kBGRA_8888_SkColorType, nullptr, nullptr,
121
85
  [](void *addr) { delete (OffscreenRenderContext *)addr; }, ctx);
122
86
 
123
87
  return surface;
124
88
  }
125
89
 
126
90
  sk_sp<SkImage> SkiaMetalSurfaceFactory::makeTextureFromCVPixelBuffer(
127
- CVPixelBufferRef pixelBuffer) {
128
- if (!SkiaMetalSurfaceFactory::createSkiaDirectContextIfNecessary(
129
- &ThreadContextHolder::ThreadSkiaMetalContext)) [[unlikely]] {
130
- throw std::runtime_error("Failed to create Skia Context for this Thread!");
131
- }
132
- const SkiaMetalContext &context = ThreadContextHolder::ThreadSkiaMetalContext;
133
-
91
+ SkiaMetalContext *context, CVPixelBufferRef pixelBuffer) {
134
92
  SkiaCVPixelBufferUtils::CVPixelBufferBaseFormat format =
135
93
  SkiaCVPixelBufferUtils::getCVPixelBufferBaseFormat(pixelBuffer);
136
94
  switch (format) {
137
95
  case SkiaCVPixelBufferUtils::CVPixelBufferBaseFormat::rgb: {
138
96
  // CVPixelBuffer is in any RGB format, single-plane
139
97
  return SkiaCVPixelBufferUtils::RGB::makeSkImageFromCVPixelBuffer(
140
- context.skContext.get(), pixelBuffer);
98
+ context->skContext.get(), pixelBuffer);
141
99
  }
142
100
  case SkiaCVPixelBufferUtils::CVPixelBufferBaseFormat::yuv: {
143
101
  // CVPixelBuffer is in any YUV format, multi-plane
144
102
  return SkiaCVPixelBufferUtils::YUV::makeSkImageFromCVPixelBuffer(
145
- context.skContext.get(), pixelBuffer);
103
+ context->skContext.get(), pixelBuffer);
146
104
  }
147
105
  default:
148
106
  [[unlikely]] {
@@ -14,8 +14,6 @@
14
14
  #import <React/RCTViewComponentView.h>
15
15
  #endif // RCT_NEW_ARCH_ENABLED
16
16
 
17
- class RNSkiOSJsView;
18
-
19
17
  @interface SkiaUIView :
20
18
  #if RCT_NEW_ARCH_ENABLED
21
19
  RCTViewComponentView
@@ -34,14 +34,7 @@
34
34
  UIGraphicsImageRendererFormat *format =
35
35
  [UIGraphicsImageRendererFormat defaultFormat];
36
36
  format.opaque = NO;
37
-
38
- // Explicitly ask for the standard format to get ARGB 32bits and not 64bits.
39
- if (@available(iOS 12.0, *)) {
40
- format.preferredRange = UIGraphicsImageRendererFormatRangeStandard;
41
- } else {
42
- // Fallback on earlier versions
43
- format.prefersExtendedRange = false;
44
- }
37
+ format.preferredRange = UIGraphicsImageRendererFormatRangeStandard;
45
38
 
46
39
  UIGraphicsImageRenderer *renderer =
47
40
  [[UIGraphicsImageRenderer alloc] initWithSize:size format:format];
@@ -25,7 +25,10 @@ const WithSkiaWeb = ({
25
25
  console.warn("<WithSkiaWeb /> is only necessary on web. Consider not using on native.");
26
26
  }
27
27
  return getComponent();
28
- }), [getComponent, opts]);
28
+ }),
29
+ // We we to run this only once.
30
+ // eslint-disable-next-line react-hooks/exhaustive-deps
31
+ []);
29
32
  return /*#__PURE__*/_react.default.createElement(_react.Suspense, {
30
33
  fallback: fallback !== null && fallback !== void 0 ? fallback : null
31
34
  }, /*#__PURE__*/_react.default.createElement(Inner, componentProps));
@@ -1 +1 @@
1
- {"version":3,"names":["_react","_interopRequireWildcard","require","_Platform","_LoadSkiaWeb","_getRequireWildcardCache","e","WeakMap","r","t","__esModule","default","has","get","n","__proto__","a","Object","defineProperty","getOwnPropertyDescriptor","u","hasOwnProperty","call","i","set","WithSkiaWeb","getComponent","fallback","opts","componentProps","Inner","useMemo","lazy","Platform","OS","LoadSkiaWeb","console","warn","createElement","Suspense","exports"],"sources":["WithSkiaWeb.tsx"],"sourcesContent":["import type { ComponentProps, ComponentType } from \"react\";\nimport React, { useMemo, lazy, Suspense } from \"react\";\n\nimport { Platform } from \"../Platform\";\n\nimport { LoadSkiaWeb } from \"./LoadSkiaWeb\";\n\ntype NonOptionalKeys<T> = {\n [k in keyof T]-?: undefined extends T[k] ? never : k;\n}[keyof T];\n\ntype WithSkiaProps<TProps> = {\n fallback?: ComponentProps<typeof Suspense>[\"fallback\"];\n getComponent: () => Promise<{ default: ComponentType<TProps> }>;\n opts?: Parameters<typeof LoadSkiaWeb>[0];\n} & (NonOptionalKeys<TProps> extends never\n ? {\n componentProps?: TProps;\n }\n : {\n componentProps: TProps;\n });\n\nexport const WithSkiaWeb = <TProps extends object>({\n getComponent,\n fallback,\n opts,\n componentProps,\n}: WithSkiaProps<TProps>) => {\n const Inner = useMemo(\n // TODO: investigate\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n (): any =>\n lazy(async () => {\n if (Platform.OS === \"web\") {\n await LoadSkiaWeb(opts);\n } else {\n console.warn(\n \"<WithSkiaWeb /> is only necessary on web. Consider not using on native.\"\n );\n }\n return getComponent();\n }),\n [getComponent, opts]\n );\n return (\n <Suspense fallback={fallback ?? null}>\n <Inner {...componentProps} />\n </Suspense>\n );\n};\n"],"mappings":";;;;;;AACA,IAAAA,MAAA,GAAAC,uBAAA,CAAAC,OAAA;AAEA,IAAAC,SAAA,GAAAD,OAAA;AAEA,IAAAE,YAAA,GAAAF,OAAA;AAA4C,SAAAG,yBAAAC,CAAA,6BAAAC,OAAA,mBAAAC,CAAA,OAAAD,OAAA,IAAAE,CAAA,OAAAF,OAAA,YAAAF,wBAAA,YAAAA,CAAAC,CAAA,WAAAA,CAAA,GAAAG,CAAA,GAAAD,CAAA,KAAAF,CAAA;AAAA,SAAAL,wBAAAK,CAAA,EAAAE,CAAA,SAAAA,CAAA,IAAAF,CAAA,IAAAA,CAAA,CAAAI,UAAA,SAAAJ,CAAA,eAAAA,CAAA,uBAAAA,CAAA,yBAAAA,CAAA,WAAAK,OAAA,EAAAL,CAAA,QAAAG,CAAA,GAAAJ,wBAAA,CAAAG,CAAA,OAAAC,CAAA,IAAAA,CAAA,CAAAG,GAAA,CAAAN,CAAA,UAAAG,CAAA,CAAAI,GAAA,CAAAP,CAAA,OAAAQ,CAAA,KAAAC,SAAA,UAAAC,CAAA,GAAAC,MAAA,CAAAC,cAAA,IAAAD,MAAA,CAAAE,wBAAA,WAAAC,CAAA,IAAAd,CAAA,oBAAAc,CAAA,OAAAC,cAAA,CAAAC,IAAA,CAAAhB,CAAA,EAAAc,CAAA,SAAAG,CAAA,GAAAP,CAAA,GAAAC,MAAA,CAAAE,wBAAA,CAAAb,CAAA,EAAAc,CAAA,UAAAG,CAAA,KAAAA,CAAA,CAAAV,GAAA,IAAAU,CAAA,CAAAC,GAAA,IAAAP,MAAA,CAAAC,cAAA,CAAAJ,CAAA,EAAAM,CAAA,EAAAG,CAAA,IAAAT,CAAA,CAAAM,CAAA,IAAAd,CAAA,CAAAc,CAAA,YAAAN,CAAA,CAAAH,OAAA,GAAAL,CAAA,EAAAG,CAAA,IAAAA,CAAA,CAAAe,GAAA,CAAAlB,CAAA,EAAAQ,CAAA,GAAAA,CAAA;AAkBrC,MAAMW,WAAW,GAAGA,CAAwB;EACjDC,YAAY;EACZC,QAAQ;EACRC,IAAI;EACJC;AACqB,CAAC,KAAK;EAC3B,MAAMC,KAAK,GAAG,IAAAC,cAAO;EACnB;EACA;EACA,mBACE,IAAAC,WAAI,EAAC,YAAY;IACf,IAAIC,kBAAQ,CAACC,EAAE,KAAK,KAAK,EAAE;MACzB,MAAM,IAAAC,wBAAW,EAACP,IAAI,CAAC;IACzB,CAAC,MAAM;MACLQ,OAAO,CAACC,IAAI,CACV,yEACF,CAAC;IACH;IACA,OAAOX,YAAY,CAAC,CAAC;EACvB,CAAC,CAAC,EACJ,CAACA,YAAY,EAAEE,IAAI,CACrB,CAAC;EACD,oBACE5B,MAAA,CAAAW,OAAA,CAAA2B,aAAA,CAACtC,MAAA,CAAAuC,QAAQ;IAACZ,QAAQ,EAAEA,QAAQ,aAARA,QAAQ,cAARA,QAAQ,GAAI;EAAK,gBACnC3B,MAAA,CAAAW,OAAA,CAAA2B,aAAA,CAACR,KAAK,EAAKD,cAAiB,CACpB,CAAC;AAEf,CAAC;AAACW,OAAA,CAAAf,WAAA,GAAAA,WAAA","ignoreList":[]}
1
+ {"version":3,"names":["_react","_interopRequireWildcard","require","_Platform","_LoadSkiaWeb","_getRequireWildcardCache","e","WeakMap","r","t","__esModule","default","has","get","n","__proto__","a","Object","defineProperty","getOwnPropertyDescriptor","u","hasOwnProperty","call","i","set","WithSkiaWeb","getComponent","fallback","opts","componentProps","Inner","useMemo","lazy","Platform","OS","LoadSkiaWeb","console","warn","createElement","Suspense","exports"],"sources":["WithSkiaWeb.tsx"],"sourcesContent":["import type { ComponentProps, ComponentType } from \"react\";\nimport React, { useMemo, lazy, Suspense } from \"react\";\n\nimport { Platform } from \"../Platform\";\n\nimport { LoadSkiaWeb } from \"./LoadSkiaWeb\";\n\ntype NonOptionalKeys<T> = {\n [k in keyof T]-?: undefined extends T[k] ? never : k;\n}[keyof T];\n\ntype WithSkiaProps<TProps> = {\n fallback?: ComponentProps<typeof Suspense>[\"fallback\"];\n getComponent: () => Promise<{ default: ComponentType<TProps> }>;\n opts?: Parameters<typeof LoadSkiaWeb>[0];\n} & (NonOptionalKeys<TProps> extends never\n ? {\n componentProps?: TProps;\n }\n : {\n componentProps: TProps;\n });\n\nexport const WithSkiaWeb = <TProps extends object>({\n getComponent,\n fallback,\n opts,\n componentProps,\n}: WithSkiaProps<TProps>) => {\n const Inner = useMemo(\n // TODO: investigate\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n (): any =>\n lazy(async () => {\n if (Platform.OS === \"web\") {\n await LoadSkiaWeb(opts);\n } else {\n console.warn(\n \"<WithSkiaWeb /> is only necessary on web. Consider not using on native.\"\n );\n }\n return getComponent();\n }),\n // We we to run this only once.\n // eslint-disable-next-line react-hooks/exhaustive-deps\n []\n );\n return (\n <Suspense fallback={fallback ?? null}>\n <Inner {...componentProps} />\n </Suspense>\n );\n};\n"],"mappings":";;;;;;AACA,IAAAA,MAAA,GAAAC,uBAAA,CAAAC,OAAA;AAEA,IAAAC,SAAA,GAAAD,OAAA;AAEA,IAAAE,YAAA,GAAAF,OAAA;AAA4C,SAAAG,yBAAAC,CAAA,6BAAAC,OAAA,mBAAAC,CAAA,OAAAD,OAAA,IAAAE,CAAA,OAAAF,OAAA,YAAAF,wBAAA,YAAAA,CAAAC,CAAA,WAAAA,CAAA,GAAAG,CAAA,GAAAD,CAAA,KAAAF,CAAA;AAAA,SAAAL,wBAAAK,CAAA,EAAAE,CAAA,SAAAA,CAAA,IAAAF,CAAA,IAAAA,CAAA,CAAAI,UAAA,SAAAJ,CAAA,eAAAA,CAAA,uBAAAA,CAAA,yBAAAA,CAAA,WAAAK,OAAA,EAAAL,CAAA,QAAAG,CAAA,GAAAJ,wBAAA,CAAAG,CAAA,OAAAC,CAAA,IAAAA,CAAA,CAAAG,GAAA,CAAAN,CAAA,UAAAG,CAAA,CAAAI,GAAA,CAAAP,CAAA,OAAAQ,CAAA,KAAAC,SAAA,UAAAC,CAAA,GAAAC,MAAA,CAAAC,cAAA,IAAAD,MAAA,CAAAE,wBAAA,WAAAC,CAAA,IAAAd,CAAA,oBAAAc,CAAA,OAAAC,cAAA,CAAAC,IAAA,CAAAhB,CAAA,EAAAc,CAAA,SAAAG,CAAA,GAAAP,CAAA,GAAAC,MAAA,CAAAE,wBAAA,CAAAb,CAAA,EAAAc,CAAA,UAAAG,CAAA,KAAAA,CAAA,CAAAV,GAAA,IAAAU,CAAA,CAAAC,GAAA,IAAAP,MAAA,CAAAC,cAAA,CAAAJ,CAAA,EAAAM,CAAA,EAAAG,CAAA,IAAAT,CAAA,CAAAM,CAAA,IAAAd,CAAA,CAAAc,CAAA,YAAAN,CAAA,CAAAH,OAAA,GAAAL,CAAA,EAAAG,CAAA,IAAAA,CAAA,CAAAe,GAAA,CAAAlB,CAAA,EAAAQ,CAAA,GAAAA,CAAA;AAkBrC,MAAMW,WAAW,GAAGA,CAAwB;EACjDC,YAAY;EACZC,QAAQ;EACRC,IAAI;EACJC;AACqB,CAAC,KAAK;EAC3B,MAAMC,KAAK,GAAG,IAAAC,cAAO;EACnB;EACA;EACA,mBACE,IAAAC,WAAI,EAAC,YAAY;IACf,IAAIC,kBAAQ,CAACC,EAAE,KAAK,KAAK,EAAE;MACzB,MAAM,IAAAC,wBAAW,EAACP,IAAI,CAAC;IACzB,CAAC,MAAM;MACLQ,OAAO,CAACC,IAAI,CACV,yEACF,CAAC;IACH;IACA,OAAOX,YAAY,CAAC,CAAC;EACvB,CAAC,CAAC;EACJ;EACA;EACA,EACF,CAAC;EACD,oBACE1B,MAAA,CAAAW,OAAA,CAAA2B,aAAA,CAACtC,MAAA,CAAAuC,QAAQ;IAACZ,QAAQ,EAAEA,QAAQ,aAARA,QAAQ,cAARA,QAAQ,GAAI;EAAK,gBACnC3B,MAAA,CAAAW,OAAA,CAAA2B,aAAA,CAACR,KAAK,EAAKD,cAAiB,CACpB,CAAC;AAEf,CAAC;AAACW,OAAA,CAAAf,WAAA,GAAAA,WAAA","ignoreList":[]}
@@ -17,7 +17,10 @@ export const WithSkiaWeb = ({
17
17
  console.warn("<WithSkiaWeb /> is only necessary on web. Consider not using on native.");
18
18
  }
19
19
  return getComponent();
20
- }), [getComponent, opts]);
20
+ }),
21
+ // We we to run this only once.
22
+ // eslint-disable-next-line react-hooks/exhaustive-deps
23
+ []);
21
24
  return /*#__PURE__*/React.createElement(Suspense, {
22
25
  fallback: fallback !== null && fallback !== void 0 ? fallback : null
23
26
  }, /*#__PURE__*/React.createElement(Inner, componentProps));