react-native-windows 0.74.4 → 0.74.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/Libraries/Components/TextInput/TextInput.windows.js +6 -2
- package/Libraries/Components/View/View.windows.js +3 -0
- package/Microsoft.ReactNative/ComponentView.idl +26 -0
- package/Microsoft.ReactNative/CompositionComponentView.idl +19 -7
- package/Microsoft.ReactNative/CompositionRootView.idl +1 -0
- package/Microsoft.ReactNative/CompositionUIService.idl +4 -0
- package/Microsoft.ReactNative/Fabric/AbiViewComponentDescriptor.cpp +2 -1
- package/Microsoft.ReactNative/Fabric/AbiViewProps.cpp +106 -19
- package/Microsoft.ReactNative/Fabric/AbiViewProps.h +45 -13
- package/Microsoft.ReactNative/Fabric/ComponentView.cpp +83 -12
- package/Microsoft.ReactNative/Fabric/ComponentView.h +33 -2
- package/Microsoft.ReactNative/Fabric/Composition/ActivityIndicatorComponentView.cpp +28 -64
- package/Microsoft.ReactNative/Fabric/Composition/ActivityIndicatorComponentView.h +7 -11
- package/Microsoft.ReactNative/Fabric/Composition/CompositionRootView.cpp +30 -11
- package/Microsoft.ReactNative/Fabric/Composition/CompositionRootView.h +4 -0
- package/Microsoft.ReactNative/Fabric/Composition/CompositionRootView_emptyimpl.cpp +4 -0
- package/Microsoft.ReactNative/Fabric/Composition/CompositionUIService.cpp +12 -0
- package/Microsoft.ReactNative/Fabric/Composition/CompositionUIService.h +4 -0
- package/Microsoft.ReactNative/Fabric/Composition/CompositionUIService_emptyimpl.cpp +6 -0
- package/Microsoft.ReactNative/Fabric/Composition/CompositionViewComponentView.cpp +60 -39
- package/Microsoft.ReactNative/Fabric/Composition/CompositionViewComponentView.h +19 -6
- package/Microsoft.ReactNative/Fabric/Composition/DebuggingOverlayComponentView.cpp +1 -0
- package/Microsoft.ReactNative/Fabric/Composition/FocusManager.cpp +152 -0
- package/Microsoft.ReactNative/Fabric/Composition/FocusManager.h +85 -0
- package/Microsoft.ReactNative/Fabric/Composition/ImageComponentView.cpp +49 -95
- package/Microsoft.ReactNative/Fabric/Composition/ImageComponentView.h +11 -15
- package/Microsoft.ReactNative/Fabric/Composition/Modal/WindowsModalHostViewComponentView.cpp +16 -31
- package/Microsoft.ReactNative/Fabric/Composition/Modal/WindowsModalHostViewComponentView.h +5 -8
- package/Microsoft.ReactNative/Fabric/Composition/ParagraphComponentView.cpp +24 -81
- package/Microsoft.ReactNative/Fabric/Composition/ParagraphComponentView.h +4 -13
- package/Microsoft.ReactNative/Fabric/Composition/RootComponentView.cpp +41 -40
- package/Microsoft.ReactNative/Fabric/Composition/RootComponentView.h +5 -1
- package/Microsoft.ReactNative/Fabric/Composition/ScrollViewComponentView.cpp +53 -68
- package/Microsoft.ReactNative/Fabric/Composition/ScrollViewComponentView.h +5 -7
- package/Microsoft.ReactNative/Fabric/Composition/SwitchComponentView.cpp +38 -84
- package/Microsoft.ReactNative/Fabric/Composition/SwitchComponentView.h +6 -10
- package/Microsoft.ReactNative/Fabric/Composition/TextInput/WindowsTextInputComponentView.cpp +59 -109
- package/Microsoft.ReactNative/Fabric/Composition/TextInput/WindowsTextInputComponentView.h +9 -15
- package/Microsoft.ReactNative/Fabric/Composition/UnimplementedNativeViewComponentView.cpp +1 -0
- package/Microsoft.ReactNative/FocusManager.idl +22 -0
- package/Microsoft.ReactNative/ViewProps.idl +37 -3
- package/Microsoft.ReactNative.Cxx/JSValueComposition.h +4 -0
- package/PropertySheets/Generated/PackageVersion.g.props +3 -3
- package/Shared/Shared.vcxitems +6 -0
- package/package.json +1 -1
|
@@ -0,0 +1,152 @@
|
|
|
1
|
+
// Copyright (c) Microsoft Corporation.
|
|
2
|
+
// Licensed under the MIT License.
|
|
3
|
+
|
|
4
|
+
#include "pch.h"
|
|
5
|
+
#include "FocusManager.h"
|
|
6
|
+
#include "Composition.FocusManager.g.cpp"
|
|
7
|
+
#include <Fabric/FabricUIManagerModule.h>
|
|
8
|
+
|
|
9
|
+
namespace winrt::Microsoft::ReactNative::implementation {
|
|
10
|
+
|
|
11
|
+
LostFocusEventArgs::LostFocusEventArgs(const winrt::Microsoft::ReactNative::ComponentView &originalSource)
|
|
12
|
+
: m_originalSource(originalSource ? originalSource.Tag() : -1) {}
|
|
13
|
+
int32_t LostFocusEventArgs::OriginalSource() noexcept {
|
|
14
|
+
return m_originalSource;
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
GotFocusEventArgs::GotFocusEventArgs(const winrt::Microsoft::ReactNative::ComponentView &originalSource)
|
|
18
|
+
: m_originalSource(originalSource ? originalSource.Tag() : -1) {}
|
|
19
|
+
int32_t GotFocusEventArgs::OriginalSource() noexcept {
|
|
20
|
+
return m_originalSource;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
LosingFocusEventArgs::LosingFocusEventArgs(
|
|
24
|
+
const winrt::Microsoft::ReactNative::ComponentView &originalSource,
|
|
25
|
+
const winrt::Microsoft::ReactNative::ComponentView &oldFocusedComponent,
|
|
26
|
+
const winrt::Microsoft::ReactNative::ComponentView &newFocusedComponent)
|
|
27
|
+
: m_originalSource(originalSource ? originalSource.Tag() : -1),
|
|
28
|
+
m_old(oldFocusedComponent),
|
|
29
|
+
m_new(newFocusedComponent) {}
|
|
30
|
+
|
|
31
|
+
int32_t LosingFocusEventArgs::OriginalSource() noexcept {
|
|
32
|
+
return m_originalSource;
|
|
33
|
+
}
|
|
34
|
+
winrt::Microsoft::ReactNative::ComponentView LosingFocusEventArgs::NewFocusedComponent() noexcept {
|
|
35
|
+
return m_new;
|
|
36
|
+
}
|
|
37
|
+
winrt::Microsoft::ReactNative::ComponentView LosingFocusEventArgs::OldFocusedComponent() noexcept {
|
|
38
|
+
return m_old;
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
void LosingFocusEventArgs::TryCancel() noexcept {
|
|
42
|
+
m_new = m_old;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
void LosingFocusEventArgs::TrySetNewFocusedComponent(
|
|
46
|
+
const winrt::Microsoft::ReactNative::ComponentView &newFocusedComponent) noexcept {
|
|
47
|
+
auto selfView = winrt::get_self<winrt::Microsoft::ReactNative::implementation::ComponentView>(newFocusedComponent);
|
|
48
|
+
if (selfView->focusable()) {
|
|
49
|
+
m_new = newFocusedComponent;
|
|
50
|
+
} else {
|
|
51
|
+
auto target =
|
|
52
|
+
winrt::Microsoft::ReactNative::Composition::FocusManager::FindFirstFocusableElement(newFocusedComponent);
|
|
53
|
+
if (!target)
|
|
54
|
+
return;
|
|
55
|
+
m_new = target;
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
GettingFocusEventArgs::GettingFocusEventArgs(
|
|
60
|
+
const winrt::Microsoft::ReactNative::ComponentView &originalSource,
|
|
61
|
+
const winrt::Microsoft::ReactNative::ComponentView &oldFocusedComponent,
|
|
62
|
+
const winrt::Microsoft::ReactNative::ComponentView &newFocusedComponent)
|
|
63
|
+
: m_originalSource(originalSource ? originalSource.Tag() : -1),
|
|
64
|
+
m_old(oldFocusedComponent),
|
|
65
|
+
m_new(newFocusedComponent) {}
|
|
66
|
+
|
|
67
|
+
int32_t GettingFocusEventArgs::OriginalSource() noexcept {
|
|
68
|
+
return m_originalSource;
|
|
69
|
+
}
|
|
70
|
+
winrt::Microsoft::ReactNative::ComponentView GettingFocusEventArgs::NewFocusedComponent() noexcept {
|
|
71
|
+
return m_new;
|
|
72
|
+
}
|
|
73
|
+
winrt::Microsoft::ReactNative::ComponentView GettingFocusEventArgs::OldFocusedComponent() noexcept {
|
|
74
|
+
return m_old;
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
void GettingFocusEventArgs::TryCancel() noexcept {
|
|
78
|
+
m_new = m_old;
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
void GettingFocusEventArgs::TrySetNewFocusedComponent(
|
|
82
|
+
const winrt::Microsoft::ReactNative::ComponentView &newFocusedComponent) noexcept {
|
|
83
|
+
auto selfView = winrt::get_self<winrt::Microsoft::ReactNative::implementation::ComponentView>(newFocusedComponent);
|
|
84
|
+
if (selfView->focusable()) {
|
|
85
|
+
m_new = newFocusedComponent;
|
|
86
|
+
} else {
|
|
87
|
+
auto target =
|
|
88
|
+
winrt::Microsoft::ReactNative::Composition::FocusManager::FindFirstFocusableElement(newFocusedComponent);
|
|
89
|
+
if (!target)
|
|
90
|
+
return;
|
|
91
|
+
m_new = target;
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
} // namespace winrt::Microsoft::ReactNative::implementation
|
|
96
|
+
|
|
97
|
+
namespace winrt::Microsoft::ReactNative::Composition::implementation {
|
|
98
|
+
|
|
99
|
+
winrt::Microsoft::ReactNative::implementation::ComponentView *NavigateFocusHelper(
|
|
100
|
+
winrt::Microsoft::ReactNative::implementation::ComponentView &view,
|
|
101
|
+
winrt::Microsoft::ReactNative::FocusNavigationReason reason) {
|
|
102
|
+
if (reason == winrt::Microsoft::ReactNative::FocusNavigationReason::First) {
|
|
103
|
+
if (view.focusable()) {
|
|
104
|
+
return &view;
|
|
105
|
+
}
|
|
106
|
+
}
|
|
107
|
+
winrt::Microsoft::ReactNative::implementation::ComponentView *toFocus = nullptr;
|
|
108
|
+
|
|
109
|
+
Mso::Functor<bool(::winrt::Microsoft::ReactNative::implementation::ComponentView & v)> fn =
|
|
110
|
+
[reason, &toFocus](::winrt::Microsoft::ReactNative::implementation::ComponentView &v) noexcept
|
|
111
|
+
-> bool { return (toFocus = NavigateFocusHelper(v, reason)); };
|
|
112
|
+
|
|
113
|
+
if (view.runOnChildren(reason == winrt::Microsoft::ReactNative::FocusNavigationReason::First, fn)) {
|
|
114
|
+
return toFocus;
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
if (reason == winrt::Microsoft::ReactNative::FocusNavigationReason::Last) {
|
|
118
|
+
if (view.focusable()) {
|
|
119
|
+
return &view;
|
|
120
|
+
}
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
return nullptr;
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
winrt::Microsoft::ReactNative::ComponentView FocusManager::FindFirstFocusableElement(
|
|
127
|
+
const winrt::Microsoft::ReactNative::ComponentView &searchScope) noexcept {
|
|
128
|
+
auto selfSearchScope = winrt::get_self<winrt::Microsoft::ReactNative::implementation::ComponentView>(searchScope);
|
|
129
|
+
auto view = NavigateFocusHelper(*selfSearchScope, winrt::Microsoft::ReactNative::FocusNavigationReason::First);
|
|
130
|
+
if (view) {
|
|
131
|
+
winrt::Microsoft::ReactNative::ComponentView component{nullptr};
|
|
132
|
+
winrt::check_hresult(view->QueryInterface(
|
|
133
|
+
winrt::guid_of<winrt::Microsoft::ReactNative::ComponentView>(), winrt::put_abi(component)));
|
|
134
|
+
return *view;
|
|
135
|
+
}
|
|
136
|
+
return nullptr;
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
winrt::Microsoft::ReactNative::ComponentView FocusManager::FindLastFocusableElement(
|
|
140
|
+
const winrt::Microsoft::ReactNative::ComponentView &searchScope) noexcept {
|
|
141
|
+
auto selfSearchScope = winrt::get_self<winrt::Microsoft::ReactNative::implementation::ComponentView>(searchScope);
|
|
142
|
+
auto view = NavigateFocusHelper(*selfSearchScope, winrt::Microsoft::ReactNative::FocusNavigationReason::Last);
|
|
143
|
+
if (view) {
|
|
144
|
+
winrt::Microsoft::ReactNative::ComponentView component{nullptr};
|
|
145
|
+
winrt::check_hresult(view->QueryInterface(
|
|
146
|
+
winrt::guid_of<winrt::Microsoft::ReactNative::ComponentView>(), winrt::put_abi(component)));
|
|
147
|
+
return *view;
|
|
148
|
+
}
|
|
149
|
+
return nullptr;
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
} // namespace winrt::Microsoft::ReactNative::Composition::implementation
|
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
// Copyright (c) Microsoft Corporation.
|
|
2
|
+
// Licensed under the MIT License.
|
|
3
|
+
|
|
4
|
+
#pragma once
|
|
5
|
+
#include "Composition.FocusManager.g.h"
|
|
6
|
+
#include "GettingFocusEventArgs.g.h"
|
|
7
|
+
#include "LosingFocusEventArgs.g.h"
|
|
8
|
+
#include <winrt/Microsoft.ReactNative.Composition.Experimental.h>
|
|
9
|
+
#include <winrt/Microsoft.ReactNative.Composition.Input.h>
|
|
10
|
+
|
|
11
|
+
namespace winrt::Microsoft::ReactNative::implementation {
|
|
12
|
+
|
|
13
|
+
struct LostFocusEventArgs
|
|
14
|
+
: winrt::implements<LostFocusEventArgs, winrt::Microsoft::ReactNative::Composition::Input::RoutedEventArgs> {
|
|
15
|
+
LostFocusEventArgs(const winrt::Microsoft::ReactNative::ComponentView &originalSource);
|
|
16
|
+
int32_t OriginalSource() noexcept;
|
|
17
|
+
|
|
18
|
+
private:
|
|
19
|
+
const int32_t m_originalSource;
|
|
20
|
+
};
|
|
21
|
+
|
|
22
|
+
struct GotFocusEventArgs
|
|
23
|
+
: winrt::implements<GotFocusEventArgs, winrt::Microsoft::ReactNative::Composition::Input::RoutedEventArgs> {
|
|
24
|
+
GotFocusEventArgs(const winrt::Microsoft::ReactNative::ComponentView &originalSource);
|
|
25
|
+
int32_t OriginalSource() noexcept;
|
|
26
|
+
|
|
27
|
+
private:
|
|
28
|
+
const int32_t m_originalSource;
|
|
29
|
+
};
|
|
30
|
+
|
|
31
|
+
struct LosingFocusEventArgs
|
|
32
|
+
: winrt::Microsoft::ReactNative::implementation::LosingFocusEventArgsT<LosingFocusEventArgs> {
|
|
33
|
+
LosingFocusEventArgs(
|
|
34
|
+
const winrt::Microsoft::ReactNative::ComponentView &originalSource,
|
|
35
|
+
const winrt::Microsoft::ReactNative::ComponentView &oldFocusedComponent,
|
|
36
|
+
const winrt::Microsoft::ReactNative::ComponentView &newFocusedComponent);
|
|
37
|
+
int32_t OriginalSource() noexcept;
|
|
38
|
+
winrt::Microsoft::ReactNative::ComponentView NewFocusedComponent() noexcept;
|
|
39
|
+
winrt::Microsoft::ReactNative::ComponentView OldFocusedComponent() noexcept;
|
|
40
|
+
|
|
41
|
+
void TryCancel() noexcept;
|
|
42
|
+
void TrySetNewFocusedComponent(const winrt::Microsoft::ReactNative::ComponentView &newFocusedComponent) noexcept;
|
|
43
|
+
|
|
44
|
+
private:
|
|
45
|
+
const int32_t m_originalSource;
|
|
46
|
+
winrt::Microsoft::ReactNative::ComponentView m_old{nullptr};
|
|
47
|
+
winrt::Microsoft::ReactNative::ComponentView m_new{nullptr};
|
|
48
|
+
};
|
|
49
|
+
|
|
50
|
+
struct GettingFocusEventArgs
|
|
51
|
+
: winrt::Microsoft::ReactNative::implementation::GettingFocusEventArgsT<GettingFocusEventArgs> {
|
|
52
|
+
GettingFocusEventArgs(
|
|
53
|
+
const winrt::Microsoft::ReactNative::ComponentView &originalSource,
|
|
54
|
+
const winrt::Microsoft::ReactNative::ComponentView &oldFocusedComponent,
|
|
55
|
+
const winrt::Microsoft::ReactNative::ComponentView &newFocusedComponent);
|
|
56
|
+
int32_t OriginalSource() noexcept;
|
|
57
|
+
winrt::Microsoft::ReactNative::ComponentView NewFocusedComponent() noexcept;
|
|
58
|
+
winrt::Microsoft::ReactNative::ComponentView OldFocusedComponent() noexcept;
|
|
59
|
+
|
|
60
|
+
void TryCancel() noexcept;
|
|
61
|
+
void TrySetNewFocusedComponent(const winrt::Microsoft::ReactNative::ComponentView &newFocusedComponent) noexcept;
|
|
62
|
+
|
|
63
|
+
private:
|
|
64
|
+
const int32_t m_originalSource;
|
|
65
|
+
winrt::Microsoft::ReactNative::ComponentView m_old{nullptr};
|
|
66
|
+
winrt::Microsoft::ReactNative::ComponentView m_new{nullptr};
|
|
67
|
+
};
|
|
68
|
+
} // namespace winrt::Microsoft::ReactNative::implementation
|
|
69
|
+
|
|
70
|
+
namespace winrt::Microsoft::ReactNative::Composition::implementation {
|
|
71
|
+
|
|
72
|
+
struct FocusManager : FocusManagerT<FocusManager> {
|
|
73
|
+
FocusManager() = default;
|
|
74
|
+
|
|
75
|
+
static winrt::Microsoft::ReactNative::ComponentView FindFirstFocusableElement(
|
|
76
|
+
const winrt::Microsoft::ReactNative::ComponentView &searchScope) noexcept;
|
|
77
|
+
static winrt::Microsoft::ReactNative::ComponentView FindLastFocusableElement(
|
|
78
|
+
const winrt::Microsoft::ReactNative::ComponentView &searchScope) noexcept;
|
|
79
|
+
};
|
|
80
|
+
|
|
81
|
+
} // namespace winrt::Microsoft::ReactNative::Composition::implementation
|
|
82
|
+
|
|
83
|
+
namespace winrt::Microsoft::ReactNative::Composition::factory_implementation {
|
|
84
|
+
struct FocusManager : FocusManagerT<FocusManager, implementation::FocusManager> {};
|
|
85
|
+
} // namespace winrt::Microsoft::ReactNative::Composition::factory_implementation
|
|
@@ -14,6 +14,7 @@
|
|
|
14
14
|
#include <react/renderer/components/image/ImageEventEmitter.h>
|
|
15
15
|
|
|
16
16
|
#include <AutoDraw.h>
|
|
17
|
+
#include <Fabric/AbiViewProps.h>
|
|
17
18
|
#include <Fabric/FabricUIManagerModule.h>
|
|
18
19
|
#include <Utils/ImageUtils.h>
|
|
19
20
|
#include <shcore.h>
|
|
@@ -48,19 +49,22 @@ void ImageComponentView::WindowsImageResponseObserver::didReceiveFailure() const
|
|
|
48
49
|
m_image->didReceiveFailureFromObserver();
|
|
49
50
|
}
|
|
50
51
|
|
|
52
|
+
facebook::react::SharedViewProps ImageComponentView::defaultProps() noexcept {
|
|
53
|
+
static auto const defaultProps = std::make_shared<facebook::react::ImageProps const>();
|
|
54
|
+
return defaultProps;
|
|
55
|
+
}
|
|
56
|
+
|
|
51
57
|
ImageComponentView::ImageComponentView(
|
|
52
58
|
const winrt::Microsoft::ReactNative::Composition::Experimental::ICompositionContext &compContext,
|
|
53
59
|
facebook::react::Tag tag,
|
|
54
60
|
winrt::Microsoft::ReactNative::ReactContext const &reactContext)
|
|
55
61
|
: Super(
|
|
62
|
+
ImageComponentView::defaultProps(),
|
|
56
63
|
compContext,
|
|
57
64
|
tag,
|
|
58
65
|
reactContext,
|
|
59
66
|
ComponentViewFeatures::Default & ~ComponentViewFeatures::Background,
|
|
60
|
-
false) {
|
|
61
|
-
static auto const defaultProps = std::make_shared<facebook::react::ImageProps const>();
|
|
62
|
-
m_props = defaultProps;
|
|
63
|
-
}
|
|
67
|
+
false) {}
|
|
64
68
|
|
|
65
69
|
void ImageComponentView::MountChildComponentView(
|
|
66
70
|
const winrt::Microsoft::ReactNative::ComponentView &childComponentView,
|
|
@@ -111,32 +115,24 @@ void ImageComponentView::didReceiveFailureFromObserver() noexcept {
|
|
|
111
115
|
}
|
|
112
116
|
}
|
|
113
117
|
|
|
118
|
+
const facebook::react::ImageProps &ImageComponentView::imageProps() const noexcept {
|
|
119
|
+
return *std::static_pointer_cast<const facebook::react::ImageProps>(viewProps());
|
|
120
|
+
}
|
|
121
|
+
|
|
114
122
|
void ImageComponentView::updateProps(
|
|
115
123
|
facebook::react::Props::Shared const &props,
|
|
116
124
|
facebook::react::Props::Shared const &oldProps) noexcept {
|
|
117
|
-
const auto &oldImageProps =
|
|
125
|
+
const auto &oldImageProps =
|
|
126
|
+
*std::static_pointer_cast<const facebook::react::ImageProps>(oldProps ? oldProps : viewProps());
|
|
118
127
|
const auto &newImageProps = *std::static_pointer_cast<const facebook::react::ImageProps>(props);
|
|
119
128
|
|
|
120
|
-
ensureVisual();
|
|
121
|
-
|
|
122
|
-
// update BaseComponentView props
|
|
123
|
-
updateTransformProps(oldImageProps, newImageProps, m_visual);
|
|
124
|
-
Super::updateProps(props, oldProps);
|
|
125
|
-
|
|
126
129
|
if (oldImageProps.backgroundColor != newImageProps.backgroundColor ||
|
|
127
130
|
oldImageProps.blurRadius != newImageProps.blurRadius || oldImageProps.tintColor != newImageProps.tintColor ||
|
|
128
131
|
oldImageProps.resizeMode != newImageProps.resizeMode) {
|
|
129
132
|
m_drawingSurface = nullptr; // TODO don't need to recreate the surface just to redraw...
|
|
130
133
|
}
|
|
131
134
|
|
|
132
|
-
|
|
133
|
-
m_visual.Opacity(newImageProps.opacity);
|
|
134
|
-
}
|
|
135
|
-
if (oldImageProps.testId != newImageProps.testId) {
|
|
136
|
-
m_visual.Comment(winrt::to_hstring(newImageProps.testId));
|
|
137
|
-
}
|
|
138
|
-
|
|
139
|
-
m_props = std::static_pointer_cast<facebook::react::ImageProps const>(props);
|
|
135
|
+
Super::updateProps(props, oldProps);
|
|
140
136
|
}
|
|
141
137
|
|
|
142
138
|
void ImageComponentView::updateState(
|
|
@@ -182,19 +178,22 @@ void ImageComponentView::setStateAndResubscribeImageResponseObserver(
|
|
|
182
178
|
}
|
|
183
179
|
}
|
|
184
180
|
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
181
|
+
winrt::Microsoft::ReactNative::ImageProps ImageComponentView::ImageProps() noexcept {
|
|
182
|
+
// We do not currently support custom ImageComponentView's
|
|
183
|
+
// If we did we would need to create a AbiImageProps and possibly return them here
|
|
184
|
+
assert(!m_customComponent);
|
|
185
|
+
return winrt::make<winrt::Microsoft::ReactNative::implementation::ImageProps>(viewProps());
|
|
186
|
+
}
|
|
189
187
|
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
188
|
+
winrt::Microsoft::ReactNative::ImageProps ImageComponentView::ViewProps() noexcept {
|
|
189
|
+
return ViewPropsInner().as<winrt::Microsoft::ReactNative::ImageProps>();
|
|
190
|
+
}
|
|
193
191
|
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
192
|
+
winrt::Microsoft::ReactNative::ViewProps ImageComponentView::ViewPropsInner() noexcept {
|
|
193
|
+
// We do not currently support custom ImageComponentView's
|
|
194
|
+
// If we did we would need to create a AbiImageProps and possibly return them here
|
|
195
|
+
assert(!m_customComponent);
|
|
196
|
+
return winrt::make<winrt::Microsoft::ReactNative::implementation::ImageProps>(viewProps());
|
|
198
197
|
}
|
|
199
198
|
|
|
200
199
|
void ImageComponentView::OnRenderingDeviceLost() noexcept {
|
|
@@ -203,7 +202,7 @@ void ImageComponentView::OnRenderingDeviceLost() noexcept {
|
|
|
203
202
|
}
|
|
204
203
|
|
|
205
204
|
bool ImageComponentView::themeEffectsImage() const noexcept {
|
|
206
|
-
return
|
|
205
|
+
return viewProps()->backgroundColor || isColorMeaningful(imageProps().tintColor);
|
|
207
206
|
}
|
|
208
207
|
|
|
209
208
|
void ImageComponentView::onThemeChanged() noexcept {
|
|
@@ -218,7 +217,7 @@ void ImageComponentView::ensureDrawingSurface() noexcept {
|
|
|
218
217
|
assert(m_reactContext.UIDispatcher().HasThreadAccess());
|
|
219
218
|
|
|
220
219
|
if (!m_imageResponseImage) {
|
|
221
|
-
|
|
220
|
+
Visual().as<Experimental::ISpriteVisual>().Brush(nullptr);
|
|
222
221
|
return;
|
|
223
222
|
}
|
|
224
223
|
|
|
@@ -230,18 +229,18 @@ void ImageComponentView::ensureDrawingSurface() noexcept {
|
|
|
230
229
|
if (!m_drawingSurface && m_imageResponseImage->m_wicbmp) {
|
|
231
230
|
winrt::Windows::Foundation::Size drawingSurfaceSize{static_cast<float>(width), static_cast<float>(height)};
|
|
232
231
|
|
|
233
|
-
const auto
|
|
232
|
+
const auto &imgProps = imageProps();
|
|
234
233
|
const auto frame{m_layoutMetrics.getContentFrame().size};
|
|
235
234
|
|
|
236
|
-
if (
|
|
235
|
+
if (imgProps.resizeMode == facebook::react::ImageResizeMode::Repeat) {
|
|
237
236
|
drawingSurfaceSize = {
|
|
238
237
|
frame.width * m_layoutMetrics.pointScaleFactor, frame.height * m_layoutMetrics.pointScaleFactor};
|
|
239
|
-
} else if (
|
|
238
|
+
} else if (imgProps.blurRadius > 0) {
|
|
240
239
|
// https://learn.microsoft.com/en-us/windows/win32/direct2d/gaussian-blur#output-bitmap
|
|
241
240
|
// The following equation that can be used to compute the output bitmap:
|
|
242
241
|
// Output bitmap growth (X and Y) = (StandardDeviation(DIPs)*3 + StandardDeviation(DIPs)*3)*((User DPI)/96)
|
|
243
242
|
// Where StandardDeviation(DIPs)*3 is equivalent to the blur radius.
|
|
244
|
-
const auto bmpGrowth{
|
|
243
|
+
const auto bmpGrowth{imgProps.blurRadius * 2 * m_layoutMetrics.pointScaleFactor};
|
|
245
244
|
drawingSurfaceSize = {drawingSurfaceSize.Width + bmpGrowth, drawingSurfaceSize.Height + bmpGrowth};
|
|
246
245
|
}
|
|
247
246
|
|
|
@@ -252,7 +251,7 @@ void ImageComponentView::ensureDrawingSurface() noexcept {
|
|
|
252
251
|
|
|
253
252
|
DrawImage();
|
|
254
253
|
|
|
255
|
-
switch (
|
|
254
|
+
switch (imgProps.resizeMode) {
|
|
256
255
|
case facebook::react::ImageResizeMode::Stretch:
|
|
257
256
|
m_drawingSurface.Stretch(winrt::Microsoft::ReactNative::Composition::Experimental::CompositionStretch::Fill);
|
|
258
257
|
break;
|
|
@@ -281,9 +280,10 @@ void ImageComponentView::ensureDrawingSurface() noexcept {
|
|
|
281
280
|
assert(false);
|
|
282
281
|
}
|
|
283
282
|
|
|
284
|
-
|
|
283
|
+
Visual().as<Experimental::ISpriteVisual>().Brush(m_drawingSurface);
|
|
285
284
|
} else if (m_imageResponseImage->m_brushFactory) {
|
|
286
|
-
|
|
285
|
+
Visual().as<Experimental::ISpriteVisual>().Brush(
|
|
286
|
+
m_imageResponseImage->m_brushFactory(m_reactContext.Handle(), m_compContext));
|
|
287
287
|
}
|
|
288
288
|
}
|
|
289
289
|
|
|
@@ -310,15 +310,15 @@ void ImageComponentView::DrawImage() noexcept {
|
|
|
310
310
|
d2dDeviceContext->CreateBitmapFromWicBitmap(m_imageResponseImage->m_wicbmp.get(), nullptr, bitmap.put()));
|
|
311
311
|
|
|
312
312
|
d2dDeviceContext->Clear(D2D1::ColorF(D2D1::ColorF::Black, 0.0f));
|
|
313
|
-
if (
|
|
314
|
-
d2dDeviceContext->Clear(theme()->D2DColor(*
|
|
313
|
+
if (viewProps()->backgroundColor) {
|
|
314
|
+
d2dDeviceContext->Clear(theme()->D2DColor(*viewProps()->backgroundColor));
|
|
315
315
|
}
|
|
316
316
|
|
|
317
|
-
const auto
|
|
317
|
+
const auto &imgProps = imageProps();
|
|
318
318
|
|
|
319
319
|
bool useEffects{
|
|
320
|
-
|
|
321
|
-
|
|
320
|
+
imgProps.blurRadius > 0 || isColorMeaningful(imgProps.tintColor) ||
|
|
321
|
+
imgProps.resizeMode == facebook::react::ImageResizeMode::Repeat};
|
|
322
322
|
|
|
323
323
|
if (useEffects) {
|
|
324
324
|
winrt::com_ptr<ID2D1Effect> bitmapEffects;
|
|
@@ -326,23 +326,22 @@ void ImageComponentView::DrawImage() noexcept {
|
|
|
326
326
|
winrt::check_hresult(
|
|
327
327
|
bitmapEffects->SetValue(D2D1_BITMAPSOURCE_PROP_WIC_BITMAP_SOURCE, m_imageResponseImage->m_wicbmp.get()));
|
|
328
328
|
|
|
329
|
-
if (
|
|
329
|
+
if (imgProps.blurRadius > 0) {
|
|
330
330
|
winrt::com_ptr<ID2D1Effect> gaussianBlurEffect;
|
|
331
331
|
winrt::check_hresult(d2dDeviceContext->CreateEffect(CLSID_D2D1GaussianBlur, gaussianBlurEffect.put()));
|
|
332
332
|
// https://learn.microsoft.com/en-us/windows/win32/direct2d/gaussian-blur#effect-properties
|
|
333
333
|
// You can compute the blur radius of the kernel by multiplying the standard deviation by 3 (radius multiplier).
|
|
334
334
|
constexpr float radiusMultiplier = 3;
|
|
335
335
|
winrt::check_hresult(gaussianBlurEffect->SetValue(
|
|
336
|
-
D2D1_GAUSSIANBLUR_PROP_STANDARD_DEVIATION, (
|
|
336
|
+
D2D1_GAUSSIANBLUR_PROP_STANDARD_DEVIATION, (imgProps.blurRadius) / radiusMultiplier));
|
|
337
337
|
gaussianBlurEffect->SetInputEffect(0, bitmapEffects.get());
|
|
338
338
|
bitmapEffects.copy_from(gaussianBlurEffect.get());
|
|
339
339
|
}
|
|
340
340
|
|
|
341
|
-
if (isColorMeaningful(
|
|
341
|
+
if (isColorMeaningful(imgProps.tintColor)) {
|
|
342
342
|
winrt::com_ptr<ID2D1Effect> tintColorEffect;
|
|
343
343
|
winrt::check_hresult(d2dDeviceContext->CreateEffect(CLSID_D2D1Flood, tintColorEffect.put()));
|
|
344
|
-
winrt::check_hresult(
|
|
345
|
-
tintColorEffect->SetValue(D2D1_FLOOD_PROP_COLOR, theme()->D2DColor(*imageProps->tintColor)));
|
|
344
|
+
winrt::check_hresult(tintColorEffect->SetValue(D2D1_FLOOD_PROP_COLOR, theme()->D2DColor(*imgProps.tintColor)));
|
|
346
345
|
|
|
347
346
|
winrt::com_ptr<ID2D1Effect> compositeEffect;
|
|
348
347
|
winrt::check_hresult(d2dDeviceContext->CreateEffect(CLSID_D2D1Composite, compositeEffect.put()));
|
|
@@ -353,7 +352,7 @@ void ImageComponentView::DrawImage() noexcept {
|
|
|
353
352
|
bitmapEffects.copy_from(compositeEffect.get());
|
|
354
353
|
}
|
|
355
354
|
|
|
356
|
-
if (
|
|
355
|
+
if (imgProps.resizeMode == facebook::react::ImageResizeMode::Repeat) {
|
|
357
356
|
winrt::com_ptr<ID2D1Effect> borderEffect;
|
|
358
357
|
winrt::check_hresult(d2dDeviceContext->CreateEffect(CLSID_D2D1Border, borderEffect.put()));
|
|
359
358
|
winrt::check_hresult(borderEffect->SetValue(D2D1_BORDER_PROP_EDGE_MODE_X, D2D1_BORDER_EDGE_MODE_WRAP));
|
|
@@ -386,51 +385,6 @@ void ImageComponentView::DrawImage() noexcept {
|
|
|
386
385
|
}
|
|
387
386
|
}
|
|
388
387
|
|
|
389
|
-
void ImageComponentView::prepareForRecycle() noexcept {}
|
|
390
|
-
|
|
391
|
-
facebook::react::SharedViewProps ImageComponentView::viewProps() noexcept {
|
|
392
|
-
return m_props;
|
|
393
|
-
}
|
|
394
|
-
|
|
395
|
-
facebook::react::Tag ImageComponentView::hitTest(
|
|
396
|
-
facebook::react::Point pt,
|
|
397
|
-
facebook::react::Point &localPt,
|
|
398
|
-
bool ignorePointerEvents) const noexcept {
|
|
399
|
-
facebook::react::Point ptLocal{pt.x - m_layoutMetrics.frame.origin.x, pt.y - m_layoutMetrics.frame.origin.y};
|
|
400
|
-
|
|
401
|
-
facebook::react::Tag targetTag;
|
|
402
|
-
|
|
403
|
-
if ((ignorePointerEvents || m_props->pointerEvents == facebook::react::PointerEventsMode::Auto ||
|
|
404
|
-
m_props->pointerEvents == facebook::react::PointerEventsMode::BoxNone) &&
|
|
405
|
-
anyHitTestHelper(targetTag, ptLocal, localPt))
|
|
406
|
-
return targetTag;
|
|
407
|
-
|
|
408
|
-
if ((ignorePointerEvents || m_props->pointerEvents == facebook::react::PointerEventsMode::Auto ||
|
|
409
|
-
m_props->pointerEvents == facebook::react::PointerEventsMode::BoxOnly) &&
|
|
410
|
-
ptLocal.x >= 0 && ptLocal.x <= m_layoutMetrics.frame.size.width && ptLocal.y >= 0 &&
|
|
411
|
-
ptLocal.y <= m_layoutMetrics.frame.size.height) {
|
|
412
|
-
localPt = ptLocal;
|
|
413
|
-
return Tag();
|
|
414
|
-
}
|
|
415
|
-
|
|
416
|
-
return -1;
|
|
417
|
-
}
|
|
418
|
-
|
|
419
|
-
void ImageComponentView::ensureVisual() noexcept {
|
|
420
|
-
if (!m_visual) {
|
|
421
|
-
m_visual = m_compContext.CreateSpriteVisual();
|
|
422
|
-
OuterVisual().InsertAt(m_visual, 0);
|
|
423
|
-
}
|
|
424
|
-
}
|
|
425
|
-
|
|
426
|
-
winrt::Microsoft::ReactNative::Composition::Experimental::IVisual ImageComponentView::Visual() const noexcept {
|
|
427
|
-
return m_visual;
|
|
428
|
-
}
|
|
429
|
-
|
|
430
|
-
bool ImageComponentView::focusable() const noexcept {
|
|
431
|
-
return m_props->focusable;
|
|
432
|
-
}
|
|
433
|
-
|
|
434
388
|
std::string ImageComponentView::DefaultControlType() const noexcept {
|
|
435
389
|
return "image";
|
|
436
390
|
}
|
|
@@ -29,8 +29,8 @@ namespace winrt::Microsoft::ReactNative::Composition::implementation {
|
|
|
29
29
|
|
|
30
30
|
struct WindowsImageResponseObserver;
|
|
31
31
|
|
|
32
|
-
struct ImageComponentView : ImageComponentViewT<ImageComponentView,
|
|
33
|
-
using Super = ImageComponentViewT<ImageComponentView,
|
|
32
|
+
struct ImageComponentView : ImageComponentViewT<ImageComponentView, ViewComponentView> {
|
|
33
|
+
using Super = ImageComponentViewT<ImageComponentView, ViewComponentView>;
|
|
34
34
|
|
|
35
35
|
[[nodiscard]] static winrt::Microsoft::ReactNative::ComponentView Create(
|
|
36
36
|
const winrt::Microsoft::ReactNative::Composition::Experimental::ICompositionContext &compContext,
|
|
@@ -47,25 +47,25 @@ struct ImageComponentView : ImageComponentViewT<ImageComponentView, ComponentVie
|
|
|
47
47
|
override;
|
|
48
48
|
void updateState(facebook::react::State::Shared const &state, facebook::react::State::Shared const &oldState) noexcept
|
|
49
49
|
override;
|
|
50
|
-
void updateLayoutMetrics(
|
|
51
|
-
facebook::react::LayoutMetrics const &layoutMetrics,
|
|
52
|
-
facebook::react::LayoutMetrics const &oldLayoutMetrics) noexcept override;
|
|
53
|
-
void prepareForRecycle() noexcept override;
|
|
54
|
-
facebook::react::SharedViewProps viewProps() noexcept override;
|
|
55
50
|
void OnRenderingDeviceLost() noexcept override;
|
|
56
51
|
void onThemeChanged() noexcept override;
|
|
57
52
|
|
|
58
|
-
facebook::react::Tag hitTest(facebook::react::Point pt, facebook::react::Point &localPt, bool ignorePointerEvents)
|
|
59
|
-
const noexcept override;
|
|
60
|
-
winrt::Microsoft::ReactNative::Composition::Experimental::IVisual Visual() const noexcept override;
|
|
61
|
-
bool focusable() const noexcept override;
|
|
62
53
|
virtual std::string DefaultControlType() const noexcept;
|
|
54
|
+
static facebook::react::SharedViewProps defaultProps() noexcept;
|
|
63
55
|
|
|
64
56
|
ImageComponentView(
|
|
65
57
|
const winrt::Microsoft::ReactNative::Composition::Experimental::ICompositionContext &compContext,
|
|
66
58
|
facebook::react::Tag tag,
|
|
67
59
|
winrt::Microsoft::ReactNative::ReactContext const &reactContext);
|
|
68
60
|
|
|
61
|
+
const facebook::react::ImageProps &imageProps() const noexcept;
|
|
62
|
+
// TODO try to change to ViewProps
|
|
63
|
+
winrt::Microsoft::ReactNative::ImageProps ImageProps() noexcept;
|
|
64
|
+
winrt::Microsoft::ReactNative::ImageProps ViewProps() noexcept;
|
|
65
|
+
|
|
66
|
+
protected:
|
|
67
|
+
winrt::Microsoft::ReactNative::ViewProps ViewPropsInner() noexcept override;
|
|
68
|
+
|
|
69
69
|
private:
|
|
70
70
|
struct WindowsImageResponseObserver : facebook::react::ImageResponseObserver {
|
|
71
71
|
public:
|
|
@@ -78,7 +78,6 @@ struct ImageComponentView : ImageComponentViewT<ImageComponentView, ComponentVie
|
|
|
78
78
|
winrt::com_ptr<ImageComponentView> m_image;
|
|
79
79
|
};
|
|
80
80
|
|
|
81
|
-
void ensureVisual() noexcept;
|
|
82
81
|
void ensureDrawingSurface() noexcept;
|
|
83
82
|
void DrawImage() noexcept;
|
|
84
83
|
|
|
@@ -90,9 +89,6 @@ struct ImageComponentView : ImageComponentViewT<ImageComponentView, ComponentVie
|
|
|
90
89
|
facebook::react::ImageShadowNode::ConcreteState::Shared const &state) noexcept;
|
|
91
90
|
bool themeEffectsImage() const noexcept;
|
|
92
91
|
|
|
93
|
-
std::shared_ptr<const facebook::react::ImageProps> m_props;
|
|
94
|
-
|
|
95
|
-
winrt::Microsoft::ReactNative::Composition::Experimental::ISpriteVisual m_visual{nullptr};
|
|
96
92
|
winrt::Microsoft::ReactNative::Composition::Experimental::IDrawingSurfaceBrush m_drawingSurface;
|
|
97
93
|
std::shared_ptr<ImageResponseImage> m_imageResponseImage;
|
|
98
94
|
std::shared_ptr<WindowsImageResponseObserver> m_imageResponseObserver;
|