Include transform property when calling getRelativeLayoutMetrics
Summary: Changelog: [Internal] Current implementation of `measure` doesn't take transform into account.. So if you had a view which has width and height 100 and had `Scale(0.5, 0.5, 1)` (this will shrink view by half). Calling `getRelativeLayoutMetrics` would report its size being `{100, 100}`. This applies if view's parent has transformation as well, because transformation is applied to all subviews of the view as well. Reviewed By: mdvacca Differential Revision: D20621590 fbshipit-source-id: 2cf902a0494291c821ecada56f810c5e6620db5a
This commit is contained in:
Родитель
26b209431b
Коммит
bbd91446dd
|
@ -55,15 +55,15 @@ static LayoutMetrics calculateOffsetForLayoutMetrics(
|
|||
return EmptyLayoutMetrics;
|
||||
}
|
||||
|
||||
auto origin = layoutableCurrentShadowNode->getLayoutMetrics().frame.origin;
|
||||
auto frame = layoutableCurrentShadowNode->getLayoutMetrics().frame;
|
||||
|
||||
if (policy.includeTransform) {
|
||||
// The check for ScrollView will be implemented after we have
|
||||
// a dedicated trait (part of `ShadowNodeTraits`) for that.
|
||||
origin = origin * layoutableCurrentShadowNode->getTransform();
|
||||
layoutMetrics.frame.size = layoutMetrics.frame.size *
|
||||
layoutableCurrentShadowNode->getTransform();
|
||||
frame = frame * layoutableCurrentShadowNode->getTransform();
|
||||
}
|
||||
|
||||
layoutMetrics.frame.origin += origin;
|
||||
layoutMetrics.frame.origin += frame.origin;
|
||||
}
|
||||
return layoutMetrics;
|
||||
}
|
||||
|
@ -132,9 +132,13 @@ LayoutMetrics LayoutableShadowNode::getRelativeLayoutMetrics(
|
|||
return EmptyLayoutMetrics;
|
||||
}
|
||||
|
||||
auto layoutMetrics = dynamic_cast<LayoutableShadowNode const *>(newestChild)
|
||||
->getLayoutMetrics();
|
||||
|
||||
auto layoutableNewestChild =
|
||||
dynamic_cast<LayoutableShadowNode const *>(newestChild);
|
||||
auto layoutMetrics = layoutableNewestChild->getLayoutMetrics();
|
||||
if (policy.includeTransform) {
|
||||
layoutMetrics.frame =
|
||||
layoutMetrics.frame * layoutableNewestChild->getTransform();
|
||||
}
|
||||
return calculateOffsetForLayoutMetrics(layoutMetrics, ancestors, policy);
|
||||
}
|
||||
|
||||
|
|
|
@ -71,14 +71,33 @@ class LayoutableShadowNodeTest : public ::testing::Test {
|
|||
familyAAA,
|
||||
traits);
|
||||
|
||||
auto familyAAAA = std::make_shared<ShadowNodeFamily>(
|
||||
ShadowNodeFamilyFragment{
|
||||
/* .tag = */ 11,
|
||||
/* .surfaceId = */ 1,
|
||||
/* .eventEmitter = */ nullptr,
|
||||
},
|
||||
eventDispatcher_,
|
||||
componentDescriptor_);
|
||||
|
||||
nodeAAAA_ = std::make_shared<TestShadowNode>(
|
||||
ShadowNodeFragment{
|
||||
/* .props = */ std::make_shared<const TestProps>(),
|
||||
/* .children = */ ShadowNode::emptySharedShadowNodeSharedList(),
|
||||
},
|
||||
familyAAAA,
|
||||
traits);
|
||||
|
||||
nodeA_->appendChild(nodeAA_);
|
||||
nodeAA_->appendChild(nodeAAA_);
|
||||
nodeAAA_->appendChild(nodeAAAA_);
|
||||
}
|
||||
|
||||
std::shared_ptr<EventDispatcher const> eventDispatcher_;
|
||||
std::shared_ptr<TestShadowNode> nodeA_;
|
||||
std::shared_ptr<TestShadowNode> nodeAA_;
|
||||
std::shared_ptr<TestShadowNode> nodeAAA_;
|
||||
std::shared_ptr<TestShadowNode> nodeAAAA_;
|
||||
TestComponentDescriptor componentDescriptor_;
|
||||
};
|
||||
|
||||
|
@ -98,6 +117,50 @@ TEST_F(LayoutableShadowNodeTest, relativeLayoutMetrics) {
|
|||
EXPECT_EQ(relativeLayoutMetrics.frame.origin.y, 20);
|
||||
}
|
||||
|
||||
TEST_F(LayoutableShadowNodeTest, relativeLayoutMetricsOnTransformedNode) {
|
||||
auto layoutMetrics = EmptyLayoutMetrics;
|
||||
layoutMetrics.frame.size = {1000, 1000};
|
||||
nodeA_->setLayoutMetrics(layoutMetrics);
|
||||
|
||||
layoutMetrics.frame.origin = {10, 20};
|
||||
layoutMetrics.frame.size = {100, 200};
|
||||
nodeAA_->_transform = Transform::Scale(0.5, 0.5, 1);
|
||||
nodeAA_->setLayoutMetrics(layoutMetrics);
|
||||
|
||||
auto relativeLayoutMetrics = nodeAA_->getRelativeLayoutMetrics(*nodeA_, {});
|
||||
|
||||
EXPECT_EQ(relativeLayoutMetrics.frame.origin.x, 35);
|
||||
EXPECT_EQ(relativeLayoutMetrics.frame.origin.y, 70);
|
||||
|
||||
EXPECT_EQ(relativeLayoutMetrics.frame.size.width, 50);
|
||||
EXPECT_EQ(relativeLayoutMetrics.frame.size.height, 100);
|
||||
}
|
||||
|
||||
TEST_F(LayoutableShadowNodeTest, relativeLayoutMetricsOnTransformedParent) {
|
||||
auto layoutMetrics = EmptyLayoutMetrics;
|
||||
layoutMetrics.frame.size = {1000, 1000};
|
||||
nodeA_->setLayoutMetrics(layoutMetrics);
|
||||
nodeAA_->setLayoutMetrics(layoutMetrics);
|
||||
|
||||
layoutMetrics.frame.origin = {10, 10};
|
||||
layoutMetrics.frame.size = {100, 100};
|
||||
nodeAAA_->_transform = Transform::Scale(0.5, 0.5, 1);
|
||||
nodeAAA_->setLayoutMetrics(layoutMetrics);
|
||||
|
||||
layoutMetrics.frame.origin = {10, 10};
|
||||
layoutMetrics.frame.size = {50, 50};
|
||||
nodeAAAA_->setLayoutMetrics(layoutMetrics);
|
||||
|
||||
auto relativeLayoutMetrics =
|
||||
nodeAAAA_->getRelativeLayoutMetrics(*nodeAA_, {});
|
||||
|
||||
EXPECT_EQ(relativeLayoutMetrics.frame.origin.x, 45);
|
||||
EXPECT_EQ(relativeLayoutMetrics.frame.origin.y, 45);
|
||||
|
||||
EXPECT_EQ(relativeLayoutMetrics.frame.size.width, 25);
|
||||
EXPECT_EQ(relativeLayoutMetrics.frame.size.height, 25);
|
||||
}
|
||||
|
||||
TEST_F(LayoutableShadowNodeTest, relativeLayoutMetricsOnSameNode) {
|
||||
auto layoutMetrics = EmptyLayoutMetrics;
|
||||
layoutMetrics.frame.origin = {10, 20};
|
||||
|
|
Загрузка…
Ссылка в новой задаче