Skip to content

Commit

Permalink
chore(🖼️): minor refactoring in platform context (#2795)
Browse files Browse the repository at this point in the history
  • Loading branch information
wcandillon authored Dec 7, 2024
1 parent cc15a30 commit 52f2e44
Show file tree
Hide file tree
Showing 8 changed files with 113 additions and 74 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,6 @@
#include "MainThreadDispatcher.h"
#include "RNSkAndroidVideo.h"
#include "RNSkPlatformContext.h"

#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Wdocumentation"

Expand Down Expand Up @@ -78,26 +77,15 @@ class RNSkAndroidPlatformContext : public RNSkPlatformContext {
#endif
}

sk_sp<SkImage> makeImageFromNativeTexture(jsi::Runtime &runtime,
jsi::Value jsiTextureInfo,
sk_sp<SkImage> makeImageFromNativeTexture(const TextureInfo &texInfo,
int width, int height,
bool mipMapped) override {
if (!jsiTextureInfo.isObject()) {
throw new std::runtime_error("Invalid textureInfo");
}
auto jsiTextureInfoObj = jsiTextureInfo.asObject(runtime);

GrGLTextureInfo textureInfo;
textureInfo.fTarget =
(GrGLenum)jsiTextureInfoObj.getProperty(runtime, "fTarget").asNumber();
textureInfo.fID =
(GrGLuint)jsiTextureInfoObj.getProperty(runtime, "fID").asNumber();
textureInfo.fFormat =
(GrGLenum)jsiTextureInfoObj.getProperty(runtime, "fFormat").asNumber();
textureInfo.fTarget = (GrGLenum)texInfo.glTarget;
textureInfo.fID = (GrGLuint)texInfo.glID;
textureInfo.fFormat = (GrGLenum)texInfo.glFormat;
textureInfo.fProtected =
jsiTextureInfoObj.getProperty(runtime, "fProtected").asBool()
? skgpu::Protected::kYes
: skgpu::Protected::kNo;
texInfo.glProtected ? skgpu::Protected::kYes : skgpu::Protected::kNo;

OpenGLContext::getInstance().makeCurrent();
if (glIsTexture(textureInfo.fID) == GL_FALSE) {
Expand Down Expand Up @@ -185,42 +173,38 @@ class RNSkAndroidPlatformContext : public RNSkPlatformContext {
#endif
}

jsi::Value getTexture(jsi::Runtime &runtime, sk_sp<SkImage> image) override {
const TextureInfo getTexture(sk_sp<SkImage> image) override {
GrBackendTexture texture;
if (!SkImages::GetBackendTextureFromImage(image, &texture, true)) {
return jsi::Value::null();
throw std::runtime_error("Couldn't get backend texture from image.");
}
return getJSITextureInfo(runtime, texture);
return getJSITextureInfo(texture);
}

jsi::Value getTexture(jsi::Runtime &runtime,
sk_sp<SkSurface> surface) override {
const TextureInfo getTexture(sk_sp<SkSurface> surface) override {
GrBackendTexture texture = SkSurfaces::GetBackendTexture(
surface.get(), SkSurface::BackendHandleAccess::kFlushRead);
return getJSITextureInfo(runtime, texture);
return getJSITextureInfo(texture);
}

static jsi::Value getJSITextureInfo(jsi::Runtime &runtime,
const GrBackendTexture &texture) {
static const TextureInfo getJSITextureInfo(const GrBackendTexture &texture) {
if (!texture.isValid()) {
return jsi::Value::null();
throw std::runtime_error("invalid backend texture");
}
GrGLTextureInfo textureInfo;
if (!GrBackendTextures::GetGLTextureInfo(texture, &textureInfo)) {
return jsi::Value::null();
throw std::runtime_error("couldn't get OpenGL texture");
}

OpenGLContext::getInstance().makeCurrent();
glFlush();

jsi::Object jsiTextureInfo = jsi::Object(runtime);
jsiTextureInfo.setProperty(runtime, "fTarget", (int)textureInfo.fTarget);
jsiTextureInfo.setProperty(runtime, "fFormat", (int)textureInfo.fFormat);
jsiTextureInfo.setProperty(runtime, "fID", (int)textureInfo.fID);
jsiTextureInfo.setProperty(runtime, "fProtected",
(bool)textureInfo.fProtected);

return jsiTextureInfo;
TextureInfo texInfo;
texInfo.glProtected = textureInfo.isProtected();
texInfo.glID = textureInfo.fID;
texInfo.glFormat = textureInfo.fFormat;
texInfo.glTarget = textureInfo.fTarget;
return texInfo;
}

#if !defined(SK_GRAPHITE)
Expand Down
4 changes: 3 additions & 1 deletion packages/skia/cpp/api/JsiSkImage.h
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
#include "JsiSkShader.h"
#include "third_party/base64.h"

#include "JsiTextureInfo.h"
#include "RNSkTypedArray.h"

#if defined(SK_GRAPHITE)
Expand Down Expand Up @@ -220,7 +221,8 @@ class JsiSkImage : public JsiSkWrappingSkPtrHostObject<SkImage> {
if (!image->isTextureBacked()) {
return jsi::Value::null();
}
return getContext()->getTexture(runtime, image);
auto texInfo = getContext()->getTexture(image);
return JsiTextureInfo::toValue(runtime, texInfo);
}

EXPORT_JSI_API_TYPENAME(JsiSkImage, Image)
Expand Down
5 changes: 3 additions & 2 deletions packages/skia/cpp/api/JsiSkImageFactory.h
Original file line number Diff line number Diff line change
Expand Up @@ -79,9 +79,10 @@ class JsiSkImageFactory : public JsiSkHostObject {
}

JSI_HOST_FUNCTION(MakeImageFromNativeTextureUnstable) {
auto texInfo = JsiTextureInfo::fromValue(runtime, arguments[0]);
auto image = getContext()->makeImageFromNativeTexture(
runtime, jsi::Value(runtime, arguments[0]), arguments[1].asNumber(),
arguments[2].asNumber(), count > 3 && arguments[3].asBool());
texInfo, arguments[1].asNumber(), arguments[2].asNumber(),
count > 3 && arguments[3].asBool());
if (image == nullptr) {
throw std::runtime_error("Failed to convert native texture to SkImage!");
}
Expand Down
4 changes: 3 additions & 1 deletion packages/skia/cpp/api/JsiSkSurface.h
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
#include <jsi/jsi.h>

#include "JsiSkHostObjects.h"
#include "JsiTextureInfo.h"

#include "JsiSkCanvas.h"
#include "JsiSkImage.h"
Expand Down Expand Up @@ -79,7 +80,8 @@ class JsiSkSurface : public JsiSkWrappingSkPtrHostObject<SkSurface> {
}

JSI_HOST_FUNCTION(getNativeTextureUnstable) {
return getContext()->getTexture(runtime, getObject());
auto texInfo = getContext()->getTexture(getObject());
return JsiTextureInfo::toValue(runtime, texInfo);
}

JSI_EXPORT_FUNCTIONS(JSI_EXPORT_FUNC(JsiSkSurface, width),
Expand Down
53 changes: 53 additions & 0 deletions packages/skia/cpp/api/JsiTextureInfo.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
#pragma once

#include <jsi/jsi.h>

#include "RNSkPlatformContext.h"

namespace jsi = facebook::jsi;
namespace react = facebook::react;

namespace RNSkia {

namespace JsiTextureInfo {

inline jsi::Value toValue(jsi::Runtime &runtime, const TextureInfo &texInfo) {
jsi::Object textureInfo(runtime);
textureInfo.setProperty(
runtime, "mtlTexture",
jsi::BigInt::fromUint64(runtime,
reinterpret_cast<uint64_t>(texInfo.mtlTexture)));
textureInfo.setProperty(runtime, "glTarget",
static_cast<int>(texInfo.glTarget));
textureInfo.setProperty(runtime, "glID", static_cast<int>(texInfo.glID));
textureInfo.setProperty(runtime, "glFormat",
static_cast<int>(texInfo.glFormat));
textureInfo.setProperty(runtime, "glProtected",
static_cast<int>(texInfo.glProtected));
return textureInfo;
}

inline TextureInfo fromValue(jsi::Runtime &runtime, const jsi::Value &value) {
auto object = value.getObject(runtime);
TextureInfo texInfo;
if (object.hasProperty(runtime, "mtlTexture")) {
texInfo.mtlTexture =
reinterpret_cast<const void *>(object.getProperty(runtime, "mtlTexture")
.asBigInt(runtime)
.asUint64(runtime));
}
if (object.hasProperty(runtime, "glID")) {
texInfo.glTarget = static_cast<unsigned int>(
object.getProperty(runtime, "glTarget").asNumber());
texInfo.glID = static_cast<unsigned int>(
object.getProperty(runtime, "glID").asNumber());
texInfo.glFormat = static_cast<unsigned int>(
object.getProperty(runtime, "glFormat").asNumber());
texInfo.glProtected =
object.getProperty(runtime, "glProtected").asNumber() != 0;
}
return texInfo;
}

} // namespace JsiTextureInfo
} // namespace RNSkia
23 changes: 13 additions & 10 deletions packages/skia/cpp/rnskia/RNSkPlatformContext.h
Original file line number Diff line number Diff line change
Expand Up @@ -23,15 +23,21 @@

#pragma clang diagnostic pop

#include <jsi/jsi.h>

#include <ReactCommon/CallInvoker.h>

namespace RNSkia {

namespace jsi = facebook::jsi;
namespace react = facebook::react;

struct TextureInfo {
const void *mtlTexture = nullptr;
unsigned int glTarget = 0;
unsigned int glID = 0;
unsigned int glFormat = 0;
bool glProtected = false;
};

class RNSkPlatformContext {
public:
/**
Expand Down Expand Up @@ -100,10 +106,9 @@ class RNSkPlatformContext {
*/
virtual sk_sp<SkImage> makeImageFromNativeBuffer(void *buffer) = 0;

virtual sk_sp<SkImage> makeImageFromNativeTexture(jsi::Runtime &runtime,
jsi::Value textureInfo,
int width, int height,
bool mipMapped) = 0;
virtual sk_sp<SkImage>
makeImageFromNativeTexture(const TextureInfo &textureInfo, int width,
int height, bool mipMapped) = 0;

#if !defined(SK_GRAPHITE)
virtual GrDirectContext *getDirectContext() = 0;
Expand All @@ -113,11 +118,9 @@ class RNSkPlatformContext {

virtual uint64_t makeNativeBuffer(sk_sp<SkImage> image) = 0;

virtual jsi::Value getTexture(jsi::Runtime &runtime,
sk_sp<SkSurface> image) = 0;
virtual const TextureInfo getTexture(sk_sp<SkSurface> image) = 0;

virtual jsi::Value getTexture(jsi::Runtime &runtime,
sk_sp<SkImage> image) = 0;
virtual const TextureInfo getTexture(sk_sp<SkImage> image) = 0;

virtual std::shared_ptr<RNSkVideo> createVideo(const std::string &url) = 0;

Expand Down
9 changes: 4 additions & 5 deletions packages/skia/ios/RNSkia-iOS/RNSkiOSPlatformContext.h
Original file line number Diff line number Diff line change
Expand Up @@ -42,16 +42,15 @@ class RNSkiOSPlatformContext : public RNSkPlatformContext {

sk_sp<SkImage> makeImageFromNativeBuffer(void *buffer) override;

sk_sp<SkImage> makeImageFromNativeTexture(jsi::Runtime &runtime,
jsi::Value textureInfo, int width,
int height,
sk_sp<SkImage> makeImageFromNativeTexture(const TextureInfo &textureInfo,
int width, int height,
bool mipMapped) override;

uint64_t makeNativeBuffer(sk_sp<SkImage> image) override;

jsi::Value getTexture(jsi::Runtime &runtime, sk_sp<SkSurface> image) override;
const TextureInfo getTexture(sk_sp<SkSurface> image) override;

jsi::Value getTexture(jsi::Runtime &runtime, sk_sp<SkImage> image) override;
const TextureInfo getTexture(sk_sp<SkImage> image) override;

void releaseNativeBuffer(uint64_t pointer) override;

Expand Down
35 changes: 15 additions & 20 deletions packages/skia/ios/RNSkia-iOS/RNSkiOSPlatformContext.mm
Original file line number Diff line number Diff line change
Expand Up @@ -156,36 +156,36 @@
return reinterpret_cast<uint64_t>(pixelBuffer);
}

jsi::Value RNSkiOSPlatformContext::getTexture(jsi::Runtime &runtime,
sk_sp<SkImage> image) {
const TextureInfo RNSkiOSPlatformContext::getTexture(sk_sp<SkImage> image) {
GrBackendTexture texture;
TextureInfo result;
if (!SkImages::GetBackendTextureFromImage(image, &texture, true)) {
return jsi::Value::null();
throw std::runtime_error("Couldn't get backend texture");
}
if (!texture.isValid()) {
return jsi::Value::null();
throw std::runtime_error("Invalid backend texture");
}
GrMtlTextureInfo textureInfo;
if (!GrBackendTextures::GetMtlTextureInfo(texture, &textureInfo)) {
return jsi::Value::null();
throw std::runtime_error("Couldn't get Metal texture info");
}
auto pointer = reinterpret_cast<uint64_t>(textureInfo.fTexture.get());
return jsi::BigInt::fromUint64(runtime, pointer);
result.mtlTexture = textureInfo.fTexture.get();
return result;
}

jsi::Value RNSkiOSPlatformContext::getTexture(jsi::Runtime &runtime,
sk_sp<SkSurface> surface) {
const TextureInfo RNSkiOSPlatformContext::getTexture(sk_sp<SkSurface> surface) {
GrBackendTexture texture = SkSurfaces::GetBackendTexture(
surface.get(), SkSurfaces::BackendHandleAccess::kFlushRead);
TextureInfo result;
if (!texture.isValid()) {
return jsi::Value::null();
throw std::runtime_error("Invalid backend texture");
}
GrMtlTextureInfo textureInfo;
if (!GrBackendTextures::GetMtlTextureInfo(texture, &textureInfo)) {
return jsi::Value::null();
throw std::runtime_error("Couldn't get Metal texture info");
}
auto pointer = reinterpret_cast<uint64_t>(textureInfo.fTexture.get());
return jsi::BigInt::fromUint64(runtime, pointer);
result.mtlTexture = textureInfo.fTexture.get();
return result;
}

std::shared_ptr<RNSkVideo>
Expand Down Expand Up @@ -226,13 +226,8 @@
}

sk_sp<SkImage> RNSkiOSPlatformContext::makeImageFromNativeTexture(
jsi::Runtime &runtime, jsi::Value jsiTextureInfo, int width, int height,
bool mipMapped) {
if (!jsiTextureInfo.isBigInt()) {
throw std::runtime_error("Invalid textureInfo");
}
auto pointer = (void *)jsiTextureInfo.asBigInt(runtime).asUint64(runtime);
id<MTLTexture> mtlTexture = (__bridge id<MTLTexture>)(pointer);
const TextureInfo &texInfo, int width, int height, bool mipMapped) {
id<MTLTexture> mtlTexture = (__bridge id<MTLTexture>)(texInfo.mtlTexture);

SkColorType colorType = mtlPixelFormatToSkColorType(mtlTexture.pixelFormat);
if (colorType == SkColorType::kUnknown_SkColorType) {
Expand Down

0 comments on commit 52f2e44

Please sign in to comment.