Remove instanceHandle, pass event target instead + add dispatchToEmptyTarget
Summary: Removes the concept of instance handle. Instead we pass the event target to createNode and don't pass it to subsequent clones. The life time of the event target is managed by native (the event emitter). It has to be released manually. Reviewed By: shergin Differential Revision: D8688330 fbshipit-source-id: e11b61f147ea9ca4dfb453fe07063ed06f24b7ac
This commit is contained in:
parent
7b1bd4d4f3
commit
5d9326be29
|
@ -14,12 +14,17 @@ public interface FabricBinding {
|
|||
|
||||
void installFabric(JavaScriptContextHolder jsContext, FabricUIManager fabricModule);
|
||||
|
||||
long createEventTarget(long jsContextNativePointer, long instanceHandlePointer);
|
||||
|
||||
void releaseEventTarget(long jsContextNativePointer, long eventTargetPointer);
|
||||
|
||||
void releaseEventHandler(long jsContextNativePointer, long eventHandlerPointer);
|
||||
|
||||
void dispatchEventToEmptyTarget(
|
||||
long jsContextNativePointer,
|
||||
long eventHandlerPointer,
|
||||
String type,
|
||||
NativeMap payload
|
||||
);
|
||||
|
||||
void dispatchEventToTarget(
|
||||
long jsContextNativePointer,
|
||||
long eventHandlerPointer,
|
||||
|
|
|
@ -106,7 +106,7 @@ public class FabricUIManager implements UIManager, JSHandler {
|
|||
@Nullable
|
||||
@DoNotStrip
|
||||
public ReactShadowNode createNode(
|
||||
int reactTag, String viewName, int rootTag, ReadableNativeMap props, long instanceHandle) {
|
||||
int reactTag, String viewName, int rootTag, ReadableNativeMap props, long eventTarget) {
|
||||
if (DEBUG) {
|
||||
FLog.d(TAG, "createNode \n\ttag: " + reactTag +
|
||||
"\n\tviewName: " + viewName +
|
||||
|
@ -119,7 +119,7 @@ public class FabricUIManager implements UIManager, JSHandler {
|
|||
ReactShadowNode rootNode = getRootNode(rootTag);
|
||||
node.setRootTag(rootNode.getReactTag());
|
||||
node.setViewClassName(viewName);
|
||||
node.setInstanceHandle(instanceHandle);
|
||||
node.setInstanceHandle(eventTarget);
|
||||
node.setReactTag(reactTag);
|
||||
node.setThemedContext(rootNode.getThemedContext());
|
||||
|
||||
|
@ -157,7 +157,7 @@ public class FabricUIManager implements UIManager, JSHandler {
|
|||
*/
|
||||
@Nullable
|
||||
@DoNotStrip
|
||||
public ReactShadowNode cloneNode(ReactShadowNode node, long instanceHandle) {
|
||||
public ReactShadowNode cloneNode(ReactShadowNode node) {
|
||||
if (DEBUG) {
|
||||
FLog.d(TAG, "cloneNode \n\tnode: " + node);
|
||||
}
|
||||
|
@ -166,7 +166,7 @@ public class FabricUIManager implements UIManager, JSHandler {
|
|||
"FabricUIManager.cloneNode")
|
||||
.flush();
|
||||
try {
|
||||
ReactShadowNode clone = node.mutableCopy(instanceHandle);
|
||||
ReactShadowNode clone = node.mutableCopy(node.getInstanceHandle());
|
||||
assertReactShadowNodeCopy(node, clone);
|
||||
return clone;
|
||||
} catch (Throwable t) {
|
||||
|
@ -184,7 +184,7 @@ public class FabricUIManager implements UIManager, JSHandler {
|
|||
*/
|
||||
@Nullable
|
||||
@DoNotStrip
|
||||
public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node, long instanceHandle) {
|
||||
public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node) {
|
||||
if (DEBUG) {
|
||||
FLog.d(TAG, "cloneNodeWithNewChildren \n\tnode: " + node);
|
||||
}
|
||||
|
@ -193,7 +193,7 @@ public class FabricUIManager implements UIManager, JSHandler {
|
|||
"FabricUIManager.cloneNodeWithNewChildren")
|
||||
.flush();
|
||||
try {
|
||||
ReactShadowNode clone = node.mutableCopyWithNewChildren(instanceHandle);
|
||||
ReactShadowNode clone = node.mutableCopyWithNewChildren(node.getInstanceHandle());
|
||||
assertReactShadowNodeCopy(node, clone);
|
||||
return clone;
|
||||
} catch (Throwable t) {
|
||||
|
@ -212,7 +212,7 @@ public class FabricUIManager implements UIManager, JSHandler {
|
|||
@Nullable
|
||||
@DoNotStrip
|
||||
public ReactShadowNode cloneNodeWithNewProps(
|
||||
ReactShadowNode node, @Nullable ReadableNativeMap newProps, long instanceHandle) {
|
||||
ReactShadowNode node, @Nullable ReadableNativeMap newProps) {
|
||||
if (DEBUG) {
|
||||
FLog.d(TAG, "cloneNodeWithNewProps \n\tnode: " + node + "\n\tprops: " + newProps);
|
||||
}
|
||||
|
@ -221,7 +221,7 @@ public class FabricUIManager implements UIManager, JSHandler {
|
|||
"FabricUIManager.cloneNodeWithNewProps")
|
||||
.flush();
|
||||
try {
|
||||
ReactShadowNode clone = node.mutableCopyWithNewProps(instanceHandle,
|
||||
ReactShadowNode clone = node.mutableCopyWithNewProps(node.getInstanceHandle(),
|
||||
newProps == null ? null : new ReactStylesDiffMap(newProps));
|
||||
assertReactShadowNodeCopy(node, clone);
|
||||
return clone;
|
||||
|
@ -242,7 +242,7 @@ public class FabricUIManager implements UIManager, JSHandler {
|
|||
@Nullable
|
||||
@DoNotStrip
|
||||
public ReactShadowNode cloneNodeWithNewChildrenAndProps(
|
||||
ReactShadowNode node, ReadableNativeMap newProps, long instanceHandle) {
|
||||
ReactShadowNode node, ReadableNativeMap newProps) {
|
||||
if (DEBUG) {
|
||||
FLog.d(TAG, "cloneNodeWithNewChildrenAndProps \n\tnode: " + node + "\n\tnewProps: " + newProps);
|
||||
}
|
||||
|
@ -252,7 +252,7 @@ public class FabricUIManager implements UIManager, JSHandler {
|
|||
.flush();
|
||||
try {
|
||||
ReactShadowNode clone =
|
||||
node.mutableCopyWithNewChildrenAndProps(instanceHandle,
|
||||
node.mutableCopyWithNewChildrenAndProps(node.getInstanceHandle(),
|
||||
newProps == null ? null : new ReactStylesDiffMap(newProps));
|
||||
assertReactShadowNodeCopy(node, clone);
|
||||
return clone;
|
||||
|
@ -610,16 +610,9 @@ public class FabricUIManager implements UIManager, JSHandler {
|
|||
|
||||
@Nullable
|
||||
@DoNotStrip
|
||||
public long createEventTarget(int reactTag) {
|
||||
public long getEventTarget(int reactTag) {
|
||||
long instanceHandle = mNativeViewHierarchyManager.getInstanceHandle(reactTag);
|
||||
long context = mJSContext.get();
|
||||
long eventTarget = mBinding.createEventTarget(context, instanceHandle);
|
||||
if (DEBUG) {
|
||||
FLog.d(
|
||||
TAG,
|
||||
"Created EventTarget: " + eventTarget + " for tag: " + reactTag + " with instanceHandle: " + instanceHandle);
|
||||
}
|
||||
return eventTarget;
|
||||
return instanceHandle;
|
||||
}
|
||||
|
||||
@DoNotStrip
|
||||
|
|
|
@ -49,7 +49,7 @@ public class FabricEventEmitter implements RCTEventEmitter, Closeable {
|
|||
@Override
|
||||
public void receiveEvent(int reactTag, String eventName, @Nullable WritableMap params) {
|
||||
try {
|
||||
long eventTarget = mFabricUIManager.createEventTarget(reactTag);
|
||||
long eventTarget = mFabricUIManager.getEventTarget(reactTag);
|
||||
mScheduler.scheduleWork(new FabricUIManagerWork(eventTarget, eventName, params));
|
||||
} catch (IllegalViewOperationException e) {
|
||||
FLog.e(TAG, "Unable to emmit event for tag " + reactTag, e);
|
||||
|
@ -80,7 +80,10 @@ public class FabricEventEmitter implements RCTEventEmitter, Closeable {
|
|||
FLog.e(TAG, "Error sending event " + mEventName, t);
|
||||
//TODO: manage exception properly
|
||||
} finally{
|
||||
mFabricUIManager.releaseEventTarget(mEventTarget);
|
||||
// TODO(dvacca): We need to only release this after all shadow nodes
|
||||
// have been released. The easiest way would be to adopt the event
|
||||
// emitter approach from the C++ Fabric. For now, we'll just leak.
|
||||
// mFabricUIManager.releaseEventTarget(mEventTarget);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -28,15 +28,20 @@ public class FabricJSCBinding implements FabricBinding {
|
|||
|
||||
private static native HybridData initHybrid();
|
||||
|
||||
@Override
|
||||
public native long createEventTarget(long jsContextNativePointer, long instanceHandlePointer);
|
||||
|
||||
@Override
|
||||
public native void releaseEventTarget(long jsContextNativePointer, long eventTargetPointer);
|
||||
|
||||
@Override
|
||||
public native void releaseEventHandler(long jsContextNativePointer, long eventHandlerPointer);
|
||||
|
||||
@Override
|
||||
public native void dispatchEventToEmptyTarget(
|
||||
long jsContextNativePointer,
|
||||
long eventHandlerPointer,
|
||||
String type,
|
||||
NativeMap payload
|
||||
);
|
||||
|
||||
@Override
|
||||
public native void dispatchEventToTarget(
|
||||
long jsContextNativePointer,
|
||||
|
|
|
@ -103,9 +103,9 @@ JSValueRef createNode(JSContextRef ctx, JSObjectRef function, JSObjectRef thisOb
|
|||
int rootTag = (int)JSC_JSValueToNumber(ctx, arguments[2], NULL);
|
||||
auto props = JSC_JSValueIsNull(ctx, arguments[3]) ? local_ref<ReadableNativeMap::jhybridobject>(nullptr) :
|
||||
JSValueToReadableMapViaJSON(ctx, arguments[3]);;
|
||||
auto instanceHandle = (void *)arguments[4];
|
||||
auto eventTarget = (void *)arguments[4];
|
||||
|
||||
auto node = createNode(manager, reactTag, viewName.get(), rootTag, props.get(), (jlong)instanceHandle);
|
||||
auto node = createNode(manager, reactTag, viewName.get(), rootTag, props.get(), (jlong)eventTarget);
|
||||
|
||||
return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(node.get()));
|
||||
}
|
||||
|
@ -117,11 +117,10 @@ JSValueRef cloneNode(JSContextRef ctx, JSObjectRef function, JSObjectRef thisObj
|
|||
|
||||
static auto cloneNode =
|
||||
jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
|
||||
->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, jlong)>("cloneNode");
|
||||
->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject)>("cloneNode");
|
||||
|
||||
auto previousNode = JSValueToJShadowNode(ctx, arguments[0]);
|
||||
auto instanceHandle = (void *)arguments[1];
|
||||
auto newNode = cloneNode(manager, previousNode.get(), (jlong)instanceHandle);
|
||||
auto newNode = cloneNode(manager, previousNode.get());
|
||||
|
||||
return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(newNode.get()));
|
||||
}
|
||||
|
@ -133,11 +132,10 @@ JSValueRef cloneNodeWithNewChildren(JSContextRef ctx, JSObjectRef function, JSOb
|
|||
|
||||
static auto cloneNodeWithNewChildren =
|
||||
jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
|
||||
->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, jlong)>("cloneNodeWithNewChildren");
|
||||
->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject)>("cloneNodeWithNewChildren");
|
||||
|
||||
auto previousNode = JSValueToJShadowNode(ctx, arguments[0]);
|
||||
auto instanceHandle = (void *)arguments[1];
|
||||
auto newNode = cloneNodeWithNewChildren(manager, previousNode.get(), (jlong)instanceHandle);
|
||||
auto newNode = cloneNodeWithNewChildren(manager, previousNode.get());
|
||||
|
||||
return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(newNode.get()));
|
||||
}
|
||||
|
@ -149,12 +147,11 @@ JSValueRef cloneNodeWithNewProps(JSContextRef ctx, JSObjectRef function, JSObjec
|
|||
|
||||
static auto cloneNodeWithNewProps =
|
||||
jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
|
||||
->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, ReadableNativeMap::javaobject, jlong)>("cloneNodeWithNewProps");
|
||||
->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, ReadableNativeMap::javaobject)>("cloneNodeWithNewProps");
|
||||
|
||||
auto previousNode = JSValueToJShadowNode(ctx, arguments[0]);
|
||||
auto props = JSValueToReadableMapViaJSON(ctx, arguments[1]);
|
||||
auto instanceHandle = (void *)arguments[2];
|
||||
auto newNode = cloneNodeWithNewProps(manager, previousNode.get(), props.get(), (jlong)instanceHandle);
|
||||
auto newNode = cloneNodeWithNewProps(manager, previousNode.get(), props.get());
|
||||
|
||||
return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(newNode.get()));
|
||||
}
|
||||
|
@ -166,12 +163,11 @@ JSValueRef cloneNodeWithNewChildrenAndProps(JSContextRef ctx, JSObjectRef functi
|
|||
|
||||
static auto cloneNodeWithNewChildrenAndProps =
|
||||
jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
|
||||
->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, ReadableNativeMap::javaobject, jlong)>("cloneNodeWithNewChildrenAndProps");
|
||||
->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, ReadableNativeMap::javaobject)>("cloneNodeWithNewChildrenAndProps");
|
||||
|
||||
auto previousNode = JSValueToJShadowNode(ctx, arguments[0]);
|
||||
auto props = JSValueToReadableMapViaJSON(ctx, arguments[1]);
|
||||
auto instanceHandle = (void *)arguments[2];
|
||||
auto newNode = cloneNodeWithNewChildrenAndProps(manager, previousNode.get(), props.get(), (jlong)instanceHandle);
|
||||
auto newNode = cloneNodeWithNewChildrenAndProps(manager, previousNode.get(), props.get());
|
||||
|
||||
return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(newNode.get()));
|
||||
}
|
||||
|
@ -293,25 +289,11 @@ jni::local_ref<FabricJSCBinding::jhybriddata> FabricJSCBinding::initHybrid(
|
|||
return makeCxxInstance();
|
||||
}
|
||||
|
||||
jlong FabricJSCBinding::createEventTarget(
|
||||
jlong jsContextNativePointer,
|
||||
jlong instanceHandlePointer
|
||||
) {
|
||||
JSContextRef context = (JSContextRef)jsContextNativePointer;
|
||||
JSValueRef value = (JSValueRef)instanceHandlePointer;
|
||||
// Retain a strong reference to this object.
|
||||
JSC_JSValueProtect(context, value);
|
||||
return (jlong)((void *)value);
|
||||
}
|
||||
|
||||
void FabricJSCBinding::releaseEventTarget(
|
||||
jlong jsContextNativePointer,
|
||||
jlong eventTargetPointer
|
||||
) {
|
||||
JSContextRef context = (JSContextRef)jsContextNativePointer;
|
||||
JSValueRef value = (JSValueRef)((void *)eventTargetPointer);
|
||||
// Release this object.
|
||||
JSC_JSValueUnprotect(context, value);
|
||||
// This is now a noop.
|
||||
}
|
||||
|
||||
void FabricJSCBinding::releaseEventHandler(
|
||||
|
@ -324,6 +306,36 @@ void FabricJSCBinding::releaseEventHandler(
|
|||
JSC_JSValueUnprotect(context, value);
|
||||
}
|
||||
|
||||
void FabricJSCBinding::dispatchEventToEmptyTarget(
|
||||
jlong jsContextNativePointer,
|
||||
jlong eventHandlerPointer,
|
||||
std::string type,
|
||||
NativeMap *payloadMap
|
||||
) {
|
||||
JSContextRef context = (JSContextRef)jsContextNativePointer;
|
||||
JSObjectRef eventHandler = (JSObjectRef)((void *)eventHandlerPointer);
|
||||
JSValueRef eventTarget = JSC_JSValueMakeNull(context);
|
||||
|
||||
JSObjectRef thisArg = (JSObjectRef)JSC_JSValueMakeUndefined(context);
|
||||
JSStringRef typeStr = JSC_JSStringCreateWithUTF8CString(context, type.c_str());
|
||||
JSValueRef typeRef = JSC_JSValueMakeString(context, typeStr);
|
||||
JSC_JSStringRelease(context, typeStr);
|
||||
JSValueRef payloadRef = ReadableMapToJSValueViaJSON(context, payloadMap);
|
||||
JSValueRef args[] = {eventTarget, typeRef, payloadRef};
|
||||
JSValueRef exn;
|
||||
JSValueRef result = JSC_JSObjectCallAsFunction(
|
||||
context,
|
||||
eventHandler,
|
||||
thisArg,
|
||||
3,
|
||||
args,
|
||||
&exn
|
||||
);
|
||||
if (!result) {
|
||||
// TODO: Handle error in exn
|
||||
}
|
||||
}
|
||||
|
||||
void FabricJSCBinding::dispatchEventToTarget(
|
||||
jlong jsContextNativePointer,
|
||||
jlong eventHandlerPointer,
|
||||
|
@ -392,9 +404,9 @@ void FabricJSCBinding::registerNatives() {
|
|||
registerHybrid({
|
||||
makeNativeMethod("initHybrid", FabricJSCBinding::initHybrid),
|
||||
makeNativeMethod("installFabric", FabricJSCBinding::installFabric),
|
||||
makeNativeMethod("createEventTarget", FabricJSCBinding::createEventTarget),
|
||||
makeNativeMethod("releaseEventTarget", FabricJSCBinding::releaseEventTarget),
|
||||
makeNativeMethod("releaseEventHandler", FabricJSCBinding::releaseEventHandler),
|
||||
makeNativeMethod("dispatchEventToEmptyTarget", FabricJSCBinding::dispatchEventToEmptyTarget),
|
||||
makeNativeMethod("dispatchEventToTarget", FabricJSCBinding::dispatchEventToTarget),
|
||||
});
|
||||
}
|
||||
|
|
|
@ -27,12 +27,17 @@ private:
|
|||
|
||||
static jni::local_ref<jhybriddata> initHybrid(jni::alias_ref<jclass>);
|
||||
|
||||
jlong createEventTarget(jlong jsContextNativePointer, jlong instanceHandlePointer);
|
||||
|
||||
void releaseEventTarget(jlong jsContextNativePointer, jlong eventTargetPointer);
|
||||
|
||||
void releaseEventHandler(jlong jsContextNativePointer, jlong eventHandlerPointer);
|
||||
|
||||
void dispatchEventToEmptyTarget(
|
||||
jlong jsContextNativePointer,
|
||||
jlong eventHandlerPointer,
|
||||
std::string type,
|
||||
NativeMap *payload
|
||||
);
|
||||
|
||||
void dispatchEventToTarget(
|
||||
jlong jsContextNativePointer,
|
||||
jlong eventHandlerPointer,
|
||||
|
|
|
@ -103,7 +103,7 @@ public class FabricUIManagerTest {
|
|||
ReactShadowNode child = createViewNode();
|
||||
node.addChildAt(child, 0);
|
||||
|
||||
ReactShadowNode clonedNode = mFabricUIManager.cloneNode(node, 0);
|
||||
ReactShadowNode clonedNode = mFabricUIManager.cloneNode(node);
|
||||
|
||||
assertThat(clonedNode).isNotSameAs(node);
|
||||
assertThat(clonedNode.getOriginalReactShadowNode()).isSameAs(node);
|
||||
|
@ -112,27 +112,12 @@ public class FabricUIManagerTest {
|
|||
assertThat(clonedNode.getChildAt(0)).isEqualTo(child);
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void testCloneWithInstanceHandle() {
|
||||
ReactShadowNode node = createViewNode();
|
||||
|
||||
long oldInstanceHandle = node.getInstanceHandle();
|
||||
long newInstanceHandle = oldInstanceHandle + 1;
|
||||
ReactShadowNode clonedNode = mFabricUIManager.cloneNode(node, newInstanceHandle);
|
||||
|
||||
assertThat(clonedNode).isNotSameAs(node);
|
||||
assertThat(clonedNode.getInstanceHandle()).isSameAs(newInstanceHandle);
|
||||
assertThat(node.getInstanceHandle()).isSameAs(oldInstanceHandle);
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void testDefaultSpacingCloning() {
|
||||
ReactShadowNode node = createViewNode();
|
||||
node.setDefaultPadding(Spacing.LEFT, 10);
|
||||
|
||||
ReactShadowNode clonedNode = mFabricUIManager.cloneNode(node, 0);
|
||||
ReactShadowNode clonedNode = mFabricUIManager.cloneNode(node);
|
||||
|
||||
node.setDefaultPadding(Spacing.LEFT, 20);
|
||||
assertThat(clonedNode.getStylePadding(Spacing.LEFT).value).isEqualTo(10f, Offset.offset(0.01f));
|
||||
|
@ -165,7 +150,7 @@ public class FabricUIManagerTest {
|
|||
ReactShadowNode child = createViewNode();
|
||||
node.addChildAt(child, 0);
|
||||
|
||||
ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewChildren(node, randomInstanceHandle());
|
||||
ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewChildren(node);
|
||||
|
||||
assertThat(clonedNode.getChildCount()).isZero();
|
||||
assertSameFields(clonedNode, node);
|
||||
|
@ -176,7 +161,7 @@ public class FabricUIManagerTest {
|
|||
ReactShadowNode node = createViewNode();
|
||||
ReadableNativeMap props = null; // TODO(ayc): Figure out how to create a Native map from tests.
|
||||
|
||||
ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewProps(node, props, randomInstanceHandle());
|
||||
ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewProps(node, props);
|
||||
}
|
||||
|
||||
@Test
|
||||
|
@ -184,7 +169,7 @@ public class FabricUIManagerTest {
|
|||
ReactShadowNode node = createViewNode();
|
||||
ReadableNativeMap props = null;
|
||||
|
||||
ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewChildrenAndProps(node, props, randomInstanceHandle());
|
||||
ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewChildrenAndProps(node, props);
|
||||
|
||||
assertThat(clonedNode.getChildCount()).isZero();
|
||||
}
|
||||
|
@ -299,10 +284,10 @@ public class FabricUIManagerTest {
|
|||
mFabricUIManager.appendChildToSet(childSet, container);
|
||||
mFabricUIManager.completeRoot(rootTag, childSet);
|
||||
|
||||
ReactShadowNode aaClone = mFabricUIManager.cloneNodeWithNewProps(aa, null, 0);
|
||||
ReactShadowNode aClone = mFabricUIManager.cloneNodeWithNewChildren(a, 0);
|
||||
ReactShadowNode aaClone = mFabricUIManager.cloneNodeWithNewProps(aa, null);
|
||||
ReactShadowNode aClone = mFabricUIManager.cloneNodeWithNewChildren(a);
|
||||
mFabricUIManager.appendChild(aClone, aaClone);
|
||||
ReactShadowNode containerClone = mFabricUIManager.cloneNodeWithNewChildren(container, 0);
|
||||
ReactShadowNode containerClone = mFabricUIManager.cloneNodeWithNewChildren(container);
|
||||
mFabricUIManager.appendChild(containerClone, b);
|
||||
mFabricUIManager.appendChild(containerClone, aClone);
|
||||
List<ReactShadowNode> childSet2 = mFabricUIManager.createChildSet(rootTag);
|
||||
|
|
|
@ -85,7 +85,7 @@ public:
|
|||
* shadow nodes.
|
||||
*/
|
||||
virtual SharedEventEmitter createEventEmitter(
|
||||
const InstanceHandle &instanceHandle,
|
||||
const EventTarget &eventTarget,
|
||||
const Tag &tag
|
||||
) const = 0;
|
||||
};
|
||||
|
|
|
@ -113,10 +113,10 @@ public:
|
|||
};
|
||||
|
||||
virtual SharedEventEmitter createEventEmitter(
|
||||
const InstanceHandle &instanceHandle,
|
||||
const EventTarget &eventTarget,
|
||||
const Tag &tag
|
||||
) const override {
|
||||
return std::make_shared<ConcreteEventEmitter>(instanceHandle, tag, eventDispatcher_);
|
||||
return std::make_shared<ConcreteEventEmitter>(eventTarget, tag, eventDispatcher_);
|
||||
}
|
||||
|
||||
protected:
|
||||
|
|
|
@ -28,8 +28,6 @@ class EventDispatcher {
|
|||
|
||||
public:
|
||||
|
||||
virtual EventTarget createEventTarget(const InstanceHandle &instanceHandle) const = 0;
|
||||
|
||||
/*
|
||||
* Dispatches "raw" event using some event-delivery infrastructure.
|
||||
*/
|
||||
|
|
|
@ -12,13 +12,10 @@
|
|||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
EventEmitter::EventEmitter(const InstanceHandle &instanceHandle, const Tag &tag, const SharedEventDispatcher &eventDispatcher):
|
||||
instanceHandle_(instanceHandle),
|
||||
EventEmitter::EventEmitter(const EventTarget &eventTarget, const Tag &tag, const SharedEventDispatcher &eventDispatcher):
|
||||
eventTarget_(eventTarget),
|
||||
tag_(tag),
|
||||
eventDispatcher_(eventDispatcher) {
|
||||
if (eventDispatcher) {
|
||||
eventTarget_ = createEventTarget();
|
||||
}
|
||||
}
|
||||
|
||||
EventEmitter::~EventEmitter() {
|
||||
|
@ -49,11 +46,5 @@ void EventEmitter::dispatchEvent(
|
|||
eventDispatcher->dispatchEvent(eventTarget_, type, extendedPayload, priority);
|
||||
}
|
||||
|
||||
EventTarget EventEmitter::createEventTarget() const {
|
||||
const auto &eventDispatcher = eventDispatcher_.lock();
|
||||
assert(eventDispatcher);
|
||||
return eventDispatcher->createEventTarget(instanceHandle_);
|
||||
}
|
||||
|
||||
} // namespace react
|
||||
} // namespace facebook
|
||||
|
|
|
@ -31,7 +31,7 @@ using SharedEventEmitter = std::shared_ptr<const EventEmitter>;
|
|||
class EventEmitter {
|
||||
|
||||
public:
|
||||
EventEmitter(const InstanceHandle &instanceHandle, const Tag &tag, const SharedEventDispatcher &eventDispatcher);
|
||||
EventEmitter(const EventTarget &eventTarget, const Tag &tag, const SharedEventDispatcher &eventDispatcher);
|
||||
virtual ~EventEmitter();
|
||||
|
||||
protected:
|
||||
|
@ -48,12 +48,9 @@ protected:
|
|||
|
||||
private:
|
||||
|
||||
EventTarget createEventTarget() const;
|
||||
|
||||
InstanceHandle instanceHandle_;
|
||||
mutable EventTarget eventTarget_ {nullptr};
|
||||
Tag tag_;
|
||||
std::weak_ptr<const EventDispatcher> eventDispatcher_;
|
||||
mutable EventTarget eventTarget_ {nullptr};
|
||||
};
|
||||
|
||||
} // namespace react
|
||||
|
|
|
@ -97,12 +97,12 @@ UIManagerDelegate *FabricUIManager::getDelegate() {
|
|||
return delegate_;
|
||||
}
|
||||
|
||||
void FabricUIManager::setCreateEventTargetFunction(std::function<CreateEventTargetFunction> createEventTargetFunction) {
|
||||
createEventTargetFunction_ = createEventTargetFunction;
|
||||
void FabricUIManager::setDispatchEventToEmptyTargetFunction(std::function<DispatchEventToEmptyTargetFunction> dispatchEventFunction) {
|
||||
dispatchEventToEmptyTargetFunction_ = dispatchEventFunction;
|
||||
}
|
||||
|
||||
void FabricUIManager::setDispatchEventFunction(std::function<DispatchEventFunction> dispatchEventFunction) {
|
||||
dispatchEventFunction_ = dispatchEventFunction;
|
||||
void FabricUIManager::setDispatchEventToTargetFunction(std::function<DispatchEventToTargetFunction> dispatchEventFunction) {
|
||||
dispatchEventToTargetFunction_ = dispatchEventFunction;
|
||||
}
|
||||
|
||||
void FabricUIManager::setReleaseEventHandlerFunction(std::function<ReleaseEventHandlerFunction> releaseEventHandlerFunction) {
|
||||
|
@ -113,12 +113,16 @@ void FabricUIManager::setReleaseEventTargetFunction(std::function<ReleaseEventTa
|
|||
releaseEventTargetFunction_ = releaseEventTargetFunction;
|
||||
}
|
||||
|
||||
EventTarget FabricUIManager::createEventTarget(const InstanceHandle &instanceHandle) const {
|
||||
return createEventTargetFunction_(instanceHandle);
|
||||
void FabricUIManager::dispatchEventToEmptyTarget(const std::string &type, const folly::dynamic &payload) const {
|
||||
dispatchEventToEmptyTargetFunction_(
|
||||
eventHandler_,
|
||||
const_cast<std::string &>(type),
|
||||
const_cast<folly::dynamic &>(payload)
|
||||
);
|
||||
}
|
||||
|
||||
void FabricUIManager::dispatchEvent(const EventTarget &eventTarget, const std::string &type, const folly::dynamic &payload) const {
|
||||
dispatchEventFunction_(
|
||||
void FabricUIManager::dispatchEventToTarget(const EventTarget &eventTarget, const std::string &type, const folly::dynamic &payload) const {
|
||||
dispatchEventToTargetFunction_(
|
||||
eventHandler_,
|
||||
eventTarget,
|
||||
const_cast<std::string &>(type),
|
||||
|
@ -130,7 +134,7 @@ void FabricUIManager::releaseEventTarget(const EventTarget &eventTarget) const {
|
|||
releaseEventTargetFunction_(eventTarget);
|
||||
}
|
||||
|
||||
SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int rootTag, folly::dynamic props, InstanceHandle instanceHandle) {
|
||||
SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int rootTag, folly::dynamic props, EventTarget eventTarget) {
|
||||
isLoggingEnabled && LOG(INFO) << "FabricUIManager::createNode(tag: " << tag << ", name: " << viewName << ", rootTag: " << rootTag << ", props: " << props << ")";
|
||||
|
||||
ComponentName componentName = componentNameByReactViewName(viewName);
|
||||
|
@ -141,7 +145,7 @@ SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int
|
|||
componentDescriptor->createShadowNode(
|
||||
tag,
|
||||
rootTag,
|
||||
componentDescriptor->createEventEmitter(instanceHandle, tag),
|
||||
componentDescriptor->createEventEmitter(eventTarget, tag),
|
||||
componentDescriptor->cloneProps(nullptr, rawProps)
|
||||
);
|
||||
|
||||
|
@ -154,7 +158,7 @@ SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int
|
|||
return shadowNode;
|
||||
}
|
||||
|
||||
SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode, InstanceHandle instanceHandle) {
|
||||
SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode) {
|
||||
isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNode(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
|
||||
const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
|
||||
|
||||
|
@ -162,7 +166,7 @@ SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode,
|
|||
componentDescriptor->cloneShadowNode(
|
||||
shadowNode,
|
||||
nullptr,
|
||||
componentDescriptor->createEventEmitter(instanceHandle, shadowNode->getTag()),
|
||||
componentDescriptor->createEventEmitter(nullptr /*TODO(shergin)*/, shadowNode->getTag()),
|
||||
nullptr
|
||||
);
|
||||
|
||||
|
@ -170,7 +174,7 @@ SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode,
|
|||
return clonedShadowNode;
|
||||
}
|
||||
|
||||
SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNode &shadowNode, InstanceHandle instanceHandle) {
|
||||
SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNode &shadowNode) {
|
||||
isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildren(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
|
||||
// Assuming semantic: Cloning with same props but empty children.
|
||||
const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
|
||||
|
@ -179,7 +183,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNod
|
|||
componentDescriptor->cloneShadowNode(
|
||||
shadowNode,
|
||||
nullptr,
|
||||
componentDescriptor->createEventEmitter(instanceHandle, shadowNode->getTag()),
|
||||
componentDescriptor->createEventEmitter(nullptr /*TODO(shergin)*/, shadowNode->getTag()),
|
||||
ShadowNode::emptySharedShadowNodeSharedList()
|
||||
);
|
||||
|
||||
|
@ -187,7 +191,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNod
|
|||
return clonedShadowNode;
|
||||
}
|
||||
|
||||
SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &shadowNode, folly::dynamic props, InstanceHandle instanceHandle) {
|
||||
SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &shadowNode, folly::dynamic props) {
|
||||
isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNodeWithNewProps(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", props: " << props << ")";
|
||||
// Assuming semantic: Cloning with same children and specified props.
|
||||
const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
|
||||
|
@ -197,7 +201,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &
|
|||
componentDescriptor->cloneShadowNode(
|
||||
shadowNode,
|
||||
componentDescriptor->cloneProps(shadowNode->getProps(), rawProps),
|
||||
componentDescriptor->createEventEmitter(instanceHandle, shadowNode->getTag()),
|
||||
componentDescriptor->createEventEmitter(nullptr /*TODO(shergin)*/, shadowNode->getTag()),
|
||||
nullptr
|
||||
);
|
||||
|
||||
|
@ -205,7 +209,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &
|
|||
return clonedShadowNode;
|
||||
}
|
||||
|
||||
SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedShadowNode &shadowNode, folly::dynamic props, InstanceHandle instanceHandle) {
|
||||
SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedShadowNode &shadowNode, folly::dynamic props) {
|
||||
isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildrenAndProps(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", props: " << props << ")";
|
||||
// Assuming semantic: Cloning with empty children and specified props.
|
||||
const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
|
||||
|
@ -215,7 +219,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedS
|
|||
componentDescriptor->cloneShadowNode(
|
||||
shadowNode,
|
||||
componentDescriptor->cloneProps(shadowNode->getProps(), rawProps),
|
||||
componentDescriptor->createEventEmitter(instanceHandle, shadowNode->getTag()),
|
||||
componentDescriptor->createEventEmitter(nullptr /*TODO(shergin)*/, shadowNode->getTag()),
|
||||
ShadowNode::emptySharedShadowNodeSharedList()
|
||||
);
|
||||
|
||||
|
|
|
@ -18,8 +18,8 @@
|
|||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
using CreateEventTargetFunction = EventTarget (InstanceHandle instanceHandle);
|
||||
using DispatchEventFunction = void (EventHandler eventHandler, EventTarget eventTarget, std::string type, folly::dynamic payload);
|
||||
using DispatchEventToEmptyTargetFunction = void (EventHandler eventHandler, std::string type, folly::dynamic payload);
|
||||
using DispatchEventToTargetFunction = void (EventHandler eventHandler, EventTarget eventTarget, std::string type, folly::dynamic payload);
|
||||
using ReleaseEventHandlerFunction = void (EventHandler eventHandler);
|
||||
using ReleaseEventTargetFunction = void (EventTarget eventTarget);
|
||||
|
||||
|
@ -44,24 +44,24 @@ public:
|
|||
/*
|
||||
* Registers callback functions.
|
||||
*/
|
||||
void setCreateEventTargetFunction(std::function<CreateEventTargetFunction> createEventTargetFunction);
|
||||
void setDispatchEventFunction(std::function<DispatchEventFunction> dispatchEventFunction);
|
||||
void setDispatchEventToEmptyTargetFunction(std::function<DispatchEventToEmptyTargetFunction> dispatchEventFunction);
|
||||
void setDispatchEventToTargetFunction(std::function<DispatchEventToTargetFunction> dispatchEventFunction);
|
||||
void setReleaseEventHandlerFunction(std::function<ReleaseEventHandlerFunction> releaseEventHandlerFunction);
|
||||
void setReleaseEventTargetFunction(std::function<ReleaseEventTargetFunction> releaseEventTargetFunction);
|
||||
|
||||
#pragma mark - Native-facing Interface
|
||||
|
||||
EventTarget createEventTarget(const InstanceHandle &instanceHandle) const;
|
||||
void dispatchEvent(const EventTarget &eventTarget, const std::string &type, const folly::dynamic &payload) const;
|
||||
void dispatchEventToEmptyTarget(const std::string &type, const folly::dynamic &payload) const;
|
||||
void dispatchEventToTarget(const EventTarget &eventTarget, const std::string &type, const folly::dynamic &payload) const;
|
||||
void releaseEventTarget(const EventTarget &eventTarget) const;
|
||||
|
||||
#pragma mark - JavaScript/React-facing Interface
|
||||
|
||||
SharedShadowNode createNode(Tag reactTag, std::string viewName, Tag rootTag, folly::dynamic props, InstanceHandle instanceHandle);
|
||||
SharedShadowNode cloneNode(const SharedShadowNode &node, InstanceHandle instanceHandle);
|
||||
SharedShadowNode cloneNodeWithNewChildren(const SharedShadowNode &node, InstanceHandle instanceHandle);
|
||||
SharedShadowNode cloneNodeWithNewProps(const SharedShadowNode &node, folly::dynamic props, InstanceHandle instanceHandle);
|
||||
SharedShadowNode cloneNodeWithNewChildrenAndProps(const SharedShadowNode &node, folly::dynamic newProps, InstanceHandle instanceHandle);
|
||||
SharedShadowNode createNode(Tag reactTag, std::string viewName, Tag rootTag, folly::dynamic props, EventTarget eventTarget);
|
||||
SharedShadowNode cloneNode(const SharedShadowNode &node);
|
||||
SharedShadowNode cloneNodeWithNewChildren(const SharedShadowNode &node);
|
||||
SharedShadowNode cloneNodeWithNewProps(const SharedShadowNode &node, folly::dynamic props);
|
||||
SharedShadowNode cloneNodeWithNewChildrenAndProps(const SharedShadowNode &node, folly::dynamic newProps);
|
||||
void appendChild(const SharedShadowNode &parentNode, const SharedShadowNode &childNode);
|
||||
SharedShadowNodeUnsharedList createChildSet(Tag rootTag);
|
||||
void appendChildToSet(const SharedShadowNodeUnsharedList &childSet, const SharedShadowNode &childNode);
|
||||
|
@ -73,8 +73,8 @@ private:
|
|||
SharedComponentDescriptorRegistry componentDescriptorRegistry_;
|
||||
UIManagerDelegate *delegate_;
|
||||
EventHandler eventHandler_;
|
||||
std::function<CreateEventTargetFunction> createEventTargetFunction_;
|
||||
std::function<DispatchEventFunction> dispatchEventFunction_;
|
||||
std::function<DispatchEventToEmptyTargetFunction> dispatchEventToEmptyTargetFunction_;
|
||||
std::function<DispatchEventToTargetFunction> dispatchEventToTargetFunction_;
|
||||
std::function<ReleaseEventHandlerFunction> releaseEventHandlerFunction_;
|
||||
std::function<ReleaseEventTargetFunction> releaseEventTargetFunction_;
|
||||
};
|
||||
|
|
|
@ -26,11 +26,6 @@ void SchedulerEventDispatcher::setUIManager(std::shared_ptr<const FabricUIManage
|
|||
uiManager_ = uiManager;
|
||||
}
|
||||
|
||||
EventTarget SchedulerEventDispatcher::createEventTarget(const InstanceHandle &instanceHandle) const {
|
||||
assert(uiManager_ && "Attempted to create EventTarget after FabricUIManager dies.");
|
||||
return uiManager_->createEventTarget(instanceHandle);
|
||||
}
|
||||
|
||||
void SchedulerEventDispatcher::dispatchEvent(
|
||||
const EventTarget &eventTarget,
|
||||
const std::string &type,
|
||||
|
@ -41,14 +36,15 @@ void SchedulerEventDispatcher::dispatchEvent(
|
|||
return;
|
||||
}
|
||||
// TODO: Schedule the event based on priority.
|
||||
uiManager_->dispatchEvent(eventTarget, normalizeEventType(type), payload);
|
||||
uiManager_->dispatchEventToTarget(eventTarget, normalizeEventType(type), payload);
|
||||
}
|
||||
|
||||
void SchedulerEventDispatcher::releaseEventTarget(const EventTarget &eventTarget) const {
|
||||
if (!uiManager_) {
|
||||
return;
|
||||
}
|
||||
uiManager_->releaseEventTarget(eventTarget);
|
||||
// TODO(shergin): This needs to move to the destructor of EventEmitter. For now we'll leak.
|
||||
// uiManager_->releaseEventTarget(eventTarget);
|
||||
}
|
||||
|
||||
} // namespace react
|
||||
|
|
|
@ -31,8 +31,6 @@ public:
|
|||
|
||||
#pragma mark - EventDispatcher
|
||||
|
||||
EventTarget createEventTarget(const InstanceHandle &instanceHandle) const override;
|
||||
|
||||
void dispatchEvent(
|
||||
const EventTarget &eventTarget,
|
||||
const std::string &type,
|
||||
|
|
Loading…
Reference in New Issue