@shopify/react-native-skia 1.8.2 → 1.9.0
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.
- package/android/cpp/rnskia-android/MainThreadDispatcher.h +1 -1
- package/android/cpp/rnskia-android/OpenGLContext.h +4 -4
- package/android/cpp/rnskia-android/RNSkOpenGLCanvasProvider.cpp +3 -3
- package/cpp/api/JsiSkCanvas.h +27 -25
- package/cpp/api/JsiSkImage.h +24 -0
- package/cpp/api/JsiSkPaint.h +1 -1
- package/cpp/rnskia/dom/nodes/JsiAtlasNode.h +5 -1
- package/cpp/rnskia/dom/nodes/JsiImageNode.h +8 -4
- package/cpp/rnskia/dom/nodes/JsiShaderNodes.h +9 -38
- package/cpp/rnskia/dom/props/SamplingProp.h +54 -0
- package/ios/RNSkia-iOS/SkiaManager.mm +2 -4
- package/lib/commonjs/dom/types/Drawings.d.ts +3 -1
- package/lib/commonjs/dom/types/Drawings.js.map +1 -1
- package/lib/commonjs/dom/types/Shaders.d.ts +2 -3
- package/lib/commonjs/dom/types/Shaders.js.map +1 -1
- package/lib/commonjs/renderer/components/image/ImageShader.d.ts +1 -1
- package/lib/commonjs/renderer/components/image/ImageShader.js +0 -4
- package/lib/commonjs/renderer/components/image/ImageShader.js.map +1 -1
- package/lib/commonjs/skia/types/Canvas.d.ts +2 -2
- package/lib/commonjs/skia/types/Canvas.js.map +1 -1
- package/lib/commonjs/skia/types/Image/Image.d.ts +18 -0
- package/lib/commonjs/skia/types/Image/Image.js +24 -1
- package/lib/commonjs/skia/types/Image/Image.js.map +1 -1
- package/lib/commonjs/skia/types/Picture/PictureRecorder.d.ts +2 -1
- package/lib/commonjs/skia/types/Picture/PictureRecorder.js.map +1 -1
- package/lib/commonjs/skia/web/JsiSkCanvas.d.ts +2 -2
- package/lib/commonjs/skia/web/JsiSkCanvas.js +15 -2
- package/lib/commonjs/skia/web/JsiSkCanvas.js.map +1 -1
- package/lib/commonjs/sksg/Container.d.ts +17 -14
- package/lib/commonjs/sksg/Container.js +59 -61
- package/lib/commonjs/sksg/Container.js.map +1 -1
- package/lib/commonjs/sksg/HostConfig.js +4 -9
- package/lib/commonjs/sksg/HostConfig.js.map +1 -1
- package/lib/commonjs/sksg/Reconciler.js +1 -2
- package/lib/commonjs/sksg/Reconciler.js.map +1 -1
- package/lib/commonjs/sksg/Recorder/Recorder.d.ts +11 -0
- package/lib/commonjs/sksg/Recorder/Recorder.js +9 -0
- package/lib/commonjs/sksg/Recorder/Recorder.js.map +1 -1
- package/lib/commonjs/sksg/Recorder/commands/Drawing.js +11 -4
- package/lib/commonjs/sksg/Recorder/commands/Drawing.js.map +1 -1
- package/lib/commonjs/sksg/Recorder/commands/Shaders.js +8 -3
- package/lib/commonjs/sksg/Recorder/commands/Shaders.js.map +1 -1
- package/lib/module/dom/types/Drawings.d.ts +3 -1
- package/lib/module/dom/types/Drawings.js.map +1 -1
- package/lib/module/dom/types/Shaders.d.ts +2 -3
- package/lib/module/dom/types/Shaders.js.map +1 -1
- package/lib/module/renderer/components/image/ImageShader.d.ts +1 -1
- package/lib/module/renderer/components/image/ImageShader.js +0 -4
- package/lib/module/renderer/components/image/ImageShader.js.map +1 -1
- package/lib/module/skia/types/Canvas.d.ts +2 -2
- package/lib/module/skia/types/Canvas.js.map +1 -1
- package/lib/module/skia/types/Image/Image.d.ts +18 -0
- package/lib/module/skia/types/Image/Image.js +21 -0
- package/lib/module/skia/types/Image/Image.js.map +1 -1
- package/lib/module/skia/types/Picture/PictureRecorder.d.ts +2 -1
- package/lib/module/skia/types/Picture/PictureRecorder.js.map +1 -1
- package/lib/module/skia/web/JsiSkCanvas.d.ts +2 -2
- package/lib/module/skia/web/JsiSkCanvas.js +15 -2
- package/lib/module/skia/web/JsiSkCanvas.js.map +1 -1
- package/lib/module/sksg/Container.d.ts +17 -14
- package/lib/module/sksg/Container.js +56 -59
- package/lib/module/sksg/Container.js.map +1 -1
- package/lib/module/sksg/HostConfig.js +4 -9
- package/lib/module/sksg/HostConfig.js.map +1 -1
- package/lib/module/sksg/Reconciler.js +2 -3
- package/lib/module/sksg/Reconciler.js.map +1 -1
- package/lib/module/sksg/Recorder/Recorder.d.ts +11 -0
- package/lib/module/sksg/Recorder/Recorder.js +9 -0
- package/lib/module/sksg/Recorder/Recorder.js.map +1 -1
- package/lib/module/sksg/Recorder/commands/Drawing.js +12 -5
- package/lib/module/sksg/Recorder/commands/Drawing.js.map +1 -1
- package/lib/module/sksg/Recorder/commands/Shaders.js +9 -4
- package/lib/module/sksg/Recorder/commands/Shaders.js.map +1 -1
- package/lib/typescript/lib/commonjs/renderer/components/image/ImageShader.d.ts +1 -3
- package/lib/typescript/lib/commonjs/skia/types/Image/Image.d.ts +21 -0
- package/lib/typescript/lib/commonjs/skia/web/JsiSkCanvas.d.ts +1 -1
- package/lib/typescript/lib/commonjs/sksg/Container.d.ts +15 -10
- package/lib/typescript/lib/commonjs/sksg/HostConfig.d.ts +4 -4
- package/lib/typescript/lib/commonjs/sksg/Reconciler.d.ts +21 -2
- package/lib/typescript/lib/commonjs/sksg/Recorder/Recorder.d.ts +5 -0
- package/lib/typescript/lib/module/mock/index.d.ts +18 -3
- package/lib/typescript/lib/module/renderer/components/image/ImageShader.d.ts +1 -3
- package/lib/typescript/lib/module/skia/types/Image/Image.d.ts +21 -0
- package/lib/typescript/lib/module/skia/web/JsiSkCanvas.d.ts +1 -1
- package/lib/typescript/lib/module/sksg/Container.d.ts +15 -10
- package/lib/typescript/lib/module/sksg/HostConfig.d.ts +4 -4
- package/lib/typescript/lib/module/sksg/Reconciler.d.ts +21 -2
- package/lib/typescript/lib/module/sksg/Recorder/Recorder.d.ts +5 -0
- package/lib/typescript/src/dom/types/Drawings.d.ts +3 -1
- package/lib/typescript/src/dom/types/Shaders.d.ts +2 -3
- package/lib/typescript/src/renderer/components/image/ImageShader.d.ts +1 -1
- package/lib/typescript/src/skia/types/Canvas.d.ts +2 -2
- package/lib/typescript/src/skia/types/Image/Image.d.ts +18 -0
- package/lib/typescript/src/skia/types/Picture/PictureRecorder.d.ts +2 -1
- package/lib/typescript/src/skia/web/JsiSkCanvas.d.ts +2 -2
- package/lib/typescript/src/sksg/Container.d.ts +17 -14
- package/lib/typescript/src/sksg/Recorder/Recorder.d.ts +11 -0
- package/libs/apple/libskia.xcframework/Info.plist +35 -2
- package/libs/apple/libskia.xcframework/ios-arm64_arm64e/libskia.a +0 -0
- package/libs/apple/libskia.xcframework/ios-arm64_arm64e_x86_64-simulator/libskia.a +0 -0
- package/libs/apple/libskia.xcframework/macos-arm64_x86_64/libskia.a +0 -0
- package/libs/apple/libskia.xcframework/tvos-arm64_arm64e/libskia.a +0 -0
- package/libs/apple/libskia.xcframework/tvos-arm64_arm64e_x86_64-simulator/libskia.a +0 -0
- package/libs/apple/libskottie.xcframework/Info.plist +36 -3
- package/libs/apple/libskottie.xcframework/ios-arm64_arm64e/libskottie.a +0 -0
- package/libs/apple/libskottie.xcframework/ios-arm64_arm64e_x86_64-simulator/libskottie.a +0 -0
- package/libs/apple/libskottie.xcframework/macos-arm64_x86_64/libskottie.a +0 -0
- package/libs/apple/libskottie.xcframework/tvos-arm64_arm64e/libskottie.a +0 -0
- package/libs/apple/libskottie.xcframework/tvos-arm64_arm64e_x86_64-simulator/libskottie.a +0 -0
- package/libs/apple/libskparagraph.xcframework/Info.plist +40 -7
- package/libs/apple/libskparagraph.xcframework/ios-arm64_arm64e/libskparagraph.a +0 -0
- package/libs/apple/libskparagraph.xcframework/ios-arm64_arm64e_x86_64-simulator/libskparagraph.a +0 -0
- package/libs/apple/libskparagraph.xcframework/macos-arm64_x86_64/libskparagraph.a +0 -0
- package/libs/apple/libskparagraph.xcframework/tvos-arm64_arm64e/libskparagraph.a +0 -0
- package/libs/apple/libskparagraph.xcframework/tvos-arm64_arm64e_x86_64-simulator/libskparagraph.a +0 -0
- package/libs/apple/libsksg.xcframework/Info.plist +35 -2
- package/libs/apple/libsksg.xcframework/ios-arm64_arm64e/libsksg.a +0 -0
- package/libs/apple/libsksg.xcframework/ios-arm64_arm64e_x86_64-simulator/libsksg.a +0 -0
- package/libs/apple/libsksg.xcframework/macos-arm64_x86_64/libsksg.a +0 -0
- package/libs/apple/libsksg.xcframework/tvos-arm64_arm64e/libsksg.a +0 -0
- package/libs/apple/libsksg.xcframework/tvos-arm64_arm64e_x86_64-simulator/libsksg.a +0 -0
- package/libs/apple/libskshaper.xcframework/Info.plist +33 -0
- package/libs/apple/libskshaper.xcframework/ios-arm64_arm64e/libskshaper.a +0 -0
- package/libs/apple/libskshaper.xcframework/ios-arm64_arm64e_x86_64-simulator/libskshaper.a +0 -0
- package/libs/apple/libskshaper.xcframework/macos-arm64_x86_64/libskshaper.a +0 -0
- package/libs/apple/libskshaper.xcframework/tvos-arm64_arm64e/libskshaper.a +0 -0
- package/libs/apple/libskshaper.xcframework/tvos-arm64_arm64e_x86_64-simulator/libskshaper.a +0 -0
- package/libs/apple/libskunicode_core.xcframework/Info.plist +36 -3
- package/libs/apple/libskunicode_core.xcframework/ios-arm64_arm64e/libskunicode_core.a +0 -0
- package/libs/apple/libskunicode_core.xcframework/ios-arm64_arm64e_x86_64-simulator/libskunicode_core.a +0 -0
- package/libs/apple/libskunicode_core.xcframework/macos-arm64_x86_64/libskunicode_core.a +0 -0
- package/libs/apple/libskunicode_core.xcframework/tvos-arm64_arm64e/libskunicode_core.a +0 -0
- package/libs/apple/libskunicode_core.xcframework/tvos-arm64_arm64e_x86_64-simulator/libskunicode_core.a +0 -0
- package/libs/apple/libskunicode_libgrapheme.xcframework/Info.plist +35 -2
- package/libs/apple/libskunicode_libgrapheme.xcframework/ios-arm64_arm64e/libskunicode_libgrapheme.a +0 -0
- package/libs/apple/libskunicode_libgrapheme.xcframework/ios-arm64_arm64e_x86_64-simulator/libskunicode_libgrapheme.a +0 -0
- package/libs/apple/libskunicode_libgrapheme.xcframework/macos-arm64_x86_64/libskunicode_libgrapheme.a +0 -0
- package/libs/apple/libskunicode_libgrapheme.xcframework/tvos-arm64_arm64e/libskunicode_libgrapheme.a +0 -0
- package/libs/apple/libskunicode_libgrapheme.xcframework/tvos-arm64_arm64e_x86_64-simulator/libskunicode_libgrapheme.a +0 -0
- package/libs/apple/libsvg.xcframework/Info.plist +36 -3
- package/libs/apple/libsvg.xcframework/ios-arm64_arm64e/libsvg.a +0 -0
- package/libs/apple/libsvg.xcframework/ios-arm64_arm64e_x86_64-simulator/libsvg.a +0 -0
- package/libs/apple/libsvg.xcframework/macos-arm64_x86_64/libsvg.a +0 -0
- package/libs/apple/libsvg.xcframework/tvos-arm64_arm64e/libsvg.a +0 -0
- package/libs/apple/libsvg.xcframework/tvos-arm64_arm64e_x86_64-simulator/libsvg.a +0 -0
- package/package.json +1 -1
- package/react-native-skia.podspec +2 -2
- package/src/__tests__/snapshots/animated-images/bird.png +0 -0
- package/src/__tests__/snapshots/demos/product.png +0 -0
- package/src/__tests__/snapshots/demos/product2.png +0 -0
- package/src/__tests__/snapshots/images/bundle-android.png +0 -0
- package/src/__tests__/snapshots/images/bundle-ios.png +0 -0
- package/src/__tests__/snapshots/images/bundle-node.png +0 -0
- package/src/__tests__/snapshots/images/filter.png +0 -0
- package/src/dom/types/Drawings.ts +3 -0
- package/src/dom/types/Shaders.ts +2 -4
- package/src/renderer/__tests__/e2e/Text.spec.tsx +1 -1
- package/src/renderer/components/image/ImageShader.tsx +2 -15
- package/src/skia/types/Canvas.ts +2 -3
- package/src/skia/types/Image/Image.ts +14 -0
- package/src/skia/types/Picture/PictureRecorder.ts +2 -1
- package/src/skia/web/JsiSkCanvas.ts +50 -29
- package/src/sksg/Container.ts +64 -67
- package/src/sksg/HostConfig.ts +4 -9
- package/src/sksg/Reconciler.ts +3 -3
- package/src/sksg/Recorder/Recorder.ts +20 -0
- package/src/sksg/Recorder/commands/Drawing.ts +33 -4
- package/src/sksg/Recorder/commands/Shaders.ts +21 -8
- package/lib/commonjs/sksg/Recorder/Recording.d.ts +0 -7
- package/lib/commonjs/sksg/Recorder/Recording.js +0 -12
- package/lib/commonjs/sksg/Recorder/Recording.js.map +0 -1
- package/lib/module/sksg/Recorder/Recording.d.ts +0 -7
- package/lib/module/sksg/Recorder/Recording.js +0 -5
- package/lib/module/sksg/Recorder/Recording.js.map +0 -1
- package/lib/typescript/lib/commonjs/sksg/Recorder/Recording.d.ts +0 -5
- package/lib/typescript/lib/module/sksg/Recorder/Recording.d.ts +0 -4
- package/lib/typescript/src/sksg/Recorder/Recording.d.ts +0 -7
- package/src/sksg/Recorder/Recording.ts +0 -13
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
@@ -17,6 +17,7 @@ import type {
|
|
|
17
17
|
SkRect,
|
|
18
18
|
SkRSXform,
|
|
19
19
|
SkColor,
|
|
20
|
+
SamplingOptions,
|
|
20
21
|
} from "../../skia/types";
|
|
21
22
|
|
|
22
23
|
import type {
|
|
@@ -37,6 +38,7 @@ export type ImageProps = DrawingNodeProps &
|
|
|
37
38
|
RectDef & {
|
|
38
39
|
fit?: Fit;
|
|
39
40
|
image: SkImage | null;
|
|
41
|
+
sampling?: SamplingOptions;
|
|
40
42
|
};
|
|
41
43
|
|
|
42
44
|
export type CircleProps = CircleDef & DrawingNodeProps;
|
|
@@ -65,6 +67,7 @@ export interface AtlasProps extends DrawingNodeProps {
|
|
|
65
67
|
sprites: SkRect[];
|
|
66
68
|
transforms: SkRSXform[];
|
|
67
69
|
colors?: SkColor[];
|
|
70
|
+
sampling?: SamplingOptions;
|
|
68
71
|
}
|
|
69
72
|
|
|
70
73
|
export interface CubicBezierHandle {
|
package/src/dom/types/Shaders.ts
CHANGED
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
import type {
|
|
2
2
|
Color,
|
|
3
|
-
|
|
4
|
-
MipmapMode,
|
|
3
|
+
SamplingOptions,
|
|
5
4
|
SkImage,
|
|
6
5
|
SkRect,
|
|
7
6
|
SkRuntimeEffect,
|
|
@@ -26,11 +25,10 @@ export interface ShaderProps extends TransformProps, ChildrenProps {
|
|
|
26
25
|
export interface ImageShaderProps extends TransformProps, Partial<RectCtor> {
|
|
27
26
|
tx: SkEnum<typeof TileMode>;
|
|
28
27
|
ty: SkEnum<typeof TileMode>;
|
|
29
|
-
fm: SkEnum<typeof FilterMode>;
|
|
30
|
-
mm: SkEnum<typeof MipmapMode>;
|
|
31
28
|
fit: Fit;
|
|
32
29
|
rect?: SkRect;
|
|
33
30
|
image: SkImage | null;
|
|
31
|
+
sampling?: SamplingOptions;
|
|
34
32
|
}
|
|
35
33
|
|
|
36
34
|
export interface ColorProps {
|
|
@@ -18,7 +18,7 @@ describe("Text", () => {
|
|
|
18
18
|
},
|
|
19
19
|
{ font }
|
|
20
20
|
);
|
|
21
|
-
expect(result).toEqual([892, 896]);
|
|
21
|
+
expect(result).toEqual(surface.OS === "ios" ? [0, 0] : [892, 896]);
|
|
22
22
|
});
|
|
23
23
|
it("Should calculate chinese text width correctly", async () => {
|
|
24
24
|
const font = fonts.NotoSansSCRegular;
|
|
@@ -6,24 +6,11 @@ import type { SkiaDefaultProps } from "../../processors";
|
|
|
6
6
|
export const ImageShader = ({
|
|
7
7
|
tx = "decal",
|
|
8
8
|
ty = "decal",
|
|
9
|
-
fm = "nearest",
|
|
10
|
-
mm = "none",
|
|
11
9
|
fit = "none",
|
|
12
10
|
transform = [],
|
|
13
11
|
...props
|
|
14
|
-
}: SkiaDefaultProps<
|
|
15
|
-
ImageShaderProps,
|
|
16
|
-
"tx" | "ty" | "fm" | "mm" | "fit" | "transform"
|
|
17
|
-
>) => {
|
|
12
|
+
}: SkiaDefaultProps<ImageShaderProps, "tx" | "ty" | "fit" | "transform">) => {
|
|
18
13
|
return (
|
|
19
|
-
<skImageShader
|
|
20
|
-
tx={tx}
|
|
21
|
-
ty={ty}
|
|
22
|
-
fm={fm}
|
|
23
|
-
mm={mm}
|
|
24
|
-
fit={fit}
|
|
25
|
-
transform={transform}
|
|
26
|
-
{...props}
|
|
27
|
-
/>
|
|
14
|
+
<skImageShader tx={tx} ty={ty} fit={fit} transform={transform} {...props} />
|
|
28
15
|
);
|
|
29
16
|
};
|
package/src/skia/types/Canvas.ts
CHANGED
|
@@ -7,8 +7,7 @@ import type {
|
|
|
7
7
|
MipmapMode,
|
|
8
8
|
FilterMode,
|
|
9
9
|
ImageInfo,
|
|
10
|
-
|
|
11
|
-
FilterOptions,
|
|
10
|
+
SamplingOptions,
|
|
12
11
|
} from "./Image";
|
|
13
12
|
import type { SkSVG } from "./SVG";
|
|
14
13
|
import type { SkColor } from "./Color";
|
|
@@ -521,7 +520,7 @@ export interface SkCanvas {
|
|
|
521
520
|
paint: SkPaint,
|
|
522
521
|
blendMode?: BlendMode,
|
|
523
522
|
colors?: SkColor[],
|
|
524
|
-
sampling?:
|
|
523
|
+
sampling?: SamplingOptions
|
|
525
524
|
): void;
|
|
526
525
|
|
|
527
526
|
/** Read Image pixels
|
|
@@ -32,6 +32,20 @@ export enum ImageFormat {
|
|
|
32
32
|
WEBP = 6,
|
|
33
33
|
}
|
|
34
34
|
|
|
35
|
+
export type SamplingOptions = CubicResampler | FilterOptions;
|
|
36
|
+
|
|
37
|
+
export const isCubicSampling = (
|
|
38
|
+
sampling: SamplingOptions
|
|
39
|
+
): sampling is CubicResampler => {
|
|
40
|
+
"worklet";
|
|
41
|
+
return "B" in sampling && "C" in sampling;
|
|
42
|
+
};
|
|
43
|
+
|
|
44
|
+
export const MitchellCubicSampling = { B: 1 / 3.0, C: 1 / 3.0 };
|
|
45
|
+
export const CatmullRomCubicSampling = { B: 0, C: 1 / 2.0 };
|
|
46
|
+
export const CubicSampling = { B: 0, C: 0 };
|
|
47
|
+
export const MakeCubic = (B: number, C: number) => ({ B, C });
|
|
48
|
+
|
|
35
49
|
export interface SkImage extends SkJSIInstance<"Image"> {
|
|
36
50
|
/**
|
|
37
51
|
* Returns the possibly scaled height of the image.
|
|
@@ -1,9 +1,10 @@
|
|
|
1
1
|
import type { SkCanvas } from "../Canvas";
|
|
2
|
+
import type { SkJSIInstance } from "../JsiInstance";
|
|
2
3
|
import type { SkRect } from "../Rect";
|
|
3
4
|
|
|
4
5
|
import type { SkPicture } from "./Picture";
|
|
5
6
|
|
|
6
|
-
export interface SkPictureRecorder {
|
|
7
|
+
export interface SkPictureRecorder extends SkJSIInstance<"PictureRecorder"> {
|
|
7
8
|
/**
|
|
8
9
|
* Returns a canvas on which to draw. When done drawing, call finishRecordingAsPicture()
|
|
9
10
|
*
|
|
@@ -1,31 +1,37 @@
|
|
|
1
|
-
import type { Canvas, CanvasKit } from "canvaskit-wasm";
|
|
2
|
-
|
|
3
1
|
import type {
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
2
|
+
Canvas,
|
|
3
|
+
CanvasKit,
|
|
4
|
+
CubicResampler as CKCubicResampler,
|
|
5
|
+
FilterOptions as CKFilterOptions,
|
|
6
|
+
} from "canvaskit-wasm";
|
|
7
|
+
|
|
8
|
+
import {
|
|
9
|
+
type BlendMode,
|
|
10
|
+
type ClipOp,
|
|
11
|
+
type FilterMode,
|
|
12
|
+
type MipmapMode,
|
|
13
|
+
type PointMode,
|
|
14
|
+
type SaveLayerFlag,
|
|
15
|
+
type ImageInfo,
|
|
16
|
+
type SkCanvas,
|
|
17
|
+
type SkColor,
|
|
18
|
+
type SkFont,
|
|
19
|
+
type SkImage,
|
|
20
|
+
type SkImageFilter,
|
|
21
|
+
type SkMatrix,
|
|
22
|
+
type SkPaint,
|
|
23
|
+
type SkPath,
|
|
24
|
+
type SkPicture,
|
|
25
|
+
type SkPoint,
|
|
26
|
+
type SkRect,
|
|
27
|
+
type InputRRect,
|
|
28
|
+
type SkSVG,
|
|
29
|
+
type SkTextBlob,
|
|
30
|
+
type SkVertices,
|
|
31
|
+
type SkRSXform,
|
|
32
|
+
type CubicResampler,
|
|
33
|
+
type FilterOptions,
|
|
34
|
+
isCubicSampling,
|
|
29
35
|
} from "../types";
|
|
30
36
|
|
|
31
37
|
import { getEnum, HostObject } from "./Host";
|
|
@@ -398,7 +404,7 @@ export class JsiSkCanvas
|
|
|
398
404
|
paint: SkPaint,
|
|
399
405
|
blendMode?: BlendMode,
|
|
400
406
|
colors?: SkColor[],
|
|
401
|
-
|
|
407
|
+
sampling?: CubicResampler | FilterOptions
|
|
402
408
|
) {
|
|
403
409
|
const src = srcs.flatMap((s) =>
|
|
404
410
|
Array.from(JsiSkRect.fromValue(this.CanvasKit, s))
|
|
@@ -412,6 +418,20 @@ export class JsiSkCanvas
|
|
|
412
418
|
cls[i] = this.CanvasKit.ColorAsInt(r * 255, g * 255, b * 255, a * 255);
|
|
413
419
|
}
|
|
414
420
|
}
|
|
421
|
+
let ckSampling: CKCubicResampler | CKFilterOptions = {
|
|
422
|
+
filter: this.CanvasKit.FilterMode.Linear,
|
|
423
|
+
mipmap: this.CanvasKit.MipmapMode.None,
|
|
424
|
+
};
|
|
425
|
+
if (sampling && isCubicSampling(sampling)) {
|
|
426
|
+
ckSampling = sampling;
|
|
427
|
+
} else if (sampling) {
|
|
428
|
+
ckSampling = {
|
|
429
|
+
filter: getEnum(this.CanvasKit.FilterMode, sampling.filter),
|
|
430
|
+
mipmap: sampling.mipmap
|
|
431
|
+
? getEnum(this.CanvasKit.MipmapMode, sampling.mipmap)
|
|
432
|
+
: this.CanvasKit.MipmapMode.None,
|
|
433
|
+
};
|
|
434
|
+
}
|
|
415
435
|
this.ref.drawAtlas(
|
|
416
436
|
JsiSkImage.fromValue(atlas),
|
|
417
437
|
src,
|
|
@@ -420,7 +440,8 @@ export class JsiSkCanvas
|
|
|
420
440
|
blendMode
|
|
421
441
|
? getEnum(this.CanvasKit.BlendMode, blendMode)
|
|
422
442
|
: this.CanvasKit.BlendMode.DstOver,
|
|
423
|
-
cls
|
|
443
|
+
cls,
|
|
444
|
+
ckSampling
|
|
424
445
|
);
|
|
425
446
|
}
|
|
426
447
|
|
package/src/sksg/Container.ts
CHANGED
|
@@ -1,23 +1,21 @@
|
|
|
1
|
-
import { type SharedValue } from "react-native-reanimated";
|
|
2
|
-
|
|
3
1
|
import Rea from "../external/reanimated/ReanimatedProxy";
|
|
4
2
|
import type { Skia, SkCanvas } from "../skia/types";
|
|
3
|
+
import { HAS_REANIMATED_3 } from "../external/reanimated/renderHelpers";
|
|
5
4
|
|
|
6
5
|
import type { Node } from "./Node";
|
|
7
|
-
import {
|
|
6
|
+
import type { Recording } from "./Recorder/Recorder";
|
|
8
7
|
import { Recorder } from "./Recorder/Recorder";
|
|
9
8
|
import { visit } from "./Recorder/Visitor";
|
|
10
9
|
import { replay } from "./Recorder/Player";
|
|
11
10
|
import { createDrawingContext } from "./Recorder/DrawingContext";
|
|
12
|
-
import { createRecording, type Recording } from "./Recorder/Recording";
|
|
13
11
|
|
|
14
12
|
const drawOnscreen = (Skia: Skia, nativeId: number, recording: Recording) => {
|
|
15
13
|
"worklet";
|
|
14
|
+
|
|
16
15
|
const rec = Skia.PictureRecorder();
|
|
17
16
|
const canvas = rec.beginRecording();
|
|
18
17
|
// const start = performance.now();
|
|
19
18
|
|
|
20
|
-
// TODO: because the pool is not a shared value here, it is copied on every frame
|
|
21
19
|
const ctx = createDrawingContext(Skia, recording.paintPool, canvas);
|
|
22
20
|
//console.log(recording.commands);
|
|
23
21
|
replay(ctx, recording.commands);
|
|
@@ -25,84 +23,83 @@ const drawOnscreen = (Skia: Skia, nativeId: number, recording: Recording) => {
|
|
|
25
23
|
//const end = performance.now();
|
|
26
24
|
//console.log("Recording time: ", end - start);
|
|
27
25
|
SkiaViewApi.setJsiProperty(nativeId, "picture", picture);
|
|
26
|
+
rec.dispose();
|
|
27
|
+
picture.dispose();
|
|
28
28
|
};
|
|
29
29
|
|
|
30
|
-
export class Container {
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
public unmounted = false;
|
|
34
|
-
|
|
35
|
-
private values = new Set<SharedValue<unknown>>();
|
|
36
|
-
private mapperId: number | null = null;
|
|
37
|
-
|
|
38
|
-
constructor(public Skia: Skia, private nativeId: number) {}
|
|
30
|
+
export abstract class Container {
|
|
31
|
+
public root: Node[] = [];
|
|
32
|
+
protected recording: Recording | null = null;
|
|
39
33
|
|
|
40
|
-
|
|
41
|
-
return this._root;
|
|
42
|
-
}
|
|
34
|
+
constructor(protected Skia: Skia, protected nativeId: number) {}
|
|
43
35
|
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
if (this.mapperId !== null) {
|
|
48
|
-
Rea.stopMapper(this.mapperId);
|
|
49
|
-
}
|
|
50
|
-
const { nativeId, Skia, _recording } = this;
|
|
51
|
-
this.mapperId = Rea.startMapper(() => {
|
|
52
|
-
"worklet";
|
|
53
|
-
drawOnscreen(Skia, nativeId, _recording!);
|
|
54
|
-
}, Array.from(this.values));
|
|
36
|
+
drawOnCanvas(canvas: SkCanvas) {
|
|
37
|
+
if (!this.recording) {
|
|
38
|
+
throw new Error("No recording to draw");
|
|
55
39
|
}
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
40
|
+
const ctx = createDrawingContext(
|
|
41
|
+
this.Skia,
|
|
42
|
+
this.recording.paintPool,
|
|
43
|
+
canvas
|
|
44
|
+
);
|
|
45
|
+
//console.log(this._recording);
|
|
46
|
+
replay(ctx, this.recording.commands);
|
|
60
47
|
}
|
|
61
48
|
|
|
62
|
-
|
|
63
|
-
|
|
49
|
+
abstract redraw(): void;
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
class StaticContainer extends Container {
|
|
53
|
+
constructor(Skia: Skia, nativeId: number) {
|
|
54
|
+
super(Skia, nativeId);
|
|
64
55
|
}
|
|
65
56
|
|
|
66
57
|
redraw() {
|
|
67
|
-
const
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
58
|
+
const recorder = new Recorder();
|
|
59
|
+
visit(recorder, this.root);
|
|
60
|
+
this.recording = recorder.getRecording();
|
|
61
|
+
const isOnScreen = this.nativeId !== -1;
|
|
62
|
+
if (isOnScreen) {
|
|
63
|
+
const rec = this.Skia.PictureRecorder();
|
|
64
|
+
const canvas = rec.beginRecording();
|
|
65
|
+
this.drawOnCanvas(canvas);
|
|
66
|
+
const picture = rec.finishRecordingAsPicture();
|
|
67
|
+
SkiaViewApi.setJsiProperty(this.nativeId, "picture", picture);
|
|
73
68
|
}
|
|
74
69
|
}
|
|
70
|
+
}
|
|
75
71
|
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
}
|
|
79
|
-
|
|
80
|
-
unregisterValues(values: object) {
|
|
81
|
-
Object.values(values)
|
|
82
|
-
.filter(isSharedValue)
|
|
83
|
-
.forEach((value) => {
|
|
84
|
-
this.values.delete(value);
|
|
85
|
-
});
|
|
86
|
-
}
|
|
72
|
+
class ReanimatedContainer extends Container {
|
|
73
|
+
private mapperId: number | null = null;
|
|
87
74
|
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
.filter(isSharedValue)
|
|
91
|
-
.forEach((value) => {
|
|
92
|
-
this.values.add(value);
|
|
93
|
-
});
|
|
75
|
+
constructor(Skia: Skia, nativeId: number) {
|
|
76
|
+
super(Skia, nativeId);
|
|
94
77
|
}
|
|
95
78
|
|
|
96
|
-
|
|
97
|
-
if (
|
|
98
|
-
|
|
79
|
+
redraw() {
|
|
80
|
+
if (this.mapperId !== null) {
|
|
81
|
+
Rea.stopMapper(this.mapperId);
|
|
82
|
+
}
|
|
83
|
+
const recorder = new Recorder();
|
|
84
|
+
visit(recorder, this.root);
|
|
85
|
+
const record = recorder.getRecording();
|
|
86
|
+
const { animationValues } = record;
|
|
87
|
+
this.recording = {
|
|
88
|
+
commands: record.commands,
|
|
89
|
+
paintPool: record.paintPool,
|
|
90
|
+
};
|
|
91
|
+
if (animationValues.size > 0) {
|
|
92
|
+
const { nativeId, Skia, recording } = this;
|
|
93
|
+
this.mapperId = Rea.startMapper(() => {
|
|
94
|
+
"worklet";
|
|
95
|
+
drawOnscreen(Skia, nativeId, recording!);
|
|
96
|
+
}, Array.from(animationValues));
|
|
99
97
|
}
|
|
100
|
-
const ctx = createDrawingContext(
|
|
101
|
-
this.Skia,
|
|
102
|
-
this._recording.paintPool,
|
|
103
|
-
canvas
|
|
104
|
-
);
|
|
105
|
-
//console.log(this._recording);
|
|
106
|
-
replay(ctx, this._recording.commands);
|
|
107
98
|
}
|
|
108
99
|
}
|
|
100
|
+
|
|
101
|
+
export const createContainer = (Skia: Skia, nativeId: number) => {
|
|
102
|
+
return HAS_REANIMATED_3 && nativeId !== -1
|
|
103
|
+
? new ReanimatedContainer(Skia, nativeId)
|
|
104
|
+
: new StaticContainer(Skia, nativeId);
|
|
105
|
+
};
|
package/src/sksg/HostConfig.ts
CHANGED
|
@@ -85,14 +85,13 @@ export const sksgHostConfig: SkiaHostConfig = {
|
|
|
85
85
|
createInstance(
|
|
86
86
|
type,
|
|
87
87
|
propsWithChildren,
|
|
88
|
-
|
|
88
|
+
_container,
|
|
89
89
|
_hostContext,
|
|
90
90
|
_internalInstanceHandle
|
|
91
91
|
) {
|
|
92
92
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
93
93
|
const { children, ...props } = propsWithChildren as any;
|
|
94
94
|
debug("createInstance", type);
|
|
95
|
-
container.registerValues(props);
|
|
96
95
|
const instance = {
|
|
97
96
|
type,
|
|
98
97
|
props,
|
|
@@ -121,7 +120,7 @@ export const sksgHostConfig: SkiaHostConfig = {
|
|
|
121
120
|
debug("commitMount");
|
|
122
121
|
},
|
|
123
122
|
|
|
124
|
-
prepareForCommit(
|
|
123
|
+
prepareForCommit(_container: Container) {
|
|
125
124
|
debug("prepareForCommit");
|
|
126
125
|
return null;
|
|
127
126
|
},
|
|
@@ -144,9 +143,8 @@ export const sksgHostConfig: SkiaHostConfig = {
|
|
|
144
143
|
// textInstance.instance = newText;
|
|
145
144
|
},
|
|
146
145
|
|
|
147
|
-
clearContainer: (
|
|
146
|
+
clearContainer: (_container) => {
|
|
148
147
|
debug("clearContainer");
|
|
149
|
-
container.clear();
|
|
150
148
|
},
|
|
151
149
|
|
|
152
150
|
prepareUpdate(
|
|
@@ -162,8 +160,6 @@ export const sksgHostConfig: SkiaHostConfig = {
|
|
|
162
160
|
if (propsAreEqual) {
|
|
163
161
|
return null;
|
|
164
162
|
}
|
|
165
|
-
container.unregisterValues(oldProps);
|
|
166
|
-
container.registerValues(newProps);
|
|
167
163
|
return container;
|
|
168
164
|
},
|
|
169
165
|
|
|
@@ -208,7 +204,6 @@ export const sksgHostConfig: SkiaHostConfig = {
|
|
|
208
204
|
},
|
|
209
205
|
|
|
210
206
|
replaceContainerChildren(container: Container, newChildren: ChildSet) {
|
|
211
|
-
debug("replaceContainerChildren");
|
|
212
207
|
container.root = newChildren;
|
|
213
208
|
},
|
|
214
209
|
|
|
@@ -229,7 +224,7 @@ export const sksgHostConfig: SkiaHostConfig = {
|
|
|
229
224
|
getCurrentEventPriority: () => DefaultEventPriority,
|
|
230
225
|
beforeActiveInstanceBlur: () => {},
|
|
231
226
|
afterActiveInstanceBlur: () => {},
|
|
232
|
-
detachDeletedInstance: () => {},
|
|
227
|
+
detachDeletedInstance: (_node: Instance) => {},
|
|
233
228
|
getInstanceFromNode: function (_node): Fiber | null | undefined {
|
|
234
229
|
throw new Error("Function not implemented.");
|
|
235
230
|
},
|
package/src/sksg/Reconciler.ts
CHANGED
|
@@ -6,7 +6,8 @@ import type { SkCanvas, Skia } from "../skia/types";
|
|
|
6
6
|
import { NodeType } from "../dom/types";
|
|
7
7
|
|
|
8
8
|
import { debug, sksgHostConfig } from "./HostConfig";
|
|
9
|
-
import { Container } from "./Container";
|
|
9
|
+
import type { Container } from "./Container";
|
|
10
|
+
import { createContainer } from "./Container";
|
|
10
11
|
|
|
11
12
|
const skiaReconciler = ReactReconciler(sksgHostConfig);
|
|
12
13
|
|
|
@@ -21,7 +22,7 @@ export class SkiaSGRoot {
|
|
|
21
22
|
private container: Container;
|
|
22
23
|
|
|
23
24
|
constructor(public Skia: Skia, nativeId = -1) {
|
|
24
|
-
this.container =
|
|
25
|
+
this.container = createContainer(Skia, nativeId);
|
|
25
26
|
this.root = skiaReconciler.createContainer(
|
|
26
27
|
this.container,
|
|
27
28
|
0,
|
|
@@ -58,7 +59,6 @@ export class SkiaSGRoot {
|
|
|
58
59
|
}
|
|
59
60
|
|
|
60
61
|
unmount() {
|
|
61
|
-
this.container.unmounted = true;
|
|
62
62
|
skiaReconciler.updateContainer(null, this.root, null, () => {
|
|
63
63
|
debug("unmountContainer");
|
|
64
64
|
});
|
|
@@ -30,12 +30,31 @@ import type {
|
|
|
30
30
|
import type { AnimatedProps } from "../../renderer";
|
|
31
31
|
import { isSharedValue } from "../utils";
|
|
32
32
|
import { isColorFilter, isImageFilter, isPathEffect, isShader } from "../Node";
|
|
33
|
+
import type { SkPaint } from "../../skia/types";
|
|
33
34
|
|
|
34
35
|
import { CommandType } from "./Core";
|
|
35
36
|
import type { Command } from "./Core";
|
|
36
37
|
|
|
38
|
+
export interface Recording {
|
|
39
|
+
commands: Command[];
|
|
40
|
+
paintPool: SkPaint[];
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
interface AnimationValues {
|
|
44
|
+
animationValues: Set<SharedValue<unknown>>;
|
|
45
|
+
}
|
|
46
|
+
|
|
37
47
|
export class Recorder {
|
|
38
48
|
commands: Command[] = [];
|
|
49
|
+
animationValues: Set<SharedValue<unknown>> = new Set();
|
|
50
|
+
|
|
51
|
+
getRecording(): Recording & AnimationValues {
|
|
52
|
+
return {
|
|
53
|
+
commands: this.commands,
|
|
54
|
+
paintPool: [],
|
|
55
|
+
animationValues: this.animationValues,
|
|
56
|
+
};
|
|
57
|
+
}
|
|
39
58
|
|
|
40
59
|
private processProps(props: Record<string, unknown>) {
|
|
41
60
|
const animatedProps: Record<string, SharedValue<unknown>> = {};
|
|
@@ -44,6 +63,7 @@ export class Recorder {
|
|
|
44
63
|
for (const key in props) {
|
|
45
64
|
const prop = props[key];
|
|
46
65
|
if (isSharedValue(prop)) {
|
|
66
|
+
this.animationValues.add(prop);
|
|
47
67
|
props[key] = prop.value;
|
|
48
68
|
animatedProps[key] = prop;
|
|
49
69
|
hasAnimatedProps = true;
|
|
@@ -40,7 +40,10 @@ import {
|
|
|
40
40
|
BlurStyle,
|
|
41
41
|
ClipOp,
|
|
42
42
|
FillType,
|
|
43
|
+
FilterMode,
|
|
44
|
+
isCubicSampling,
|
|
43
45
|
isRRect,
|
|
46
|
+
MipmapMode,
|
|
44
47
|
PointMode,
|
|
45
48
|
VertexMode,
|
|
46
49
|
} from "../../../skia/types";
|
|
@@ -117,7 +120,7 @@ export const drawBox = (
|
|
|
117
120
|
|
|
118
121
|
export const drawImage = (ctx: DrawingContext, props: ImageProps) => {
|
|
119
122
|
"worklet";
|
|
120
|
-
const { image } = props;
|
|
123
|
+
const { image, sampling } = props;
|
|
121
124
|
if (image) {
|
|
122
125
|
const fit = props.fit ?? "contain";
|
|
123
126
|
const rect = processRect(ctx.Skia, props);
|
|
@@ -131,7 +134,25 @@ export const drawImage = (ctx: DrawingContext, props: ImageProps) => {
|
|
|
131
134
|
},
|
|
132
135
|
rect
|
|
133
136
|
);
|
|
134
|
-
|
|
137
|
+
if (sampling && isCubicSampling(sampling)) {
|
|
138
|
+
ctx.canvas.drawImageRectCubic(
|
|
139
|
+
image,
|
|
140
|
+
src,
|
|
141
|
+
dst,
|
|
142
|
+
sampling.B,
|
|
143
|
+
sampling.C,
|
|
144
|
+
ctx.paint
|
|
145
|
+
);
|
|
146
|
+
} else {
|
|
147
|
+
ctx.canvas.drawImageRectOptions(
|
|
148
|
+
image,
|
|
149
|
+
src,
|
|
150
|
+
dst,
|
|
151
|
+
sampling?.filter ?? FilterMode.Linear,
|
|
152
|
+
sampling?.mipmap ?? MipmapMode.None,
|
|
153
|
+
ctx.paint
|
|
154
|
+
);
|
|
155
|
+
}
|
|
135
156
|
}
|
|
136
157
|
};
|
|
137
158
|
|
|
@@ -349,10 +370,18 @@ export const drawPicture = (ctx: DrawingContext, props: PictureProps) => {
|
|
|
349
370
|
|
|
350
371
|
export const drawAtlas = (ctx: DrawingContext, props: AtlasProps) => {
|
|
351
372
|
"worklet";
|
|
352
|
-
const { image, sprites, transforms, colors, blendMode } = props;
|
|
373
|
+
const { image, sprites, transforms, colors, blendMode, sampling } = props;
|
|
353
374
|
const blend = blendMode ? BlendMode[enumKey(blendMode)] : undefined;
|
|
354
375
|
if (image) {
|
|
355
|
-
ctx.canvas.drawAtlas(
|
|
376
|
+
ctx.canvas.drawAtlas(
|
|
377
|
+
image,
|
|
378
|
+
sprites,
|
|
379
|
+
transforms,
|
|
380
|
+
ctx.paint,
|
|
381
|
+
blend,
|
|
382
|
+
colors,
|
|
383
|
+
sampling
|
|
384
|
+
);
|
|
356
385
|
}
|
|
357
386
|
};
|
|
358
387
|
|
|
@@ -19,9 +19,11 @@ import type {
|
|
|
19
19
|
TurbulenceProps,
|
|
20
20
|
TwoPointConicalGradientProps,
|
|
21
21
|
} from "../../../dom/types";
|
|
22
|
+
import type { SkShader } from "../../../skia/types";
|
|
22
23
|
import {
|
|
23
24
|
BlendMode,
|
|
24
25
|
FilterMode,
|
|
26
|
+
isCubicSampling,
|
|
25
27
|
MipmapMode,
|
|
26
28
|
processUniforms,
|
|
27
29
|
TileMode,
|
|
@@ -179,7 +181,7 @@ const declareTurbulenceShader = (
|
|
|
179
181
|
|
|
180
182
|
const declareImageShader = (ctx: DrawingContext, props: ImageShaderProps) => {
|
|
181
183
|
"worklet";
|
|
182
|
-
const { fit, image, tx, ty,
|
|
184
|
+
const { fit, image, tx, ty, sampling, ...imageShaderProps } = props;
|
|
183
185
|
if (!image) {
|
|
184
186
|
return;
|
|
185
187
|
}
|
|
@@ -199,13 +201,24 @@ const declareImageShader = (ctx: DrawingContext, props: ImageShaderProps) => {
|
|
|
199
201
|
const lm = ctx.Skia.Matrix();
|
|
200
202
|
lm.concat(m3);
|
|
201
203
|
processTransformProps(lm, imageShaderProps);
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
204
|
+
let shader: SkShader;
|
|
205
|
+
if (sampling && isCubicSampling(sampling)) {
|
|
206
|
+
shader = image.makeShaderCubic(
|
|
207
|
+
TileMode[enumKey(tx)],
|
|
208
|
+
TileMode[enumKey(ty)],
|
|
209
|
+
sampling.B,
|
|
210
|
+
sampling.C,
|
|
211
|
+
lm
|
|
212
|
+
);
|
|
213
|
+
} else {
|
|
214
|
+
shader = image.makeShaderCubic(
|
|
215
|
+
TileMode[enumKey(tx)],
|
|
216
|
+
TileMode[enumKey(ty)],
|
|
217
|
+
sampling?.filter ?? FilterMode.Linear,
|
|
218
|
+
sampling?.mipmap ?? MipmapMode.None,
|
|
219
|
+
lm
|
|
220
|
+
);
|
|
221
|
+
}
|
|
209
222
|
ctx.shaders.push(shader);
|
|
210
223
|
};
|
|
211
224
|
|