Doing some code spelunging with weiliangc@ and vollick@, we believe we discovered that the code for source_index in property_tree_builder.cc is more complicated than is necessary.
The current calculation is as follows:
LayerType* transform_parent = GetTransformParent(data_from_ancestor, layer);
DCHECK(is_root || transform_parent);
int parent_index = TransformTree::kRootNodeId;
if (transform_parent)
parent_index = transform_parent->transform_tree_index();
int source_index = parent_index
gfx::Vector2dF source_offset;
if (transform_parent) {
if (ScrollParent(layer)) {
LayerType* source = Parent(layer);
source_offset += source->offset_to_transform_parent();
source_index = source->transform_tree_index();
} else if (!is_fixed) {
source_offset = transform_parent->offset_to_transform_parent();
} else {
source_offset = data_from_ancestor.transform_tree_parent
->offset_to_transform_parent();
source_index =
data_from_ancestor.transform_tree_parent->transform_tree_index();
}
}
Where GetTransformParent expands to:
return PositionConstraint(layer).is_fixed_position()
? data.transform_fixed_parent
: data.transform_tree_parent;
So, there are four paths to take here (each assuming that the above are false).
1. transform_parent is nullptr. Here, source_index = parent_index = TransformTree::kRootNodeId.
2. The layer has a ScrollParent. Here, source_index = Parent(layer)->transform_tree_index();
3. The layer is not fixed. Here, source_index = parent_index = GetTransformParent(data_from_ancestor, layer)->transform_tree_index() = data_from_ancestor.transform_tree_parent->transform_tree_index();
4. The layer is fixed. Here, source_index = data_from_ancestor.transform_tree_parent->transform_tree_index();
Our belief is that cases #2-4 can be simplified to source_index = Parent(layer)->transform_tree_index(), and that this is really what the poorly documented 'source' represents (our 'source' layer in the layer tree).
To show this, let us look at what 'data_from_ancestor' is. It is part of the BuildPropertyTreesInternal recursion, and its name in the parent call is 'data_for_children'. And during the 'AddTransformNodeIfNeeded' for that parent call, whether or not we add a transform node for the particular layer, we have:
data_for_children->transform_tree_parent = layer;
So, data_from_ancestor.transform_tree_parent is always the Layer that precedes us in the BuildPropertyTreesInternal. But is that always our Parent(layer)? Nope! However, it is always either our Parent(layer) or our ScrollParent(layer), and in the latter case we already override source_index to be Parent(layer)->transform_tree_index()!
Hopefully that makes sense.
Comment 1 by bugdroid1@chromium.org
, Apr 4 2017