Skip to content

Commit

Permalink
[Fabric] Move UriHandler registration to PackageProvider (#13197)
Browse files Browse the repository at this point in the history
* Move UriHandler registration to PackageProvider

* Change files

* fix

* fix

* fix

* Remove eval test - eval is not supported by hermes

* Fix UT

* fix
  • Loading branch information
acoates-ms authored May 8, 2024
1 parent f0966d5 commit de5c307
Show file tree
Hide file tree
Showing 18 changed files with 82 additions and 77 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
{
"type": "prerelease",
"comment": "Move UriHandler registration to PackageProvider",
"packageName": "react-native-windows",
"email": "30809111+acoates-ms@users.noreply.github.com",
"dependentChangeType": "patch"
}
Original file line number Diff line number Diff line change
Expand Up @@ -92,10 +92,15 @@ struct EllipseImageHandler : winrt::implements<
}
};

void RegisterEllipseUriImageHandler(const winrt::Microsoft::ReactNative::ReactInstanceSettings &settings) noexcept {
winrt::Microsoft::ReactNative::Composition::UriImageManager::AddUriImageProvider(
settings.Properties(), winrt::make<EllipseImageHandler>());
}
struct EllipseReactPackageProvider
: winrt::implements<EllipseReactPackageProvider, winrt::Microsoft::ReactNative::IReactPackageProvider> {
public: // IReactPackageProvider
void CreatePackage(winrt::Microsoft::ReactNative::IReactPackageBuilder const &packageBuilder) noexcept {
// Register ellipse: uri handler for images
packageBuilder.as<winrt::Microsoft::ReactNative::IReactPackageBuilderFabric>().AddUriImageProvider(
winrt::make<EllipseImageHandler>());
}
};

// Have to use TurboModules to override built in modules.. so the standard attributed package provider doesn't work.
struct CompReactPackageProvider
Expand Down Expand Up @@ -238,7 +243,7 @@ struct WindowData {
InstanceSettings(), g_liftedCompositor);

// Register ellipse:// uri hander for images
RegisterEllipseUriImageHandler(host.InstanceSettings());
host.PackageProviders().Append(winrt::make<EllipseReactPackageProvider>());

auto bridge = winrt::Microsoft::UI::Content::DesktopChildSiteBridge::Create(
g_liftedCompositor, winrt::Microsoft::UI::GetWindowIdFromWindow(hwnd));
Expand Down
1 change: 1 addition & 0 deletions vnext/Desktop/ABI/TestController.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -96,6 +96,7 @@ msrn::IReactPackageBuilder TestController::CreateReactPackageBuilder() {
turboModulesProvider,
#ifdef USE_FABRIC
std::shared_ptr<::Microsoft::ReactNative::WindowsComponentDescriptorRegistry>{},
std::shared_ptr<winrt::Microsoft::ReactNative::Composition::implementation::UriImageManager>{},
#endif
true);
}
Expand Down
13 changes: 0 additions & 13 deletions vnext/Microsoft.ReactNative.IntegrationTests/ExecuteJsiTests.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -24,17 +24,6 @@ struct TestExecuteJsiModule {
TestEventService::LogEvent("initialize", nullptr);
}

REACT_METHOD(TestSimpleExecuteJsi, L"testSimpleExecuteJsi")
void TestSimpleExecuteJsi() noexcept {
TestEventService::LogEvent("testSimpleExecuteJsi started", nullptr);
ExecuteJsi(m_reactContext, [](Runtime &rt) {
auto eval = rt.global().getPropertyAsFunction(rt, "eval");
auto addFunc = eval.call(rt, "(function(x, y) { return x + y; })").getObject(rt).getFunction(rt);
TestCheckEqual(7, addFunc.call(rt, 3, 4).getNumber());
TestEventService::LogEvent("testSimpleExecuteJsi completed", nullptr);
});
}

REACT_METHOD(TestHostFunction, L"testHostFunction")
void TestHostFunction() noexcept {
TestEventService::LogEvent("testHostFunction started", nullptr);
Expand Down Expand Up @@ -143,8 +132,6 @@ TEST_CLASS (ExecuteJsiTests) {

TestEventService::ObserveEvents({
TestEvent{"initialize", nullptr},
TestEvent{"testSimpleExecuteJsi started", nullptr},
TestEvent{"testSimpleExecuteJsi completed", nullptr},
TestEvent{"testHostFunction started", nullptr},
TestEvent{"testHostFunction completed", nullptr},
TestEvent{"testHostObject started", nullptr},
Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
import { TurboModuleRegistry } from 'react-native';
const testExecuteJsiModule = TurboModuleRegistry.getEnforcing('TestExecuteJsiModule');

testExecuteJsiModule.testSimpleExecuteJsi();
testExecuteJsiModule.testHostFunction();
testExecuteJsiModule.testHostObject();
testExecuteJsiModule.testHostObject();
testExecuteJsiModule.testSameJsiRuntime();
testExecuteJsiModule.testExecuteJsiPromise();
25 changes: 12 additions & 13 deletions vnext/Microsoft.ReactNative/Fabric/Composition/UriImageManager.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,6 @@
#include "UriImageManager.h"

#include "Composition.ImageSource.g.h"
#include "Composition.UriImageManager.g.cpp"
#include <AutoDraw.h>
#include <ReactPropertyBag.h>
#include <d2d1_3.h>
Expand Down Expand Up @@ -183,8 +182,8 @@ struct DataImageHandler : winrt::implements<
}
};

static const ReactPropertyId<ReactNonAbiValue<winrt::com_ptr<UriImageManager>>> &UriImageManagerPropertyId() noexcept {
static const ReactPropertyId<ReactNonAbiValue<winrt::com_ptr<UriImageManager>>> prop{
static const ReactPropertyId<ReactNonAbiValue<std::shared_ptr<UriImageManager>>> &UriImageManagerPropertyId() noexcept {
static const ReactPropertyId<ReactNonAbiValue<std::shared_ptr<UriImageManager>>> prop{
L"ReactNative", L"UriImageManager"};
return prop;
}
Expand All @@ -194,21 +193,21 @@ UriImageManager::UriImageManager() {
m_providers.push_back(winrt::make<DataImageHandler>());
}

winrt::com_ptr<UriImageManager> UriImageManager::GetOrCreate(
void UriImageManager::Install(
const winrt::Microsoft::ReactNative::ReactPropertyBag &properties,
const std::shared_ptr<UriImageManager> &manager) noexcept {
properties.Set(UriImageManagerPropertyId(), manager);
}

std::shared_ptr<UriImageManager> UriImageManager::Get(
const winrt::Microsoft::ReactNative::ReactPropertyBag &properties) noexcept {
auto uriImageManager =
winrt::Microsoft::ReactNative::ReactPropertyBag(properties).GetOrCreate(UriImageManagerPropertyId(), []() {
return winrt::make_self<UriImageManager>();
});
return uriImageManager.Value();
return winrt::Microsoft::ReactNative::ReactPropertyBag(properties).Get(UriImageManagerPropertyId()).Value();
}

void UriImageManager::AddUriImageProvider(
const winrt::Microsoft::ReactNative::IReactPropertyBag &properties,
const IUriImageProvider &provider) {
void UriImageManager::AddUriImageProvider(const IUriImageProvider &provider) {
if (!provider)
winrt::throw_hresult(E_INVALIDARG);
GetOrCreate(winrt::Microsoft::ReactNative::ReactPropertyBag(properties))->m_providers.push_back(provider);
m_providers.push_back(provider);
}

IUriImageProvider UriImageManager::TryGetUriImageProvider(
Expand Down
17 changes: 7 additions & 10 deletions vnext/Microsoft.ReactNative/Fabric/Composition/UriImageManager.h
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@
// Licensed under the MIT License.

#pragma once
#include "Composition.UriImageManager.g.h"

#include <ReactPropertyBag.h>
#include <Utils/ImageUtils.h>
Expand All @@ -11,14 +10,16 @@

namespace winrt::Microsoft::ReactNative::Composition::implementation {

struct UriImageManager : UriImageManagerT<UriImageManager> {
struct UriImageManager {
UriImageManager();

static void AddUriImageProvider(
const winrt::Microsoft::ReactNative::IReactPropertyBag &properties,
const IUriImageProvider &provider);
void AddUriImageProvider(const IUriImageProvider &provider);

static winrt::com_ptr<UriImageManager> GetOrCreate(
static void Install(
const winrt::Microsoft::ReactNative::ReactPropertyBag &properties,
const std::shared_ptr<UriImageManager> &manager) noexcept;

static std::shared_ptr<UriImageManager> Get(
const winrt::Microsoft::ReactNative::ReactPropertyBag &properties) noexcept;

IUriImageProvider TryGetUriImageProvider(
Expand All @@ -33,7 +34,3 @@ winrt::Microsoft::ReactNative::Composition::ImageSource MakeImageSource(
const facebook::react::ImageSource &source) noexcept;

} // namespace winrt::Microsoft::ReactNative::Composition::implementation

namespace winrt::Microsoft::ReactNative::Composition::factory_implementation {
struct UriImageManager : UriImageManagerT<UriImageManager, implementation::UriImageManager> {};
} // namespace winrt::Microsoft::ReactNative::Composition::factory_implementation

This file was deleted.

4 changes: 2 additions & 2 deletions vnext/Microsoft.ReactNative/Fabric/WindowsImageManager.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -19,8 +19,8 @@ namespace Microsoft::ReactNative {

WindowsImageManager::WindowsImageManager(winrt::Microsoft::ReactNative::ReactContext reactContext)
: m_reactContext(reactContext) {
m_uriImageManager = winrt::Microsoft::ReactNative::Composition::implementation::UriImageManager::GetOrCreate(
reactContext.Properties());
m_uriImageManager =
winrt::Microsoft::ReactNative::Composition::implementation::UriImageManager::Get(reactContext.Properties());
}

winrt::com_ptr<IWICBitmapSource> wicBitmapSourceFromStream(
Expand Down
2 changes: 1 addition & 1 deletion vnext/Microsoft.ReactNative/Fabric/WindowsImageManager.h
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ struct WindowsImageManager {

private:
winrt::Microsoft::ReactNative::ReactContext m_reactContext;
winrt::com_ptr<winrt::Microsoft::ReactNative::Composition::implementation::UriImageManager> m_uriImageManager;
std::shared_ptr<winrt::Microsoft::ReactNative::Composition::implementation::UriImageManager> m_uriImageManager;
};

} // namespace Microsoft::ReactNative
5 changes: 5 additions & 0 deletions vnext/Microsoft.ReactNative/IReactPackageBuilderFabric.idl
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
// Licensed under the MIT License.

import "IReactViewComponentBuilder.idl";
import "UriImageManager.idl";

#include "DocString.h"

Expand All @@ -18,6 +19,10 @@ namespace Microsoft.ReactNative
{
DOC_STRING("Registers a custom native view component.")
void AddViewComponent(String componentName, ReactViewComponentProvider componentProvider);

DOC_STRING(
"Ability to load images using custom Uri protocol handlers. The provider should implement @Composition.IUriImageStreamProvider or @Composition.Experimental.IUriBrushProvider.")
void AddUriImageProvider(Microsoft.ReactNative.Composition.IUriImageProvider provider);
};

} // namespace Microsoft.ReactNative
7 changes: 7 additions & 0 deletions vnext/Microsoft.ReactNative/ReactHost/React.h
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,10 @@
#include <ViewManagerProvider.h>
#include <winrt/Microsoft.ReactNative.h>

#ifdef USE_FABRIC
#include <Fabric/Composition/UriImageManager.h>
#endif

namespace Mso::React {

// Forward declarations
Expand Down Expand Up @@ -182,6 +186,9 @@ struct ReactOptions {
std::shared_ptr<NativeModuleProvider2> ModuleProvider;
std::shared_ptr<ViewManagerProvider2> ViewManagerProvider;
std::shared_ptr<winrt::Microsoft::ReactNative::TurboModulesProvider> TurboModuleProvider;
#ifdef USE_FABRIC
std::shared_ptr<winrt::Microsoft::ReactNative::Composition::implementation::UriImageManager> UriImageManager;
#endif

//! Identity of the SDX. Must uniquely describe the SDX across the installed product.
std::string Identity;
Expand Down
7 changes: 7 additions & 0 deletions vnext/Microsoft.ReactNative/ReactHost/ReactInstanceWin.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,7 @@
#include "Unicode.h"

#ifdef USE_FABRIC
#include <Fabric/Composition/UriImageManager.h>
#include <Fabric/FabricUIManagerModule.h>
#include <Fabric/ReactNativeConfigProperties.h>
#include <Fabric/WindowsComponentDescriptorRegistry.h>
Expand Down Expand Up @@ -570,6 +571,8 @@ void ReactInstanceWin::InitializeBridgeless() noexcept {
});

InitDevMenu();
winrt::Microsoft::ReactNative::Composition::implementation::UriImageManager::Install(
ReactPropertyBag(m_reactContext->Properties()), m_options.UriImageManager);

m_uiQueue->Post([this, weakThis = Mso::WeakPtr{this}]() noexcept {
// Objects that must be created on the UI thread
Expand Down Expand Up @@ -726,6 +729,10 @@ void ReactInstanceWin::InitializeWithBridge() noexcept {
#endif

InitDevMenu();
#ifdef USE_FABRIC
winrt::Microsoft::ReactNative::Composition::implementation::UriImageManager::Install(
ReactPropertyBag(m_reactContext->Properties()), m_options.UriImageManager);
#endif

m_uiQueue->Post([this, weakThis = Mso::WeakPtr{this}]() noexcept {
// Objects that must be created on the UI thread
Expand Down
8 changes: 8 additions & 0 deletions vnext/Microsoft.ReactNative/ReactNativeHost.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@

#ifdef USE_FABRIC
#include <Fabric/WindowsComponentDescriptorRegistry.h>
#include <ReactPackageBuilder.h>
#include <react/renderer/componentregistry/ComponentDescriptorProviderRegistry.h>
#endif

Expand Down Expand Up @@ -93,6 +94,8 @@ IAsyncAction ReactNativeHost::ReloadInstance() noexcept {
auto turboModulesProvider = std::make_shared<TurboModulesProvider>();

#ifdef USE_FABRIC
auto uriImageManager =
std::make_shared<winrt::Microsoft::ReactNative::Composition::implementation::UriImageManager>();
auto componentregistry = std::make_shared<::Microsoft::ReactNative::WindowsComponentDescriptorRegistry>();
auto componentDescriptorRegistry = std::make_shared<facebook::react::ComponentDescriptorProviderRegistry>();

Expand All @@ -108,6 +111,7 @@ IAsyncAction ReactNativeHost::ReloadInstance() noexcept {
turboModulesProvider,
#ifdef USE_FABRIC
componentregistry,
uriImageManager,
#endif
m_instanceSettings.UseWebDebugger());

Expand Down Expand Up @@ -164,6 +168,10 @@ IAsyncAction ReactNativeHost::ReloadInstance() noexcept {
#endif
reactOptions.TurboModuleProvider = turboModulesProvider;

#ifdef USE_FABRIC
reactOptions.UriImageManager = uriImageManager;
#endif

reactOptions.OnInstanceCreated = [](Mso::CntPtr<Mso::React::IReactContext> &&context) {
auto notifications = context->Notifications();
ReactInstanceSettings::RaiseInstanceCreated(
Expand Down
8 changes: 8 additions & 0 deletions vnext/Microsoft.ReactNative/ReactPackageBuilder.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ ReactPackageBuilder::ReactPackageBuilder(
std::shared_ptr<TurboModulesProvider> const &turboModulesProvider,
#ifdef USE_FABRIC
std::shared_ptr<::Microsoft::ReactNative::WindowsComponentDescriptorRegistry> const &componentRegistry,
std::shared_ptr<winrt::Microsoft::ReactNative::Composition::implementation::UriImageManager> const &uriImageManager,
#endif
bool isWebDebugging) noexcept
: m_modulesProvider{modulesProvider},
Expand All @@ -31,6 +32,7 @@ ReactPackageBuilder::ReactPackageBuilder(
m_turboModulesProvider{turboModulesProvider},
#ifdef USE_FABRIC
m_componentRegistry{componentRegistry},
m_uriImageManager{uriImageManager},
#endif

m_isWebDebugging{isWebDebugging} {
Expand Down Expand Up @@ -63,5 +65,11 @@ void ReactPackageBuilder::AddViewComponent(
ReactViewComponentProvider const &viewComponentProvider) noexcept {
m_componentRegistry->Add(componentName, viewComponentProvider);
}

void ReactPackageBuilder::AddUriImageProvider(
const winrt::Microsoft::ReactNative::Composition::IUriImageProvider &provider) noexcept {
m_uriImageManager->AddUriImageProvider(provider);
}

#endif
} // namespace winrt::Microsoft::ReactNative
6 changes: 6 additions & 0 deletions vnext/Microsoft.ReactNative/ReactPackageBuilder.h
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,9 @@
#endif
#include "winrt/Microsoft.ReactNative.h"
#ifdef USE_FABRIC
#include <Fabric/Composition/UriImageManager.h>
#include <Fabric/WindowsComponentDescriptorRegistry.h>
#include "winrt/Microsoft.ReactNative.Composition.h"
#endif

namespace winrt::Microsoft::ReactNative {
Expand All @@ -30,6 +32,8 @@ struct ReactPackageBuilder : winrt::implements<
std::shared_ptr<TurboModulesProvider> const &turboModulesProvider,
#ifdef USE_FABRIC
std::shared_ptr<::Microsoft::ReactNative::WindowsComponentDescriptorRegistry> const &componentRegistry,
std::shared_ptr<winrt::Microsoft::ReactNative::Composition::implementation::UriImageManager> const
&uriImageManager,
#endif
bool isWebDebugging) noexcept;

Expand All @@ -43,6 +47,7 @@ struct ReactPackageBuilder : winrt::implements<
#ifdef USE_FABRIC
// IReactPackageBuilderFabric
void AddViewComponent(winrt::hstring componentName, ReactViewComponentProvider const &viewComponentProvider) noexcept;
void AddUriImageProvider(const winrt::Microsoft::ReactNative::Composition::IUriImageProvider &provider) noexcept;
#endif // USE_FABRIC

private:
Expand All @@ -54,6 +59,7 @@ struct ReactPackageBuilder : winrt::implements<

#ifdef USE_FABRIC
std::shared_ptr<::Microsoft::ReactNative::WindowsComponentDescriptorRegistry> m_componentRegistry;
std::shared_ptr<winrt::Microsoft::ReactNative::Composition::implementation::UriImageManager> m_uriImageManager;
#endif

const bool m_isWebDebugging;
Expand Down
10 changes: 0 additions & 10 deletions vnext/Microsoft.ReactNative/UriImageManager.idl
Original file line number Diff line number Diff line change
Expand Up @@ -72,14 +72,4 @@ namespace Microsoft.ReactNative.Composition
Windows.Foundation.IAsyncOperation<UriBrushFactory> GetSourceAsync(Microsoft.ReactNative.IReactContext context, Microsoft.ReactNative.Composition.ImageSource imageSource);
}
}

[default_interface]
[webhosthidden]
[experimental]
DOC_STRING(
"Ability to load images using custom Uri protocol handlers. The provider should implement @IUriImageStreamProvider or @Experimental.IUriBrushProvider")
runtimeclass UriImageManager
{
static void AddUriImageProvider(Microsoft.ReactNative.IReactPropertyBag properties, IUriImageProvider provider);
}
} // namespace Microsoft.ReactNative.Composition
Loading

0 comments on commit de5c307

Please sign in to comment.