Fabric: Simplified way to specialize ComponentName in ConcreteShadowNode class template
Summary: @public Previously, all ConcreteShadowNode subclasses had to override `getComponentName()` function to specialize a name of the component. And often it was all that those subclasses do. Now, it's a template argument; and many ShadowNode classes can be created as oneliners via *just* specializing ConcreteShadowNode template. Unfortunately, C++ does not allow to use `std::string`s or string literals as template arguments, but it allows to use pointers. Moreover, those pointers must point to some linked data, hence, those values must be declared in .cpp (not .h) files. For simplicity, we put those constants in Props classes, (but this is not a strong requirement). Reviewed By: mdvacca Differential Revision: D8942826 fbshipit-source-id: 4fd517e2485eb8f8c20a51df9b3496941856d8a5
This commit is contained in:
parent
88293d391a
commit
67a79010ca
|
@ -5,14 +5,12 @@
|
|||
* LICENSE file in the root directory of this source tree.
|
||||
*/
|
||||
|
||||
#include <fabric/components/activityindicator/ActivityIndicatorViewShadowNode.h>
|
||||
#include "ActivityIndicatorViewShadowNode.h"
|
||||
|
||||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
ComponentName ActivityIndicatorViewShadowNode::getComponentName() const {
|
||||
return ComponentName("ActivityIndicatorView");
|
||||
}
|
||||
const char ActivityIndicatorViewComponentName[] = "ActivityIndicatorView";
|
||||
|
||||
} // namespace react
|
||||
} // namespace facebook
|
||||
|
|
|
@ -13,18 +13,16 @@
|
|||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
extern const char ActivityIndicatorViewComponentName[];
|
||||
|
||||
/*
|
||||
* `ShadowNode` for <ActivityIndicatorView> component.
|
||||
*/
|
||||
class ActivityIndicatorViewShadowNode final:
|
||||
public ConcreteViewShadowNode<ActivityIndicatorViewProps> {
|
||||
|
||||
public:
|
||||
|
||||
using ConcreteViewShadowNode::ConcreteViewShadowNode;
|
||||
|
||||
ComponentName getComponentName() const override;
|
||||
};
|
||||
using ActivityIndicatorViewShadowNode =
|
||||
ConcreteViewShadowNode<
|
||||
ActivityIndicatorViewComponentName,
|
||||
ActivityIndicatorViewProps
|
||||
>;
|
||||
|
||||
} // namespace react
|
||||
} // namespace facebook
|
||||
|
|
|
@ -14,9 +14,7 @@
|
|||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
ComponentName ImageShadowNode::getComponentName() const {
|
||||
return ComponentName("Image");
|
||||
}
|
||||
const char ImageComponentName[] = "Image";
|
||||
|
||||
void ImageShadowNode::setImageManager(const SharedImageManager &imageManager) {
|
||||
ensureUnsealed();
|
||||
|
|
|
@ -16,18 +16,22 @@
|
|||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
extern const char ImageComponentName[];
|
||||
|
||||
/*
|
||||
* `ShadowNode` for <Image> component.
|
||||
*/
|
||||
class ImageShadowNode final:
|
||||
public ConcreteViewShadowNode<ImageProps, ImageEventEmitter> {
|
||||
public ConcreteViewShadowNode<
|
||||
ImageComponentName,
|
||||
ImageProps,
|
||||
ImageEventEmitter
|
||||
> {
|
||||
|
||||
public:
|
||||
|
||||
using ConcreteViewShadowNode::ConcreteViewShadowNode;
|
||||
|
||||
ComponentName getComponentName() const override;
|
||||
|
||||
/*
|
||||
* Associates a shared `ImageManager` with the node.
|
||||
*/
|
||||
|
|
|
@ -24,7 +24,6 @@ class RootProps final:
|
|||
public ViewProps {
|
||||
|
||||
public:
|
||||
|
||||
RootProps() = default;
|
||||
RootProps(
|
||||
const RootProps &sourceProps,
|
||||
|
|
|
@ -12,9 +12,7 @@
|
|||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
ComponentName RootShadowNode::getComponentName() const {
|
||||
return ComponentName("RootView");
|
||||
}
|
||||
const char RootComponentName[] = "RootView";
|
||||
|
||||
void RootShadowNode::layout() {
|
||||
ensureUnsealed();
|
||||
|
|
|
@ -21,6 +21,8 @@ class RootShadowNode;
|
|||
using SharedRootShadowNode = std::shared_ptr<const RootShadowNode>;
|
||||
using UnsharedRootShadowNode = std::shared_ptr<RootShadowNode>;
|
||||
|
||||
extern const char RootComponentName[];
|
||||
|
||||
/*
|
||||
* `ShadowNode` for the root component.
|
||||
* Besides all functionality of the `View` component, `RootShadowNode` contains
|
||||
|
@ -28,14 +30,15 @@ using UnsharedRootShadowNode = std::shared_ptr<RootShadowNode>;
|
|||
* shadow tree.
|
||||
*/
|
||||
class RootShadowNode final:
|
||||
public ConcreteViewShadowNode<RootProps> {
|
||||
public ConcreteViewShadowNode<
|
||||
RootComponentName,
|
||||
RootProps
|
||||
> {
|
||||
|
||||
public:
|
||||
|
||||
using ConcreteViewShadowNode::ConcreteViewShadowNode;
|
||||
|
||||
ComponentName getComponentName() const override;
|
||||
|
||||
/*
|
||||
* Layouts the shadow tree.
|
||||
*/
|
||||
|
|
|
@ -14,9 +14,7 @@
|
|||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
ComponentName ScrollViewShadowNode::getComponentName() const {
|
||||
return ComponentName("ScrollView");
|
||||
}
|
||||
const char ScrollViewComponentName[] = "ScrollView";
|
||||
|
||||
void ScrollViewShadowNode::updateLocalData() {
|
||||
ensureUnsealed();
|
||||
|
|
|
@ -7,8 +7,6 @@
|
|||
|
||||
#pragma once
|
||||
|
||||
#include <memory>
|
||||
|
||||
#include <fabric/components/scrollview/ScrollViewEventEmitter.h>
|
||||
#include <fabric/components/scrollview/ScrollViewProps.h>
|
||||
#include <fabric/components/view/ConcreteViewShadowNode.h>
|
||||
|
@ -17,22 +15,22 @@
|
|||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
class ScrollViewShadowNode;
|
||||
|
||||
using SharedScrollViewShadowNode = std::shared_ptr<const ScrollViewShadowNode>;
|
||||
extern const char ScrollViewComponentName[];
|
||||
|
||||
/*
|
||||
* `ShadowNode` for <ScrollView> component.
|
||||
*/
|
||||
class ScrollViewShadowNode final:
|
||||
public ConcreteViewShadowNode<ScrollViewProps, ScrollViewEventEmitter> {
|
||||
public ConcreteViewShadowNode<
|
||||
ScrollViewComponentName,
|
||||
ScrollViewProps,
|
||||
ScrollViewEventEmitter
|
||||
> {
|
||||
|
||||
public:
|
||||
|
||||
using ConcreteViewShadowNode::ConcreteViewShadowNode;
|
||||
|
||||
ComponentName getComponentName() const override;
|
||||
|
||||
#pragma mark - LayoutableShadowNode
|
||||
|
||||
void layout(LayoutContext layoutContext) override;
|
||||
|
|
|
@ -5,14 +5,12 @@
|
|||
* LICENSE file in the root directory of this source tree.
|
||||
*/
|
||||
|
||||
#include <fabric/components/switch/SwitchShadowNode.h>
|
||||
#include "SwitchShadowNode.h"
|
||||
|
||||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
ComponentName SwitchShadowNode::getComponentName() const {
|
||||
return ComponentName("Switch");
|
||||
}
|
||||
extern const char SwitchComponentName[] = "Switch";
|
||||
|
||||
} // namespace react
|
||||
} // namespace facebook
|
||||
|
|
|
@ -14,18 +14,17 @@
|
|||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
extern const char SwitchComponentName[];
|
||||
|
||||
/*
|
||||
* `ShadowNode` for <Switch> component.
|
||||
*/
|
||||
class SwitchShadowNode final:
|
||||
public ConcreteViewShadowNode<SwitchProps, SwitchEventEmitter> {
|
||||
|
||||
public:
|
||||
|
||||
using ConcreteViewShadowNode::ConcreteViewShadowNode;
|
||||
|
||||
ComponentName getComponentName() const override;
|
||||
};
|
||||
using SwitchShadowNode =
|
||||
ConcreteViewShadowNode<
|
||||
SwitchComponentName,
|
||||
SwitchProps,
|
||||
SwitchEventEmitter
|
||||
>;
|
||||
|
||||
} // namespace react
|
||||
} // namespace facebook
|
||||
|
|
|
@ -24,7 +24,7 @@ AttributedString BaseTextShadowNode::getAttributedString(
|
|||
|
||||
for (const auto &childNode : *childNodes) {
|
||||
// RawShadowNode
|
||||
SharedRawTextShadowNode rawTextShadowNode = std::dynamic_pointer_cast<const RawTextShadowNode>(childNode);
|
||||
auto rawTextShadowNode = std::dynamic_pointer_cast<const RawTextShadowNode>(childNode);
|
||||
if (rawTextShadowNode) {
|
||||
AttributedString::Fragment fragment;
|
||||
fragment.string = rawTextShadowNode->getProps()->text;
|
||||
|
@ -34,7 +34,7 @@ AttributedString BaseTextShadowNode::getAttributedString(
|
|||
}
|
||||
|
||||
// TextShadowNode
|
||||
SharedTextShadowNode textShadowNode = std::dynamic_pointer_cast<const TextShadowNode>(childNode);
|
||||
auto textShadowNode = std::dynamic_pointer_cast<const TextShadowNode>(childNode);
|
||||
if (textShadowNode) {
|
||||
TextAttributes localTextAttributes = textAttributes;
|
||||
localTextAttributes.apply(textShadowNode->getProps()->textAttributes);
|
||||
|
|
|
@ -30,7 +30,7 @@ public:
|
|||
}
|
||||
|
||||
void adopt(UnsharedShadowNode shadowNode) const override {
|
||||
ConcreteComponentDescriptor<ParagraphShadowNode>::adopt(shadowNode);
|
||||
ConcreteComponentDescriptor::adopt(shadowNode);
|
||||
|
||||
assert(std::dynamic_pointer_cast<ParagraphShadowNode>(shadowNode));
|
||||
auto paragraphShadowNode = std::static_pointer_cast<ParagraphShadowNode>(shadowNode);
|
||||
|
|
|
@ -18,10 +18,6 @@
|
|||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
class ParagraphProps;
|
||||
|
||||
using SharedParagraphProps = std::shared_ptr<const ParagraphProps>;
|
||||
|
||||
/*
|
||||
* Props of <Paragraph> component.
|
||||
* Most of the props are directly stored in composed `ParagraphAttributes`
|
||||
|
|
|
@ -7,16 +7,12 @@
|
|||
|
||||
#include "ParagraphShadowNode.h"
|
||||
|
||||
#include <fabric/debug/DebugStringConvertibleItem.h>
|
||||
|
||||
#import "ParagraphLocalData.h"
|
||||
#include "ParagraphLocalData.h"
|
||||
|
||||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
ComponentName ParagraphShadowNode::getComponentName() const {
|
||||
return ComponentName("Paragraph");
|
||||
}
|
||||
const char ParagraphComponentName[] = "Paragraph";
|
||||
|
||||
AttributedString ParagraphShadowNode::getAttributedString() const {
|
||||
if (!cachedAttributedString_.has_value()) {
|
||||
|
@ -53,7 +49,7 @@ Size ParagraphShadowNode::measure(LayoutConstraints layoutConstraints) const {
|
|||
|
||||
void ParagraphShadowNode::layout(LayoutContext layoutContext) {
|
||||
updateLocalData();
|
||||
ConcreteViewShadowNode<ParagraphProps>::layout(layoutContext);
|
||||
ConcreteViewShadowNode::layout(layoutContext);
|
||||
}
|
||||
|
||||
} // namespace react
|
||||
|
|
|
@ -19,9 +19,7 @@
|
|||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
class ParagraphShadowNode;
|
||||
|
||||
using SharedParagraphShadowNode = std::shared_ptr<const ParagraphShadowNode>;
|
||||
extern const char ParagraphComponentName[];
|
||||
|
||||
/*
|
||||
* `ShadowNode` for <Paragraph> component, represents <View>-like component
|
||||
|
@ -29,15 +27,16 @@ using SharedParagraphShadowNode = std::shared_ptr<const ParagraphShadowNode>;
|
|||
* and <RawText> components.
|
||||
*/
|
||||
class ParagraphShadowNode:
|
||||
public ConcreteViewShadowNode<ParagraphProps>,
|
||||
public ConcreteViewShadowNode<
|
||||
ParagraphComponentName,
|
||||
ParagraphProps
|
||||
>,
|
||||
public BaseTextShadowNode {
|
||||
|
||||
public:
|
||||
|
||||
using ConcreteViewShadowNode::ConcreteViewShadowNode;
|
||||
|
||||
ComponentName getComponentName() const override;
|
||||
|
||||
/*
|
||||
* Returns a `AttributedString` which represents text content of the node.
|
||||
*/
|
||||
|
|
|
@ -23,7 +23,6 @@ class RawTextProps:
|
|||
public Props {
|
||||
|
||||
public:
|
||||
|
||||
RawTextProps() = default;
|
||||
RawTextProps(const RawTextProps &sourceProps, const RawProps &rawProps);
|
||||
|
||||
|
|
|
@ -7,14 +7,10 @@
|
|||
|
||||
#include "RawTextShadowNode.h"
|
||||
|
||||
#include <fabric/debug/DebugStringConvertibleItem.h>
|
||||
|
||||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
ComponentName RawTextShadowNode::getComponentName() const {
|
||||
return ComponentName("RawText");
|
||||
}
|
||||
extern const char RawTextComponentName[] = "RawText";
|
||||
|
||||
} // namespace react
|
||||
} // namespace facebook
|
||||
|
|
|
@ -7,18 +7,13 @@
|
|||
|
||||
#pragma once
|
||||
|
||||
#include <memory>
|
||||
|
||||
#include <fabric/components/text/RawTextProps.h>
|
||||
#include <fabric/core/ConcreteShadowNode.h>
|
||||
#include <fabric/core/ShadowNode.h>
|
||||
|
||||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
class RawTextShadowNode;
|
||||
|
||||
using SharedRawTextShadowNode = std::shared_ptr<const RawTextShadowNode>;
|
||||
extern const char RawTextComponentName[];
|
||||
|
||||
/*
|
||||
* `ShadowNode` for <RawText> component, represents a purely regular string
|
||||
|
@ -26,14 +21,11 @@ using SharedRawTextShadowNode = std::shared_ptr<const RawTextShadowNode>;
|
|||
* is represented as `<RawText text="Hello!"/>`.
|
||||
* <RawText> component must not have any children.
|
||||
*/
|
||||
class RawTextShadowNode:
|
||||
public ConcreteShadowNode<RawTextProps> {
|
||||
|
||||
public:
|
||||
using ConcreteShadowNode::ConcreteShadowNode;
|
||||
|
||||
ComponentName getComponentName() const override;
|
||||
};
|
||||
using RawTextShadowNode =
|
||||
ConcreteShadowNode<
|
||||
RawTextComponentName,
|
||||
RawTextProps
|
||||
>;
|
||||
|
||||
} // namespace react
|
||||
} // namespace facebook
|
||||
|
|
|
@ -16,16 +16,11 @@
|
|||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
class TextProps;
|
||||
|
||||
using SharedTextProps = std::shared_ptr<const TextProps>;
|
||||
|
||||
class TextProps:
|
||||
public Props,
|
||||
public BaseTextProps {
|
||||
|
||||
public:
|
||||
|
||||
TextProps() = default;
|
||||
TextProps(const TextProps &sourceProps, const RawProps &rawProps);
|
||||
|
||||
|
|
|
@ -7,14 +7,10 @@
|
|||
|
||||
#include "TextShadowNode.h"
|
||||
|
||||
#include <fabric/debug/DebugStringConvertibleItem.h>
|
||||
|
||||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
ComponentName TextShadowNode::getComponentName() const {
|
||||
return ComponentName("Text");
|
||||
}
|
||||
extern const char TextComponentName[] = "Text";
|
||||
|
||||
} // namespace react
|
||||
} // namespace facebook
|
||||
|
|
|
@ -7,30 +7,25 @@
|
|||
|
||||
#pragma once
|
||||
|
||||
#include <fabric/attributedstring/AttributedString.h>
|
||||
#include <fabric/attributedstring/TextAttributes.h>
|
||||
#include <fabric/components/text/BaseTextShadowNode.h>
|
||||
#include <fabric/components/text/TextProps.h>
|
||||
#include <fabric/components/text/TextShadowNode.h>
|
||||
#include <fabric/core/ConcreteShadowNode.h>
|
||||
#include <fabric/core/ShadowNode.h>
|
||||
|
||||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
class TextShadowNode;
|
||||
|
||||
using SharedTextShadowNode = std::shared_ptr<const TextShadowNode>;
|
||||
extern const char TextComponentName[];
|
||||
|
||||
class TextShadowNode:
|
||||
public ConcreteShadowNode<TextProps>,
|
||||
public ConcreteShadowNode<
|
||||
TextComponentName,
|
||||
TextProps
|
||||
>,
|
||||
public BaseTextShadowNode {
|
||||
|
||||
public:
|
||||
|
||||
using ConcreteShadowNode::ConcreteShadowNode;
|
||||
|
||||
ComponentName getComponentName() const override;
|
||||
};
|
||||
|
||||
} // namespace react
|
||||
|
|
|
@ -24,9 +24,17 @@ namespace react {
|
|||
* as <View> and similar basic behaviour).
|
||||
* For example: <Paragraph>, <Image>, but not <Text>, <RawText>.
|
||||
*/
|
||||
template <typename ViewPropsT = ViewProps, typename ViewEventEmitterT = ViewEventEmitter>
|
||||
template <
|
||||
const char *concreteComponentName,
|
||||
typename ViewPropsT = ViewProps,
|
||||
typename ViewEventEmitterT = ViewEventEmitter
|
||||
>
|
||||
class ConcreteViewShadowNode:
|
||||
public ConcreteShadowNode<ViewPropsT, ViewEventEmitterT>,
|
||||
public ConcreteShadowNode<
|
||||
concreteComponentName,
|
||||
ViewPropsT,
|
||||
ViewEventEmitterT
|
||||
>,
|
||||
public AccessibleShadowNode,
|
||||
public YogaLayoutableShadowNode {
|
||||
|
||||
|
@ -50,7 +58,7 @@ public:
|
|||
const SharedShadowNodeSharedList &children,
|
||||
const ShadowNodeCloneFunction &cloneFunction
|
||||
):
|
||||
ConcreteShadowNode<ViewPropsT, ViewEventEmitterT>(
|
||||
ConcreteShadowNode<concreteComponentName, ViewPropsT, ViewEventEmitterT>(
|
||||
tag,
|
||||
rootTag,
|
||||
props,
|
||||
|
@ -64,7 +72,7 @@ public:
|
|||
YogaLayoutableShadowNode() {
|
||||
|
||||
YogaLayoutableShadowNode::setProps(*props);
|
||||
YogaLayoutableShadowNode::setChildren(ConcreteShadowNode<ViewPropsT, ViewEventEmitterT>::template getChildrenSlice<YogaLayoutableShadowNode>());
|
||||
YogaLayoutableShadowNode::setChildren(ConcreteShadowNode<concreteComponentName, ViewPropsT, ViewEventEmitterT>::template getChildrenSlice<YogaLayoutableShadowNode>());
|
||||
};
|
||||
|
||||
ConcreteViewShadowNode(
|
||||
|
@ -73,7 +81,7 @@ public:
|
|||
const SharedConcreteViewEventEmitter &eventEmitter,
|
||||
const SharedShadowNodeSharedList &children
|
||||
):
|
||||
ConcreteShadowNode<ViewPropsT, ViewEventEmitterT>(
|
||||
ConcreteShadowNode<concreteComponentName, ViewPropsT, ViewEventEmitterT>(
|
||||
shadowNode,
|
||||
props,
|
||||
eventEmitter,
|
||||
|
@ -92,7 +100,7 @@ public:
|
|||
}
|
||||
|
||||
if (children) {
|
||||
YogaLayoutableShadowNode::setChildren(ConcreteShadowNode<ViewPropsT, ViewEventEmitterT>::template getChildrenSlice<YogaLayoutableShadowNode>());
|
||||
YogaLayoutableShadowNode::setChildren(ConcreteShadowNode<concreteComponentName, ViewPropsT, ViewEventEmitterT>::template getChildrenSlice<YogaLayoutableShadowNode>());
|
||||
}
|
||||
};
|
||||
|
||||
|
|
|
@ -27,7 +27,6 @@ class ViewProps:
|
|||
public AccessibilityProps {
|
||||
|
||||
public:
|
||||
|
||||
ViewProps() = default;
|
||||
ViewProps(const YGStyle &yogaStyle);
|
||||
ViewProps(const ViewProps &sourceProps, const RawProps &rawProps);
|
||||
|
|
|
@ -10,9 +10,7 @@
|
|||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
ComponentName ViewShadowNode::getComponentName() const {
|
||||
return ComponentName("View");
|
||||
}
|
||||
const char ViewComponentName[] = "View";
|
||||
|
||||
} // namespace react
|
||||
} // namespace facebook
|
||||
|
|
|
@ -7,27 +7,20 @@
|
|||
|
||||
#pragma once
|
||||
|
||||
#include <memory>
|
||||
|
||||
#include <fabric/components/view/ViewProps.h>
|
||||
#include <fabric/components/view/ConcreteViewShadowNode.h>
|
||||
|
||||
namespace facebook {
|
||||
namespace react {
|
||||
|
||||
class ViewShadowNode;
|
||||
extern const char ViewComponentName[];
|
||||
|
||||
using SharedViewShadowNode = std::shared_ptr<const ViewShadowNode>;
|
||||
|
||||
class ViewShadowNode final:
|
||||
public ConcreteViewShadowNode<ViewProps, ViewEventEmitter> {
|
||||
|
||||
public:
|
||||
|
||||
using ConcreteViewShadowNode::ConcreteViewShadowNode;
|
||||
|
||||
ComponentName getComponentName() const override;
|
||||
};
|
||||
using ViewShadowNode =
|
||||
ConcreteViewShadowNode<
|
||||
ViewComponentName,
|
||||
ViewProps,
|
||||
ViewEventEmitter
|
||||
>;
|
||||
|
||||
} // namespace react
|
||||
} // namespace facebook
|
||||
|
|
|
@ -37,22 +37,11 @@ public:
|
|||
eventDispatcher_(eventDispatcher) {}
|
||||
|
||||
ComponentHandle getComponentHandle() const override {
|
||||
return typeid(ShadowNodeT).hash_code();
|
||||
return ShadowNodeT::Handle();
|
||||
}
|
||||
|
||||
ComponentName getComponentName() const override {
|
||||
// Even if this looks suboptimal, it is the only way to call
|
||||
// a virtual non-static method of `ShadowNodeT`.
|
||||
// Because it is not a hot path (it is executed once per an app run),
|
||||
// it's fine.
|
||||
return std::make_shared<ShadowNodeT>(
|
||||
0,
|
||||
0,
|
||||
std::make_shared<const ConcreteProps>(),
|
||||
nullptr,
|
||||
ShadowNode::emptySharedShadowNodeSharedList(),
|
||||
nullptr
|
||||
)->ShadowNodeT::getComponentName();
|
||||
return ShadowNodeT::Name();
|
||||
}
|
||||
|
||||
SharedShadowNode createShadowNode(
|
||||
|
@ -74,6 +63,7 @@ public:
|
|||
);
|
||||
|
||||
adopt(shadowNode);
|
||||
|
||||
return shadowNode;
|
||||
}
|
||||
|
||||
|
@ -123,6 +113,7 @@ protected:
|
|||
|
||||
virtual void adopt(UnsharedShadowNode shadowNode) const {
|
||||
// Default implementation does nothing.
|
||||
assert(shadowNode->getComponentHandle() == getComponentHandle());
|
||||
}
|
||||
|
||||
private:
|
||||
|
|
|
@ -35,7 +35,7 @@ using SharedRawProps = std::shared_ptr<const RawProps>;
|
|||
* Practically, it's something that concrete ShadowNode and concrete
|
||||
* ComponentDescriptor have in common.
|
||||
*/
|
||||
using ComponentHandle = size_t;
|
||||
using ComponentHandle = int64_t;
|
||||
|
||||
/*
|
||||
* String identifier for components used for addressing them from
|
||||
|
|
|
@ -19,7 +19,11 @@ namespace react {
|
|||
* `ConcreteShadowNode` is a default implementation of `ShadowNode` interface
|
||||
* with many handy features.
|
||||
*/
|
||||
template <typename PropsT, typename EventEmitterT = EventEmitter>
|
||||
template <
|
||||
const char *concreteComponentName,
|
||||
typename PropsT,
|
||||
typename EventEmitterT = EventEmitter
|
||||
>
|
||||
class ConcreteShadowNode: public ShadowNode {
|
||||
static_assert(std::is_base_of<Props, PropsT>::value, "PropsT must be a descendant of Props");
|
||||
|
||||
|
@ -30,6 +34,14 @@ public:
|
|||
using SharedConcreteEventEmitter = std::shared_ptr<const EventEmitterT>;
|
||||
using SharedConcreteShadowNode = std::shared_ptr<const ConcreteShadowNode>;
|
||||
|
||||
static ComponentName Name() {
|
||||
return ComponentName(concreteComponentName);
|
||||
}
|
||||
|
||||
static ComponentHandle Handle() {
|
||||
return ComponentHandle(concreteComponentName);
|
||||
}
|
||||
|
||||
static SharedConcreteProps Props(const RawProps &rawProps, const SharedProps &baseProps = nullptr) {
|
||||
return std::make_shared<const PropsT>(baseProps ? *std::static_pointer_cast<const PropsT>(baseProps) : PropsT(), rawProps);
|
||||
}
|
||||
|
@ -69,8 +81,12 @@ public:
|
|||
children
|
||||
) {}
|
||||
|
||||
virtual ComponentHandle getComponentHandle() const {
|
||||
return typeid(*this).hash_code();
|
||||
ComponentName getComponentName() const override {
|
||||
return ComponentName(concreteComponentName);
|
||||
}
|
||||
|
||||
ComponentHandle getComponentHandle() const override {
|
||||
return reinterpret_cast<ComponentHandle>(concreteComponentName);
|
||||
}
|
||||
|
||||
const SharedConcreteProps getProps() const {
|
||||
|
|
|
@ -14,7 +14,8 @@ using namespace facebook::react;
|
|||
TEST(ComponentDescriptorTest, createShadowNode) {
|
||||
SharedComponentDescriptor descriptor = std::make_shared<TestComponentDescriptor>(nullptr);
|
||||
|
||||
ASSERT_EQ(descriptor->getComponentHandle(), typeid(TestShadowNode).hash_code());
|
||||
ASSERT_EQ(descriptor->getComponentHandle(), TestShadowNode::Handle());
|
||||
ASSERT_STREQ(descriptor->getComponentName().c_str(), TestShadowNode::Name().c_str());
|
||||
ASSERT_STREQ(descriptor->getComponentName().c_str(), "Test");
|
||||
|
||||
RawProps raw;
|
||||
|
@ -22,7 +23,8 @@ TEST(ComponentDescriptorTest, createShadowNode) {
|
|||
SharedProps props = descriptor->cloneProps(nullptr, raw);
|
||||
SharedShadowNode node = descriptor->createShadowNode(9, 1, descriptor->createEventEmitter(0, 9), props);
|
||||
|
||||
ASSERT_EQ(node->getComponentHandle(), typeid(TestShadowNode).hash_code());
|
||||
ASSERT_EQ(node->getComponentHandle(), TestShadowNode::Handle());
|
||||
ASSERT_STREQ(node->getComponentName().c_str(), TestShadowNode::Name().c_str());
|
||||
ASSERT_STREQ(node->getComponentName().c_str(), "Test");
|
||||
ASSERT_EQ(node->getTag(), 9);
|
||||
ASSERT_EQ(node->getRootTag(), 1);
|
||||
|
@ -38,7 +40,6 @@ TEST(ComponentDescriptorTest, cloneShadowNode) {
|
|||
SharedShadowNode node = descriptor->createShadowNode(9, 1, descriptor->createEventEmitter(0, 9), props);
|
||||
SharedShadowNode cloned = descriptor->cloneShadowNode(node);
|
||||
|
||||
ASSERT_EQ(cloned->getComponentHandle(), typeid(TestShadowNode).hash_code());
|
||||
ASSERT_STREQ(cloned->getComponentName().c_str(), "Test");
|
||||
ASSERT_EQ(cloned->getTag(), 9);
|
||||
ASSERT_EQ(cloned->getRootTag(), 1);
|
||||
|
|
|
@ -35,8 +35,6 @@ TEST(ShadowNodeTest, handleShadowNodeCreation) {
|
|||
ASSERT_EQ(node->getTag(), 9);
|
||||
ASSERT_EQ(node->getRootTag(), 1);
|
||||
ASSERT_EQ(node->getEventEmitter(), nullptr);
|
||||
TestShadowNode *nodePtr = node.get();
|
||||
ASSERT_EQ(node->getComponentHandle(), typeid(*nodePtr).hash_code());
|
||||
ASSERT_EQ(node->getChildren()->size(), 0);
|
||||
|
||||
ASSERT_STREQ(node->getProps()->nativeId.c_str(), "testNativeID");
|
||||
|
|
|
@ -36,6 +36,8 @@ private:
|
|||
int number_ {0};
|
||||
};
|
||||
|
||||
static const char TestComponentName[] = "Test";
|
||||
|
||||
class TestProps : public Props {
|
||||
public:
|
||||
using Props::Props;
|
||||
|
@ -46,21 +48,12 @@ using SharedTestProps = std::shared_ptr<const TestProps>;
|
|||
|
||||
class TestShadowNode;
|
||||
using SharedTestShadowNode = std::shared_ptr<const TestShadowNode>;
|
||||
class TestShadowNode : public ConcreteShadowNode<TestProps> {
|
||||
class TestShadowNode : public ConcreteShadowNode<TestComponentName, TestProps> {
|
||||
public:
|
||||
using ConcreteShadowNode::ConcreteShadowNode;
|
||||
|
||||
ComponentName getComponentName() const override {
|
||||
return ComponentName("Test");
|
||||
}
|
||||
};
|
||||
|
||||
class TestComponentDescriptor: public ConcreteComponentDescriptor<TestShadowNode> {
|
||||
public:
|
||||
using ConcreteComponentDescriptor::ConcreteComponentDescriptor;
|
||||
|
||||
// TODO (shergin): Why does this gets repeated here and the shadow node class?
|
||||
ComponentName getComponentName() const override {
|
||||
return "Test";
|
||||
}
|
||||
};
|
||||
|
|
Loading…
Reference in New Issue