45
45
using namespace facebook ;
46
46
using namespace facebook ::react;
47
47
48
+ @interface RCTComponentViewFactory ()
49
+ - (void )_registerComponentIfPossible : (const std::string &)name ;
50
+ - (BOOL )_wasComponentRegistered : (const std::string &)name ;
51
+ @end
52
+
48
53
// Allow JS runtime to register native components as needed. For static view configs.
49
54
void RCTInstallNativeComponentRegistryBinding (facebook::jsi::Runtime &runtime)
50
55
{
51
56
auto hasComponentProvider = [](const std::string &name) -> bool {
52
- return [[RCTComponentViewFactory currentComponentViewFactory ]
53
- registerComponentIfPossible: componentNameByReactViewName (name)];
57
+ auto globalComponentViewFactory = [RCTComponentViewFactory currentComponentViewFactory ];
58
+ auto actualName = componentNameByReactViewName (name);
59
+ [globalComponentViewFactory _registerComponentIfPossible: actualName];
60
+ return [globalComponentViewFactory _wasComponentRegistered: actualName];
54
61
};
55
62
bindHasComponentProvider (runtime, std::move (hasComponentProvider));
56
63
}
@@ -62,7 +69,7 @@ void RCTInstallNativeComponentRegistryBinding(facebook::jsi::Runtime &runtime)
62
69
63
70
@implementation RCTComponentViewFactory {
64
71
std::unordered_map<ComponentHandle, RCTComponentViewClassDescriptor> _componentViewClasses;
65
- std::unordered_set <std::string> _registeredComponentsNames ;
72
+ std::unordered_map <std::string, bool > _registrationStatusMap ;
66
73
ComponentDescriptorProviderRegistry _providerRegistry;
67
74
std::shared_mutex _mutex;
68
75
}
@@ -81,7 +88,7 @@ + (RCTComponentViewFactory *)currentComponentViewFactory
81
88
82
89
componentViewFactory->_providerRegistry .setComponentDescriptorProviderRequest (
83
90
[](ComponentName requestedComponentName) {
84
- [componentViewFactory registerComponentIfPossible : requestedComponentName];
91
+ [componentViewFactory _registerComponentIfPossible : requestedComponentName];
85
92
});
86
93
});
87
94
@@ -106,11 +113,16 @@ - (RCTComponentViewClassDescriptor)_componentViewClassDescriptorFromClass:(Class
106
113
#pragma clang diagnostic pop
107
114
}
108
115
109
- - (BOOL )registerComponentIfPossible : (const std::string &)name
116
+ - (BOOL )_wasComponentRegistered : (const std::string &)name
110
117
{
111
- if (_registeredComponentsNames.find (name) != _registeredComponentsNames.end ()) {
112
- // Component has already been registered.
113
- return YES ;
118
+ auto registrationResult = _registrationStatusMap.find (name);
119
+ return registrationResult != _registrationStatusMap.end () && (registrationResult->second );
120
+ }
121
+
122
+ - (void )_registerComponentIfPossible : (const std::string &)name
123
+ {
124
+ if (_registrationStatusMap.find (name) != _registrationStatusMap.end ()) {
125
+ return ;
114
126
}
115
127
116
128
// Paper name: we prepare this variables to warn the user
@@ -122,7 +134,7 @@ - (BOOL)registerComponentIfPossible:(const std::string &)name
122
134
Class <RCTComponentViewProtocol> klass = RCTComponentViewClassWithName (name.c_str ());
123
135
if (klass) {
124
136
[self registerComponentViewClass: klass];
125
- return YES ;
137
+ return ;
126
138
}
127
139
128
140
// Fallback 2: Ask the provider and check in the dictionary provided
@@ -133,7 +145,7 @@ - (BOOL)registerComponentIfPossible:(const std::string &)name
133
145
klass = self.thirdPartyFabricComponentsProvider .thirdPartyFabricComponents [objcName];
134
146
if (klass) {
135
147
[self registerComponentViewClass: klass];
136
- return YES ;
148
+ return ;
137
149
}
138
150
}
139
151
@@ -153,52 +165,45 @@ - (BOOL)registerComponentIfPossible:(const std::string &)name
153
165
auto componentHandle = reinterpret_cast <ComponentHandle>(componentName);
154
166
auto constructor = [RCTLegacyViewManagerInteropComponentView componentDescriptorProvider ].constructor ;
155
167
156
- [self _addDescriptorToProviderRegistry: ComponentDescriptorProvider{
157
- componentHandle, componentName, flavor, constructor}];
168
+ auto provider = ComponentDescriptorProvider{componentHandle, componentName, flavor, constructor};
158
169
170
+ _providerRegistry.add (provider);
159
171
_componentViewClasses[componentHandle] =
160
172
[self _componentViewClassDescriptorFromClass: [RCTLegacyViewManagerInteropComponentView class ]];
161
- return YES ;
173
+ _registrationStatusMap.insert ({provider.name , true });
174
+ return ;
162
175
}
163
176
164
177
// Fallback 4: use <UnimplementedView> if component doesn't exist.
165
178
auto flavor = std::make_shared<const std::string>(name);
166
179
auto componentName = ComponentName{flavor->c_str ()};
167
180
auto componentHandle = reinterpret_cast <ComponentHandle>(componentName);
168
181
auto constructor = [RCTUnimplementedViewComponentView componentDescriptorProvider ].constructor ;
182
+ auto provider = ComponentDescriptorProvider{componentHandle, componentName, flavor, constructor};
169
183
170
- [self _addDescriptorToProviderRegistry: ComponentDescriptorProvider{
171
- componentHandle, componentName, flavor, constructor}];
172
-
184
+ _providerRegistry.add (provider);
173
185
_componentViewClasses[componentHandle] =
174
186
[self _componentViewClassDescriptorFromClass: [RCTUnimplementedViewComponentView class ]];
175
-
176
- // No matching class exists for `name`.
177
- return NO ;
187
+ _registrationStatusMap.insert ({provider.name , false });
178
188
}
179
189
180
190
- (void )registerComponentViewClass : (Class <RCTComponentViewProtocol>)componentViewClass
181
191
{
182
192
RCTAssert (componentViewClass, @" RCTComponentViewFactory: Provided `componentViewClass` is `nil`." );
183
193
std::unique_lock lock (_mutex);
184
194
185
- auto componentDescriptorProvider = [componentViewClass componentDescriptorProvider ];
186
- _componentViewClasses[componentDescriptorProvider .handle] =
187
- [ self _componentViewClassDescriptorFromClass: componentViewClass] ;
188
- [ self _addDescriptorToProviderRegistry: componentDescriptorProvider] ;
195
+ auto provider = [componentViewClass componentDescriptorProvider ];
196
+ _componentViewClasses[provider .handle] = [ self _componentViewClassDescriptorFromClass: componentViewClass];
197
+ _providerRegistry. add (provider) ;
198
+ _registrationStatusMap. insert ({provider. name , true }) ;
189
199
190
200
auto supplementalComponentDescriptorProviders = [componentViewClass supplementalComponentDescriptorProviders ];
191
- for (const auto &provider : supplementalComponentDescriptorProviders) {
192
- [self _addDescriptorToProviderRegistry: provider];
201
+ for (const auto &supplementalProvider : supplementalComponentDescriptorProviders) {
202
+ _providerRegistry.add (supplementalProvider);
203
+ _registrationStatusMap.insert ({supplementalProvider.name , true });
193
204
}
194
205
}
195
206
196
- - (void )_addDescriptorToProviderRegistry : (const ComponentDescriptorProvider &)provider
197
- {
198
- _registeredComponentsNames.insert (provider.name );
199
- _providerRegistry.add (provider);
200
- }
201
-
202
207
- (RCTComponentViewDescriptor)createComponentViewWithComponentHandle : (facebook::react::ComponentHandle)componentHandle
203
208
{
204
209
RCTAssertMainQueue ();
0 commit comments