react-native-unistyles 3.4.0 → 3.5.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/README.md +23 -7
- package/android/build.gradle +12 -1
- package/android/src/main/cxx/NativeUnistylesModule.cpp +8 -4
- package/android/src/main/cxx/NativeUnistylesModule.h +5 -1
- package/components/native/ActivityIndicator/package.json +1 -1
- package/cxx/common/UnistylesConstants.h +1 -0
- package/cxx/converters/TransformOriginConverter.cpp +106 -0
- package/cxx/core/StyleSheetRegistry.cpp +9 -9
- package/cxx/core/StyleSheetRegistry.h +3 -3
- package/cxx/core/UnistyleWrapper.h +13 -1
- package/cxx/core/UnistylesRegistry.cpp +102 -18
- package/cxx/core/UnistylesRegistry.h +42 -5
- package/cxx/hybridObjects/HybridShadowRegistry.cpp +124 -4
- package/cxx/hybridObjects/HybridShadowRegistry.h +20 -0
- package/cxx/hybridObjects/HybridStyleSheet.cpp +20 -12
- package/cxx/hybridObjects/HybridUnistylesRuntime.cpp +11 -1
- package/cxx/hybridObjects/HybridUnistylesRuntime.h +4 -2
- package/cxx/parser/Parser.cpp +29 -1
- package/cxx/parser/Parser.h +1 -0
- package/cxx/shadowTree/NativeProps.h +46 -2
- package/cxx/shadowTree/ShadowTrafficController.h +4 -0
- package/cxx/shadowTree/ShadowTreeDiagnostics.cpp +339 -0
- package/cxx/shadowTree/ShadowTreeDiagnostics.h +18 -0
- package/cxx/shadowTree/ShadowTreeManager.cpp +7 -1
- package/cxx/shadowTree/ShadowTreeManager.h +1 -1
- package/diagnostics/package.json +6 -0
- package/ios/UnistylesModuleOnLoad.mm +9 -3
- package/lib/commonjs/components/native/ActivityIndicator.native.js +10 -0
- package/lib/commonjs/components/native/ActivityIndicator.native.js.map +1 -0
- package/lib/commonjs/components/native/NativeText.js +6 -0
- package/lib/commonjs/components/native/NativeText.js.map +1 -1
- package/lib/commonjs/components/native/NativeText.native.js +17 -1
- package/lib/commonjs/components/native/NativeText.native.js.map +1 -1
- package/lib/commonjs/components/native/NativeView.js +6 -0
- package/lib/commonjs/components/native/NativeView.js.map +1 -1
- package/lib/commonjs/components/native/NativeView.native.js +22 -3
- package/lib/commonjs/components/native/NativeView.native.js.map +1 -1
- package/lib/commonjs/components/native/Pressable.js +7 -3
- package/lib/commonjs/components/native/Pressable.js.map +1 -1
- package/lib/commonjs/components/native/TouchableHighlight.native.js +10 -0
- package/lib/commonjs/components/native/TouchableHighlight.native.js.map +1 -0
- package/lib/commonjs/core/createUnistylesActivityIndicator.js +41 -0
- package/lib/commonjs/core/createUnistylesActivityIndicator.js.map +1 -0
- package/lib/commonjs/core/createUnistylesElement.js +59 -14
- package/lib/commonjs/core/createUnistylesElement.js.map +1 -1
- package/lib/commonjs/core/createUnistylesTouchableHighlight.js +58 -0
- package/lib/commonjs/core/createUnistylesTouchableHighlight.js.map +1 -0
- package/lib/commonjs/core/index.js +14 -0
- package/lib/commonjs/core/index.js.map +1 -1
- package/lib/commonjs/diagnostics/index.js +13 -0
- package/lib/commonjs/diagnostics/index.js.map +1 -0
- package/lib/commonjs/diagnostics/types.js +2 -0
- package/lib/commonjs/diagnostics/types.js.map +1 -0
- package/lib/commonjs/diagnostics/verify.js +19 -0
- package/lib/commonjs/diagnostics/verify.js.map +1 -0
- package/lib/commonjs/diagnostics/verify.native.js +12 -0
- package/lib/commonjs/diagnostics/verify.native.js.map +1 -0
- package/lib/commonjs/index.js +38 -0
- package/lib/commonjs/index.js.map +1 -1
- package/lib/commonjs/mocks.js +41 -0
- package/lib/commonjs/mocks.js.map +1 -1
- package/lib/commonjs/reanimated/variant/useUpdateVariantColor.native.js +8 -0
- package/lib/commonjs/reanimated/variant/useUpdateVariantColor.native.js.map +1 -1
- package/lib/commonjs/specs/ShadowRegistry/index.js +97 -1
- package/lib/commonjs/specs/ShadowRegistry/index.js.map +1 -1
- package/lib/commonjs/specs/StyleSheet/index.js +5 -1
- package/lib/commonjs/specs/StyleSheet/index.js.map +1 -1
- package/lib/commonjs/specs/UnistylesRuntime/index.js.map +1 -1
- package/lib/commonjs/web/registry.js +3 -0
- package/lib/commonjs/web/registry.js.map +1 -1
- package/lib/module/components/native/ActivityIndicator.native.js +6 -0
- package/lib/module/components/native/ActivityIndicator.native.js.map +1 -0
- package/lib/module/components/native/NativeText.js +1 -1
- package/lib/module/components/native/NativeText.js.map +1 -1
- package/lib/module/components/native/NativeText.native.js +15 -1
- package/lib/module/components/native/NativeText.native.js.map +1 -1
- package/lib/module/components/native/NativeView.js +1 -0
- package/lib/module/components/native/NativeView.js.map +1 -1
- package/lib/module/components/native/NativeView.native.js +19 -2
- package/lib/module/components/native/NativeView.native.js.map +1 -1
- package/lib/module/components/native/Pressable.js +7 -3
- package/lib/module/components/native/Pressable.js.map +1 -1
- package/lib/module/components/native/TouchableHighlight.native.js +6 -0
- package/lib/module/components/native/TouchableHighlight.native.js.map +1 -0
- package/lib/module/core/createUnistylesActivityIndicator.js +35 -0
- package/lib/module/core/createUnistylesActivityIndicator.js.map +1 -0
- package/lib/module/core/createUnistylesElement.js +58 -13
- package/lib/module/core/createUnistylesElement.js.map +1 -1
- package/lib/module/core/createUnistylesTouchableHighlight.js +52 -0
- package/lib/module/core/createUnistylesTouchableHighlight.js.map +1 -0
- package/lib/module/core/index.js +2 -0
- package/lib/module/core/index.js.map +1 -1
- package/lib/module/diagnostics/index.js +5 -0
- package/lib/module/diagnostics/index.js.map +1 -0
- package/lib/module/diagnostics/types.js +2 -0
- package/lib/module/diagnostics/types.js.map +1 -0
- package/lib/module/diagnostics/verify.js +14 -0
- package/lib/module/diagnostics/verify.js.map +1 -0
- package/lib/module/diagnostics/verify.native.js +8 -0
- package/lib/module/diagnostics/verify.native.js.map +1 -0
- package/lib/module/index.js +2 -0
- package/lib/module/index.js.map +1 -1
- package/lib/module/mocks.js +41 -0
- package/lib/module/mocks.js.map +1 -1
- package/lib/module/reanimated/variant/useUpdateVariantColor.native.js +9 -1
- package/lib/module/reanimated/variant/useUpdateVariantColor.native.js.map +1 -1
- package/lib/module/specs/ShadowRegistry/index.js +97 -1
- package/lib/module/specs/ShadowRegistry/index.js.map +1 -1
- package/lib/module/specs/StyleSheet/index.js +6 -1
- package/lib/module/specs/StyleSheet/index.js.map +1 -1
- package/lib/module/specs/UnistylesRuntime/index.js.map +1 -1
- package/lib/module/web/registry.js +3 -0
- package/lib/module/web/registry.js.map +1 -1
- package/lib/typescript/src/components/native/ActivityIndicator.native.d.ts +2 -0
- package/lib/typescript/src/components/native/ActivityIndicator.native.d.ts.map +1 -0
- package/lib/typescript/src/components/native/NativeText.d.ts +1 -1
- package/lib/typescript/src/components/native/NativeText.d.ts.map +1 -1
- package/lib/typescript/src/components/native/NativeText.native.d.ts.map +1 -1
- package/lib/typescript/src/components/native/NativeView.d.ts +1 -0
- package/lib/typescript/src/components/native/NativeView.d.ts.map +1 -1
- package/lib/typescript/src/components/native/NativeView.native.d.ts +2 -2
- package/lib/typescript/src/components/native/NativeView.native.d.ts.map +1 -1
- package/lib/typescript/src/components/native/Pressable.d.ts.map +1 -1
- package/lib/typescript/src/components/native/TouchableHighlight.native.d.ts +2 -0
- package/lib/typescript/src/components/native/TouchableHighlight.native.d.ts.map +1 -0
- package/lib/typescript/src/core/createUnistylesActivityIndicator.d.ts +3 -0
- package/lib/typescript/src/core/createUnistylesActivityIndicator.d.ts.map +1 -0
- package/lib/typescript/src/core/createUnistylesElement.d.ts.map +1 -1
- package/lib/typescript/src/core/createUnistylesTouchableHighlight.d.ts +3 -0
- package/lib/typescript/src/core/createUnistylesTouchableHighlight.d.ts.map +1 -0
- package/lib/typescript/src/core/index.d.ts +2 -0
- package/lib/typescript/src/core/index.d.ts.map +1 -1
- package/lib/typescript/src/core/useUnistyles.d.ts +1 -1
- package/lib/typescript/src/diagnostics/index.d.ts +3 -0
- package/lib/typescript/src/diagnostics/index.d.ts.map +1 -0
- package/lib/typescript/src/diagnostics/types.d.ts +19 -0
- package/lib/typescript/src/diagnostics/types.d.ts.map +1 -0
- package/lib/typescript/src/diagnostics/verify.d.ts +3 -0
- package/lib/typescript/src/diagnostics/verify.d.ts.map +1 -0
- package/lib/typescript/src/diagnostics/verify.native.d.ts +3 -0
- package/lib/typescript/src/diagnostics/verify.native.d.ts.map +1 -0
- package/lib/typescript/src/index.d.ts +4 -1
- package/lib/typescript/src/index.d.ts.map +1 -1
- package/lib/typescript/src/reanimated/variant/useUpdateVariantColor.native.d.ts.map +1 -1
- package/lib/typescript/src/specs/ShadowRegistry/index.d.ts +5 -1
- package/lib/typescript/src/specs/ShadowRegistry/index.d.ts.map +1 -1
- package/lib/typescript/src/specs/ShadowRegistry/types.d.ts +3 -0
- package/lib/typescript/src/specs/ShadowRegistry/types.d.ts.map +1 -1
- package/lib/typescript/src/specs/StyleSheet/index.d.ts +4 -1
- package/lib/typescript/src/specs/StyleSheet/index.d.ts.map +1 -1
- package/lib/typescript/src/specs/UnistylesRuntime/index.d.ts +2 -2
- package/lib/typescript/src/specs/UnistylesRuntime/index.d.ts.map +1 -1
- package/lib/typescript/src/types/breakpoints.d.ts +1 -1
- package/lib/typescript/src/types/breakpoints.d.ts.map +1 -1
- package/lib/typescript/src/types/stylesheet.d.ts +3 -3
- package/lib/typescript/src/types/stylesheet.d.ts.map +1 -1
- package/lib/typescript/src/web/registry.d.ts.map +1 -1
- package/package.json +9 -1
- package/plugin/index.d.ts +4 -4
- package/plugin/index.js +21 -5
- package/src/components/native/ActivityIndicator.native.tsx +5 -0
- package/src/components/native/NativeText.native.tsx +18 -1
- package/src/components/native/NativeText.tsx +1 -1
- package/src/components/native/NativeView.native.tsx +22 -2
- package/src/components/native/NativeView.tsx +2 -0
- package/src/components/native/Pressable.tsx +8 -3
- package/src/components/native/TouchableHighlight.native.tsx +5 -0
- package/src/core/createUnistylesActivityIndicator.tsx +47 -0
- package/src/core/createUnistylesElement.tsx +45 -14
- package/src/core/createUnistylesTouchableHighlight.tsx +69 -0
- package/src/core/index.ts +2 -0
- package/src/diagnostics/index.ts +3 -0
- package/src/diagnostics/types.ts +25 -0
- package/src/diagnostics/verify.native.ts +7 -0
- package/src/diagnostics/verify.ts +13 -0
- package/src/index.ts +4 -1
- package/src/mocks.ts +41 -0
- package/src/reanimated/variant/useUpdateVariantColor.native.ts +7 -1
- package/src/specs/ShadowRegistry/index.ts +128 -1
- package/src/specs/ShadowRegistry/types.ts +3 -0
- package/src/specs/StyleSheet/index.ts +10 -2
- package/src/specs/UnistylesRuntime/index.ts +7 -2
- package/src/types/breakpoints.ts +5 -3
- package/src/types/stylesheet.ts +3 -3
- package/src/web/registry.ts +3 -0
|
@@ -6,6 +6,11 @@ using namespace facebook::react;
|
|
|
6
6
|
jsi::Value HybridShadowRegistry::link(jsi::Runtime &rt, const jsi::Value &thisValue, const jsi::Value *args, size_t count) {
|
|
7
7
|
helpers::assertThat(rt, count == 2, "Unistyles: Invalid babel transform 'ShadowRegistry link' expected 2 arguments.");
|
|
8
8
|
|
|
9
|
+
// runtime was replaced, registry belongs to the next one
|
|
10
|
+
if (!this->_unistylesRuntime->ownsRegistry()) {
|
|
11
|
+
return jsi::Value::undefined();
|
|
12
|
+
}
|
|
13
|
+
|
|
9
14
|
auto shadowNodeWrapper = getShadowNodeFromRef(rt, args[0]);
|
|
10
15
|
|
|
11
16
|
std::vector<core::Unistyle::Shared> unistyleWrappers = core::unistyleFromValue(rt, args[1]);
|
|
@@ -97,28 +102,69 @@ jsi::Value HybridShadowRegistry::link(jsi::Runtime &rt, const jsi::Value &thisVa
|
|
|
97
102
|
}
|
|
98
103
|
|
|
99
104
|
std::optional<folly::dynamic> initialScopedUpdate;
|
|
105
|
+
bool shouldCommit = false;
|
|
100
106
|
|
|
101
|
-
if (scopedTheme.has_value()
|
|
102
|
-
initialScopedUpdate = parser.
|
|
107
|
+
if (scopedTheme.has_value()) {
|
|
108
|
+
initialScopedUpdate = parser.parseStylesToShadowTreeUpdates(rt, unistylesData);
|
|
109
|
+
shouldCommit = shadow::hasNativeProps(&shadowNodeWrapper->getFamily());
|
|
110
|
+
} else if (shadow::hasNativeProps(&shadowNodeWrapper->getFamily())) {
|
|
111
|
+
auto update = parser.parseStylesToShadowTreeUpdates(rt, unistylesData);
|
|
112
|
+
|
|
113
|
+
if (shadow::hasOutdatedNativeProps(&shadowNodeWrapper->getFamily(), update)) {
|
|
114
|
+
initialScopedUpdate = std::move(update);
|
|
115
|
+
shouldCommit = true;
|
|
116
|
+
}
|
|
103
117
|
}
|
|
104
118
|
|
|
105
119
|
registry.linkShadowNodeWithUnistyle(
|
|
106
120
|
rt,
|
|
121
|
+
this->_unistylesRuntime->generation,
|
|
107
122
|
shadowNodeWrapper->getFamilyShared(),
|
|
108
123
|
unistylesData,
|
|
109
124
|
std::move(initialScopedUpdate)
|
|
110
125
|
);
|
|
111
126
|
|
|
112
|
-
if (
|
|
113
|
-
|
|
127
|
+
if (shouldCommit) {
|
|
128
|
+
this->scheduleShadowTreeUpdate(rt);
|
|
114
129
|
}
|
|
115
130
|
|
|
116
131
|
return jsi::Value::undefined();
|
|
117
132
|
}
|
|
118
133
|
|
|
134
|
+
void HybridShadowRegistry::scheduleShadowTreeUpdate(jsi::Runtime& rt) {
|
|
135
|
+
if (this->_isShadowTreeUpdateScheduled->exchange(true)) {
|
|
136
|
+
return;
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
auto isShadowTreeUpdateScheduled = this->_isShadowTreeUpdateScheduled;
|
|
140
|
+
auto unistylesRuntime = this->_unistylesRuntime;
|
|
141
|
+
|
|
142
|
+
rt.queueMicrotask(jsi::Function::createFromHostFunction(
|
|
143
|
+
rt,
|
|
144
|
+
jsi::PropNameID::forAscii(rt, "unistylesUpdateShadowTree"),
|
|
145
|
+
0,
|
|
146
|
+
[isShadowTreeUpdateScheduled, unistylesRuntime](jsi::Runtime& rt, const jsi::Value&, const jsi::Value*, size_t) {
|
|
147
|
+
isShadowTreeUpdateScheduled->store(false);
|
|
148
|
+
|
|
149
|
+
// pending updates belong to the runtime that replaced this one
|
|
150
|
+
if (!unistylesRuntime->ownsRegistry()) {
|
|
151
|
+
return jsi::Value::undefined();
|
|
152
|
+
}
|
|
153
|
+
|
|
154
|
+
shadow::ShadowTreeManager::updateShadowTree(rt);
|
|
155
|
+
|
|
156
|
+
return jsi::Value::undefined();
|
|
157
|
+
}
|
|
158
|
+
));
|
|
159
|
+
}
|
|
160
|
+
|
|
119
161
|
jsi::Value HybridShadowRegistry::unlink(jsi::Runtime &rt, const jsi::Value &thisValue, const jsi::Value *args, size_t count) {
|
|
120
162
|
helpers::assertThat(rt, count == 1, "Unistyles: Invalid babel transform 'ShadowRegistry unlink' expected 1 argument.");
|
|
121
163
|
|
|
164
|
+
if (!this->_unistylesRuntime->ownsRegistry()) {
|
|
165
|
+
return jsi::Value::undefined();
|
|
166
|
+
}
|
|
167
|
+
|
|
122
168
|
auto shadowNodeWrapper = getShadowNodeFromRef(rt, args[0]);
|
|
123
169
|
|
|
124
170
|
auto& registry = core::UnistylesRegistry::get();
|
|
@@ -131,6 +177,10 @@ jsi::Value HybridShadowRegistry::unlink(jsi::Runtime &rt, const jsi::Value &this
|
|
|
131
177
|
jsi::Value HybridShadowRegistry::suspend(jsi::Runtime &rt, const jsi::Value &thisValue, const jsi::Value *args, size_t count) {
|
|
132
178
|
helpers::assertThat(rt, count == 1, "Unistyles: Invalid babel transform 'ShadowRegistry suspend' expected 1 argument.");
|
|
133
179
|
|
|
180
|
+
if (!this->_unistylesRuntime->ownsRegistry()) {
|
|
181
|
+
return jsi::Value::undefined();
|
|
182
|
+
}
|
|
183
|
+
|
|
134
184
|
auto shadowNodeWrapper = getShadowNodeFromRef(rt, args[0]);
|
|
135
185
|
auto& registry = core::UnistylesRegistry::get();
|
|
136
186
|
|
|
@@ -140,6 +190,10 @@ jsi::Value HybridShadowRegistry::suspend(jsi::Runtime &rt, const jsi::Value &thi
|
|
|
140
190
|
}
|
|
141
191
|
|
|
142
192
|
jsi::Value HybridShadowRegistry::flush(jsi::Runtime &rt, const jsi::Value &thisValue, const jsi::Value *args, size_t count) {
|
|
193
|
+
if (!this->_unistylesRuntime->ownsRegistry()) {
|
|
194
|
+
return jsi::Value::undefined();
|
|
195
|
+
}
|
|
196
|
+
|
|
143
197
|
shadow::ShadowTreeManager::updateShadowTree(rt);
|
|
144
198
|
|
|
145
199
|
return jsi::Value::undefined();
|
|
@@ -148,6 +202,10 @@ jsi::Value HybridShadowRegistry::flush(jsi::Runtime &rt, const jsi::Value &thisV
|
|
|
148
202
|
jsi::Value HybridShadowRegistry::setScopedTheme(jsi::Runtime &rt, const jsi::Value &thisValue, const jsi::Value *args, size_t count) {
|
|
149
203
|
helpers::assertThat(rt, count == 1, "Unistyles: setScopedTheme expected 1 argument.");
|
|
150
204
|
|
|
205
|
+
if (!this->_unistylesRuntime->ownsRegistry()) {
|
|
206
|
+
return jsi::Value::undefined();
|
|
207
|
+
}
|
|
208
|
+
|
|
151
209
|
auto& registry = core::UnistylesRegistry::get();
|
|
152
210
|
|
|
153
211
|
if (args[0].isUndefined()) {
|
|
@@ -170,6 +228,68 @@ jsi::Value HybridShadowRegistry::getScopedTheme(jsi::Runtime &rt, const jsi::Val
|
|
|
170
228
|
: jsi::Value::undefined();
|
|
171
229
|
}
|
|
172
230
|
|
|
231
|
+
jsi::Value HybridShadowRegistry::verify(jsi::Runtime &rt, const jsi::Value &thisValue, const jsi::Value *args, size_t count) {
|
|
232
|
+
return shadow::ShadowTreeDiagnostics::verify(rt, this->_unistylesRuntime);
|
|
233
|
+
}
|
|
234
|
+
|
|
235
|
+
jsi::Value HybridShadowRegistry::takeCommittedTags(jsi::Runtime &rt, const jsi::Value &thisValue, const jsi::Value *args, size_t count) {
|
|
236
|
+
auto tags = core::UnistylesRegistry::get().takeCommittedTags();
|
|
237
|
+
auto result = jsi::Array(rt, tags.size());
|
|
238
|
+
|
|
239
|
+
for (size_t i = 0; i < tags.size(); i++) {
|
|
240
|
+
result.setValueAtIndex(rt, i, jsi::Value(static_cast<double>(tags[i])));
|
|
241
|
+
}
|
|
242
|
+
|
|
243
|
+
return result;
|
|
244
|
+
}
|
|
245
|
+
|
|
246
|
+
jsi::Value HybridShadowRegistry::refreshReactNodes(jsi::Runtime &rt, const jsi::Value &thisValue, const jsi::Value *args, size_t count) {
|
|
247
|
+
helpers::assertThat(rt, count == 1 && args[0].isObject(), "Unistyles: refreshReactNodes expected to be called with an array of shadow nodes.");
|
|
248
|
+
|
|
249
|
+
auto nodes = args[0].asObject(rt).asArray(rt);
|
|
250
|
+
std::unordered_map<SurfaceId, std::shared_ptr<const RootShadowNode>> roots;
|
|
251
|
+
|
|
252
|
+
UIManagerBinding::getBinding(rt)->getUIManager().getShadowTreeRegistry().enumerate([&roots](const ShadowTree& shadowTree, bool&) {
|
|
253
|
+
roots.emplace(shadowTree.getSurfaceId(), shadowTree.getCurrentRevision().rootShadowNode);
|
|
254
|
+
});
|
|
255
|
+
|
|
256
|
+
for (size_t i = 0; i < nodes.size(rt); i++) {
|
|
257
|
+
auto node = nodes.getValueAtIndex(rt, i);
|
|
258
|
+
|
|
259
|
+
if (!node.isObject() || !node.asObject(rt).hasNativeState<ShadowNodeWrapper>(rt)) {
|
|
260
|
+
continue;
|
|
261
|
+
}
|
|
262
|
+
|
|
263
|
+
auto wrapper = node.asObject(rt).getNativeState<ShadowNodeWrapper>(rt);
|
|
264
|
+
|
|
265
|
+
// never committed, React cloned it in a render that isn't committed yet (eg. a transition that yielded)
|
|
266
|
+
// it holds what React rendered since, pointing it at the committed node would drop that
|
|
267
|
+
if (!wrapper->shadowNode->getHasBeenPromoted()) {
|
|
268
|
+
continue;
|
|
269
|
+
}
|
|
270
|
+
|
|
271
|
+
const auto& family = wrapper->shadowNode->getFamily();
|
|
272
|
+
auto rootIt = roots.find(family.getSurfaceId());
|
|
273
|
+
|
|
274
|
+
if (rootIt == roots.end()) {
|
|
275
|
+
continue;
|
|
276
|
+
}
|
|
277
|
+
|
|
278
|
+
auto ancestors = family.getAncestors(*rootIt->second);
|
|
279
|
+
|
|
280
|
+
// frozen nodes are not in the committed tree, nativeProps_DEPRECATED covers them
|
|
281
|
+
if (ancestors.empty()) {
|
|
282
|
+
continue;
|
|
283
|
+
}
|
|
284
|
+
|
|
285
|
+
const auto& [parent, index] = ancestors.back();
|
|
286
|
+
|
|
287
|
+
wrapper->shadowNode = parent.get().getChildren().at(index);
|
|
288
|
+
}
|
|
289
|
+
|
|
290
|
+
return jsi::Value::undefined();
|
|
291
|
+
}
|
|
292
|
+
|
|
173
293
|
std::shared_ptr<const core::ShadowNode> HybridShadowRegistry::getShadowNodeFromRef(jsi::Runtime& rt, const jsi::Value& maybeRef) {
|
|
174
294
|
return Bridging<std::shared_ptr<const ShadowNode>>::fromJs(rt, maybeRef);
|
|
175
295
|
}
|
|
@@ -6,7 +6,9 @@
|
|
|
6
6
|
#include "UnistylesState.h"
|
|
7
7
|
#include "UnistylesRegistry.h"
|
|
8
8
|
#include "ShadowTreeManager.h"
|
|
9
|
+
#include "ShadowTreeDiagnostics.h"
|
|
9
10
|
#include <cxxreact/ReactNativeVersion.h>
|
|
11
|
+
#include <atomic>
|
|
10
12
|
|
|
11
13
|
namespace margelo::nitro::unistyles {
|
|
12
14
|
|
|
@@ -38,6 +40,18 @@ struct HybridShadowRegistry: public HybridUnistylesShadowRegistrySpec {
|
|
|
38
40
|
const jsi::Value& thisValue,
|
|
39
41
|
const jsi::Value* args,
|
|
40
42
|
size_t count);
|
|
43
|
+
jsi::Value verify(jsi::Runtime& rt,
|
|
44
|
+
const jsi::Value& thisValue,
|
|
45
|
+
const jsi::Value* args,
|
|
46
|
+
size_t count);
|
|
47
|
+
jsi::Value takeCommittedTags(jsi::Runtime& rt,
|
|
48
|
+
const jsi::Value& thisValue,
|
|
49
|
+
const jsi::Value* args,
|
|
50
|
+
size_t count);
|
|
51
|
+
jsi::Value refreshReactNodes(jsi::Runtime& rt,
|
|
52
|
+
const jsi::Value& thisValue,
|
|
53
|
+
const jsi::Value* args,
|
|
54
|
+
size_t count);
|
|
41
55
|
|
|
42
56
|
void loadHybridMethods() override {
|
|
43
57
|
HybridUnistylesShadowRegistrySpec::loadHybridMethods();
|
|
@@ -49,13 +63,19 @@ struct HybridShadowRegistry: public HybridUnistylesShadowRegistrySpec {
|
|
|
49
63
|
prototype.registerRawHybridMethod("flush", 0, &HybridShadowRegistry::flush);
|
|
50
64
|
prototype.registerRawHybridMethod("setScopedTheme", 1, &HybridShadowRegistry::setScopedTheme);
|
|
51
65
|
prototype.registerRawHybridMethod("getScopedTheme", 0, &HybridShadowRegistry::getScopedTheme);
|
|
66
|
+
prototype.registerRawHybridMethod("verify", 0, &HybridShadowRegistry::verify);
|
|
67
|
+
prototype.registerRawHybridMethod("takeCommittedTags", 0, &HybridShadowRegistry::takeCommittedTags);
|
|
68
|
+
prototype.registerRawHybridMethod("refreshReactNodes", 1, &HybridShadowRegistry::refreshReactNodes);
|
|
52
69
|
});
|
|
53
70
|
};
|
|
54
71
|
|
|
55
72
|
std::shared_ptr<const core::ShadowNode> getShadowNodeFromRef(jsi::Runtime& rt, const jsi::Value& maybeRef);
|
|
56
73
|
|
|
57
74
|
private:
|
|
75
|
+
void scheduleShadowTreeUpdate(jsi::Runtime& rt);
|
|
76
|
+
|
|
58
77
|
std::shared_ptr<HybridUnistylesRuntime> _unistylesRuntime;
|
|
78
|
+
std::shared_ptr<std::atomic<bool>> _isShadowTreeUpdateScheduled = std::make_shared<std::atomic<bool>>(false);
|
|
59
79
|
};
|
|
60
80
|
|
|
61
81
|
}
|
|
@@ -16,12 +16,13 @@ double HybridStyleSheet::getHairlineWidth() {
|
|
|
16
16
|
jsi::Value HybridStyleSheet::create(jsi::Runtime& rt, const jsi::Value &thisVal, const jsi::Value *arguments, size_t count) {
|
|
17
17
|
helpers::assertThat(rt, count == 1, "StyleSheet.create expected to be called with one argument.");
|
|
18
18
|
helpers::assertThat(rt, arguments[0].isObject(), "StyleSheet.create expected to be called with object or function.");
|
|
19
|
+
helpers::assertThat(rt, this->_unistylesRuntime->ownsRegistry(), helpers::RUNTIME_REPLACED_ERROR);
|
|
19
20
|
|
|
20
21
|
auto thisStyleSheet = thisVal.asObject(rt);
|
|
21
22
|
auto& registry = core::UnistylesRegistry::get();
|
|
22
23
|
|
|
23
24
|
jsi::Object rawStyleSheet = arguments[0].asObject(rt);
|
|
24
|
-
auto registeredStyleSheet = registry.addStyleSheetFromValue(rt, std::move(rawStyleSheet));
|
|
25
|
+
auto registeredStyleSheet = registry.addStyleSheetFromValue(rt, this->_unistylesRuntime->generation, std::move(rawStyleSheet));
|
|
25
26
|
|
|
26
27
|
auto parser = parser::Parser(this->_unistylesRuntime);
|
|
27
28
|
|
|
@@ -34,6 +35,7 @@ jsi::Value HybridStyleSheet::create(jsi::Runtime& rt, const jsi::Value &thisVal,
|
|
|
34
35
|
jsi::Value HybridStyleSheet::configure(jsi::Runtime &rt, const jsi::Value &thisVal, const jsi::Value *arguments, size_t count) {
|
|
35
36
|
helpers::assertThat(rt, count == 1, "StyleSheet.configure expected to be called with one argument.");
|
|
36
37
|
helpers::assertThat(rt, arguments[0].isObject(), "StyleSheet.configure expected to be called with object.");
|
|
38
|
+
helpers::assertThat(rt, this->_unistylesRuntime->ownsRegistry(), helpers::RUNTIME_REPLACED_ERROR);
|
|
37
39
|
|
|
38
40
|
auto config = arguments[0].asObject(rt);
|
|
39
41
|
|
|
@@ -73,6 +75,8 @@ jsi::Value HybridStyleSheet::init(jsi::Runtime &rt, const jsi::Value &thisVal, c
|
|
|
73
75
|
return jsi::Value::undefined();
|
|
74
76
|
}
|
|
75
77
|
|
|
78
|
+
helpers::assertThat(rt, this->_unistylesRuntime->ownsRegistry(), helpers::RUNTIME_REPLACED_ERROR);
|
|
79
|
+
|
|
76
80
|
// create new state
|
|
77
81
|
auto& registry = core::UnistylesRegistry::get();
|
|
78
82
|
|
|
@@ -165,7 +169,7 @@ void HybridStyleSheet::parseThemes(jsi::Runtime &rt, jsi::Object themes) {
|
|
|
165
169
|
helpers::enumerateJSIObject(rt, themes, [&](const std::string& propertyName, jsi::Value& propertyValue){
|
|
166
170
|
helpers::assertThat(rt, propertyValue.isObject(), "StyleSheet.configure's registered theme '" + propertyName + "' must be an object.");
|
|
167
171
|
|
|
168
|
-
registry.registerTheme(rt, propertyName, propertyValue);
|
|
172
|
+
registry.registerTheme(rt, this->_unistylesRuntime->generation, propertyName, propertyValue);
|
|
169
173
|
});
|
|
170
174
|
}
|
|
171
175
|
|
|
@@ -267,7 +271,8 @@ void HybridStyleSheet::onPlatformDependenciesChange(std::vector<UnistyleDependen
|
|
|
267
271
|
this->_unistylesRuntime->runOnJSThread([weakSelf, dependencies](jsi::Runtime& rt) {
|
|
268
272
|
auto self = std::dynamic_pointer_cast<HybridStyleSheet>(weakSelf.lock());
|
|
269
273
|
|
|
270
|
-
|
|
274
|
+
// runtime was replaced in the meantime, registry belongs to the next one
|
|
275
|
+
if (!self || !self->_unistylesRuntime->ownsRegistry()) {
|
|
271
276
|
return;
|
|
272
277
|
}
|
|
273
278
|
|
|
@@ -288,7 +293,7 @@ void HybridStyleSheet::onPlatformNativeDependenciesChange(std::vector<UnistyleDe
|
|
|
288
293
|
this->_unistylesRuntime->runOnJSThread([weakSelf, dependencies, miniRuntime](jsi::Runtime& rt){
|
|
289
294
|
auto self = std::dynamic_pointer_cast<HybridStyleSheet>(weakSelf.lock());
|
|
290
295
|
|
|
291
|
-
if (!self) {
|
|
296
|
+
if (!self || !self->_unistylesRuntime->ownsRegistry()) {
|
|
292
297
|
return;
|
|
293
298
|
}
|
|
294
299
|
|
|
@@ -329,7 +334,7 @@ void HybridStyleSheet::onImeChange(UnistylesNativeMiniRuntime miniRuntime) {
|
|
|
329
334
|
this->_unistylesRuntime->runOnJSThread([weakSelf, miniRuntime](jsi::Runtime& rt){
|
|
330
335
|
auto self = std::dynamic_pointer_cast<HybridStyleSheet>(weakSelf.lock());
|
|
331
336
|
|
|
332
|
-
if (!self) {
|
|
337
|
+
if (!self || !self->_unistylesRuntime->ownsRegistry()) {
|
|
333
338
|
return;
|
|
334
339
|
}
|
|
335
340
|
|
|
@@ -348,22 +353,25 @@ void HybridStyleSheet::applyDependencyChanges(jsi::Runtime& rt, std::vector<Unis
|
|
|
348
353
|
// but their rawValue must still be refreshed so rerenders read fresh closures
|
|
349
354
|
auto dependentStyleSheets = registry.getStyleSheetsToRefresh(dependencies);
|
|
350
355
|
|
|
351
|
-
if (dependencyMap.empty() && dependentStyleSheets.empty()) {
|
|
352
|
-
return;
|
|
353
|
-
}
|
|
354
|
-
|
|
355
356
|
// rebuild rawValue BEFORE notifying listeners so JS rerenders read fresh closures
|
|
356
|
-
|
|
357
|
+
if (!dependencyMap.empty() || !dependentStyleSheets.empty()) {
|
|
358
|
+
parser.rebuildUnistylesInDependencyMap(rt, dependencyMap, dependentStyleSheets, maybeMiniRuntime);
|
|
359
|
+
}
|
|
357
360
|
|
|
358
361
|
if (!dependencyMap.empty()) {
|
|
359
362
|
parser.rebuildShadowLeafUpdates(rt, dependencyMap);
|
|
360
363
|
}
|
|
361
364
|
|
|
362
|
-
|
|
365
|
+
std::vector<Tag> committedTags;
|
|
363
366
|
|
|
364
367
|
if (!dependencyMap.empty()) {
|
|
365
|
-
shadow::ShadowTreeManager::updateShadowTree(rt);
|
|
368
|
+
committedTags = shadow::ShadowTreeManager::updateShadowTree(rt);
|
|
366
369
|
}
|
|
370
|
+
|
|
371
|
+
// after the commit, so listeners can point React at the committed nodes
|
|
372
|
+
registry.setCommittedTags(std::move(committedTags));
|
|
373
|
+
// also when no StyleSheet depends on the change, hooks (useUnistyles, withUnistyles, Display, Hide) may
|
|
374
|
+
this->notifyJSListeners(dependencies);
|
|
367
375
|
}
|
|
368
376
|
|
|
369
377
|
void HybridStyleSheet::notifyJSListeners(std::vector<UnistyleDependency>& dependencies) {
|
|
@@ -4,9 +4,18 @@
|
|
|
4
4
|
using namespace margelo::nitro::unistyles;
|
|
5
5
|
|
|
6
6
|
core::UnistylesState& HybridUnistylesRuntime::getState() {
|
|
7
|
+
// state belongs to the runtime that replaced this one
|
|
8
|
+
if (!this->ownsRegistry()) {
|
|
9
|
+
throw std::runtime_error(helpers::RUNTIME_REPLACED_ERROR);
|
|
10
|
+
}
|
|
11
|
+
|
|
7
12
|
return core::UnistylesRegistry::get().getState();
|
|
8
13
|
}
|
|
9
14
|
|
|
15
|
+
bool HybridUnistylesRuntime::ownsRegistry() const {
|
|
16
|
+
return core::UnistylesRegistry::get().isCurrent(this->generation);
|
|
17
|
+
}
|
|
18
|
+
|
|
10
19
|
ColorScheme HybridUnistylesRuntime::getColorScheme() {
|
|
11
20
|
auto colorScheme = this->_nativePlatform->getColorScheme();
|
|
12
21
|
|
|
@@ -166,13 +175,14 @@ jsi::Value HybridUnistylesRuntime::updateTheme(jsi::Runtime &rt, const jsi::Valu
|
|
|
166
175
|
helpers::assertThat(rt, count == 2, "UnistylesRuntime.updateTheme expected to be called with 2 arguments.");
|
|
167
176
|
helpers::assertThat(rt, args[0].isString(), "UnistylesRuntime.updateTheme expected first argument to be a string.");
|
|
168
177
|
helpers::assertThat(rt, args[1].isObject(), "UnistylesRuntime.updateTheme expected first argument to be a function.");
|
|
178
|
+
helpers::assertThat(rt, this->ownsRegistry(), helpers::RUNTIME_REPLACED_ERROR);
|
|
169
179
|
|
|
170
180
|
auto& registry = core::UnistylesRegistry::get();
|
|
171
181
|
auto themeName = args[0].asString(rt).utf8(rt);
|
|
172
182
|
|
|
173
183
|
helpers::assertThat(rt, args[1].asObject(rt).isFunction(rt), "UnistylesRuntime.updateTheme expected second argument to be a function.");
|
|
174
184
|
|
|
175
|
-
registry.updateTheme(rt, themeName, args[1].asObject(rt).asFunction(rt));
|
|
185
|
+
registry.updateTheme(rt, this->generation, themeName, args[1].asObject(rt).asFunction(rt));
|
|
176
186
|
|
|
177
187
|
this->_onDependenciesChange({UnistyleDependency::THEME});
|
|
178
188
|
|
|
@@ -13,8 +13,8 @@
|
|
|
13
13
|
namespace margelo::nitro::unistyles {
|
|
14
14
|
|
|
15
15
|
struct HybridUnistylesRuntime: public HybridUnistylesRuntimeSpec {
|
|
16
|
-
HybridUnistylesRuntime(std::shared_ptr<HybridNativePlatformSpec> nativePlatform, std::function<void(std::function<void(jsi::Runtime&)>&&)> runOnJSThread)
|
|
17
|
-
: HybridObject(TAG), _nativePlatform{nativePlatform}, runOnJSThread(std::move(runOnJSThread)) {}
|
|
16
|
+
HybridUnistylesRuntime(std::shared_ptr<HybridNativePlatformSpec> nativePlatform, std::function<void(std::function<void(jsi::Runtime&)>&&)> runOnJSThread, uint64_t generation)
|
|
17
|
+
: HybridObject(TAG), _nativePlatform{nativePlatform}, runOnJSThread(std::move(runOnJSThread)), generation{generation} {}
|
|
18
18
|
|
|
19
19
|
jsi::Value getTheme(jsi::Runtime& rt,
|
|
20
20
|
const jsi::Value& thisValue,
|
|
@@ -70,11 +70,13 @@ struct HybridUnistylesRuntime: public HybridUnistylesRuntimeSpec {
|
|
|
70
70
|
std::unordered_map<std::string, double> getBreakpoints() override;
|
|
71
71
|
|
|
72
72
|
core::UnistylesState& getState();
|
|
73
|
+
bool ownsRegistry() const;
|
|
73
74
|
UnistylesCxxMiniRuntime buildMiniRuntimeFromNativeRuntime(UnistylesNativeMiniRuntime& nativeMiniRuntime);
|
|
74
75
|
jsi::Value getMiniRuntimeAsValue(jsi::Runtime& rt, std::optional<UnistylesNativeMiniRuntime> maybeMiniRuntime);
|
|
75
76
|
void includeDependenciesForColorSchemeChange(std::vector<UnistyleDependency>& deps);
|
|
76
77
|
void calculateNewThemeAndDependencies(std::vector<UnistyleDependency>& deps);
|
|
77
78
|
std::function<void(std::function<void(jsi::Runtime&)>&&)> runOnJSThread;
|
|
79
|
+
const uint64_t generation;
|
|
78
80
|
|
|
79
81
|
private:
|
|
80
82
|
std::shared_ptr<HybridNavigationBar> _navigationBar;
|
package/cxx/parser/Parser.cpp
CHANGED
|
@@ -439,7 +439,7 @@ void parser::Parser::rebuildShadowLeafUpdates(jsi::Runtime& rt, core::Dependency
|
|
|
439
439
|
|
|
440
440
|
for (const auto& [shadowNode, unistyles] : dependencyMap) {
|
|
441
441
|
// Parse string colors (e.g., "#000000") to int representation
|
|
442
|
-
auto rawProps = this->
|
|
442
|
+
auto rawProps = this->parseStylesToShadowTreeUpdates(rt, unistyles);
|
|
443
443
|
|
|
444
444
|
updates.emplace(shadowNode, std::move(rawProps));
|
|
445
445
|
}
|
|
@@ -1268,6 +1268,34 @@ folly::dynamic parser::Parser::parseStylesToShadowTreeStyles(jsi::Runtime& rt, c
|
|
|
1268
1268
|
return jsi::dynamicFromValue(rt, jsi::Value(rt, convertedStyles));
|
|
1269
1269
|
}
|
|
1270
1270
|
|
|
1271
|
+
// shadow tree updates skip the props an inline style sets last, React (or an animation) owns them
|
|
1272
|
+
// writing them would also leave them in nativeProps_DEPRECATED, which React Native applies to every later clone,
|
|
1273
|
+
// so a value captured at link time would undo what React rendered since
|
|
1274
|
+
folly::dynamic parser::Parser::parseStylesToShadowTreeUpdates(jsi::Runtime& rt, const std::vector<std::shared_ptr<UnistyleData>>& unistyles) {
|
|
1275
|
+
auto props = this->parseStylesToShadowTreeStyles(rt, unistyles);
|
|
1276
|
+
std::unordered_map<std::string, bool> isOwnedByInlineStyle;
|
|
1277
|
+
|
|
1278
|
+
for (const auto& unistyleData : unistyles) {
|
|
1279
|
+
if (!unistyleData->parsedStyle.has_value()) {
|
|
1280
|
+
continue;
|
|
1281
|
+
}
|
|
1282
|
+
|
|
1283
|
+
bool isInlineStyle = unistyleData->unistyle->styleKey == helpers::EXOTIC_STYLE_KEY;
|
|
1284
|
+
|
|
1285
|
+
helpers::enumerateJSIObject(rt, unistyleData->parsedStyle.value(), [&isOwnedByInlineStyle, isInlineStyle](const std::string& propName, jsi::Value&) {
|
|
1286
|
+
isOwnedByInlineStyle[propName] = isInlineStyle;
|
|
1287
|
+
});
|
|
1288
|
+
}
|
|
1289
|
+
|
|
1290
|
+
for (const auto& [propName, isInline] : isOwnedByInlineStyle) {
|
|
1291
|
+
if (isInline) {
|
|
1292
|
+
props.erase(propName);
|
|
1293
|
+
}
|
|
1294
|
+
}
|
|
1295
|
+
|
|
1296
|
+
return props;
|
|
1297
|
+
}
|
|
1298
|
+
|
|
1271
1299
|
|
|
1272
1300
|
// check is styleKey contains color
|
|
1273
1301
|
bool parser::Parser::isColor(const std::string& propertyName) {
|
package/cxx/parser/Parser.h
CHANGED
|
@@ -28,6 +28,7 @@ struct Parser {
|
|
|
28
28
|
void rebuildUnistylesInDependencyMap(jsi::Runtime& rt, core::DependencyMap& dependencyMap, std::vector<std::shared_ptr<core::StyleSheet>>& styleSheets, std::optional<UnistylesNativeMiniRuntime> maybeMiniRuntime);
|
|
29
29
|
void rebuildShadowLeafUpdates(jsi::Runtime& rt, core::DependencyMap& dependencyMap);
|
|
30
30
|
folly::dynamic parseStylesToShadowTreeStyles(jsi::Runtime& rt, const std::vector<std::shared_ptr<UnistyleData>>& unistyles);
|
|
31
|
+
folly::dynamic parseStylesToShadowTreeUpdates(jsi::Runtime& rt, const std::vector<std::shared_ptr<UnistyleData>>& unistyles);
|
|
31
32
|
void rebuildUnistyle(jsi::Runtime& rt, Unistyle::Shared unistyle, const Variants& variants, std::optional<std::vector<folly::dynamic>>);
|
|
32
33
|
void rebuildUnistyleWithScopedTheme(jsi::Runtime& rt, jsi::Value& jsScopedTheme, std::shared_ptr<core::UnistyleData> unistyleData);
|
|
33
34
|
jsi::Value getParsedStyleSheetForScopedTheme(jsi::Runtime& rt, core::Unistyle::Shared unistyle, std::string& scopedTheme);
|
|
@@ -3,8 +3,11 @@
|
|
|
3
3
|
#include <folly/dynamic.h>
|
|
4
4
|
#include <react/renderer/core/ShadowNodeFamily.h>
|
|
5
5
|
#include <cxxreact/ReactNativeVersion.h>
|
|
6
|
+
#include <algorithm>
|
|
7
|
+
#include <cstdint>
|
|
6
8
|
#include <memory>
|
|
7
9
|
#include <mutex>
|
|
10
|
+
#include <string>
|
|
8
11
|
|
|
9
12
|
// React Native reads ShadowNodeFamily::nativeProps_DEPRECATED from any thread
|
|
10
13
|
// (eg. ShadowNode::clone during main thread layout) and since 0.86.1 guards every access with nativePropsMutex
|
|
@@ -33,12 +36,53 @@ inline void mergeNativeProps(const ShadowNodeFamily* family, const folly::dynami
|
|
|
33
36
|
family->nativeProps_DEPRECATED = std::make_unique<folly::dynamic>(props);
|
|
34
37
|
}
|
|
35
38
|
|
|
36
|
-
inline
|
|
39
|
+
inline bool hasNativeProps(const ShadowNodeFamily* family) {
|
|
37
40
|
#if UNISTYLES_HAS_NATIVE_PROPS_MUTEX
|
|
38
41
|
std::lock_guard<std::mutex> lock(family->nativePropsMutex);
|
|
39
42
|
#endif
|
|
40
43
|
|
|
41
|
-
family->nativeProps_DEPRECATED
|
|
44
|
+
return family->nativeProps_DEPRECATED && family->nativeProps_DEPRECATED->isObject();
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
inline bool isSamePropValue(const std::string& propName, const folly::dynamic& value, const folly::dynamic& otherValue) {
|
|
48
|
+
if (value == otherValue) {
|
|
49
|
+
return true;
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
if (!value.isNumber() || !otherValue.isNumber()) {
|
|
53
|
+
return false;
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
std::string lowercasePropName = propName;
|
|
57
|
+
std::transform(lowercasePropName.begin(), lowercasePropName.end(), lowercasePropName.begin(), ::tolower);
|
|
58
|
+
|
|
59
|
+
if (lowercasePropName.find("color") == std::string::npos) {
|
|
60
|
+
return false;
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
return static_cast<uint32_t>(static_cast<int64_t>(value.asDouble())) == static_cast<uint32_t>(static_cast<int64_t>(otherValue.asDouble()));
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
inline bool hasOutdatedNativeProps(const ShadowNodeFamily* family, const folly::dynamic& props) {
|
|
67
|
+
#if UNISTYLES_HAS_NATIVE_PROPS_MUTEX
|
|
68
|
+
std::lock_guard<std::mutex> lock(family->nativePropsMutex);
|
|
69
|
+
#endif
|
|
70
|
+
|
|
71
|
+
if (!family->nativeProps_DEPRECATED || !family->nativeProps_DEPRECATED->isObject() || !props.isObject()) {
|
|
72
|
+
return false;
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
auto& nativeProps = *family->nativeProps_DEPRECATED;
|
|
76
|
+
|
|
77
|
+
for (const auto& [propName, propValue] : props.items()) {
|
|
78
|
+
auto it = nativeProps.find(propName);
|
|
79
|
+
|
|
80
|
+
if (it != nativeProps.items().end() && !isSamePropValue(propName.asString(), it->second, propValue)) {
|
|
81
|
+
return true;
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
return false;
|
|
42
86
|
}
|
|
43
87
|
|
|
44
88
|
}
|