Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(256)

Side by Side Diff: third_party/WebKit/Source/core/page/scrolling/SnapCoordinator.cpp

Issue 2932593004: Update the snap points css properties (Closed)
Patch Set: Fix nits Created 3 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2016 The Chromium Authors. All rights reserved. 1 // Copyright 2016 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "SnapCoordinator.h" 5 #include "SnapCoordinator.h"
6 6
7 #include "core/dom/Element.h" 7 #include "core/dom/Element.h"
8 #include "core/dom/Node.h" 8 #include "core/dom/Node.h"
9 #include "core/dom/NodeComputedStyle.h" 9 #include "core/dom/NodeComputedStyle.h"
10 #include "core/layout/LayoutBlock.h" 10 #include "core/layout/LayoutBlock.h"
(...skipping 25 matching lines...) Expand all
36 box->GetNode() != viewport_defining_element) 36 box->GetNode() != viewport_defining_element)
37 box = box->ContainingBlock(); 37 box = box->ContainingBlock();
38 38
39 // If we reach to viewportDefiningElement then we dispatch to viewport 39 // If we reach to viewportDefiningElement then we dispatch to viewport
40 if (box && box->GetNode() == viewport_defining_element) 40 if (box && box->GetNode() == viewport_defining_element)
41 return snap_area.GetDocument().GetLayoutView(); 41 return snap_area.GetDocument().GetLayoutView();
42 42
43 return box; 43 return box;
44 } 44 }
45 45
46 void SnapCoordinator::SnapAreaDidChange( 46 void SnapCoordinator::SnapAreaDidChange(LayoutBox& snap_area,
47 LayoutBox& snap_area, 47 ScrollSnapAlign scroll_snap_align) {
48 const Vector<LengthPoint>& snap_coordinates) { 48 if (scroll_snap_align.alignmentX == kSnapAlignmentNone &&
49 if (snap_coordinates.IsEmpty()) { 49 scroll_snap_align.alignmentY == kSnapAlignmentNone) {
50 snap_area.SetSnapContainer(nullptr); 50 snap_area.SetSnapContainer(nullptr);
51 return; 51 return;
52 } 52 }
53 53
54 if (LayoutBox* snap_container = FindSnapContainer(snap_area)) { 54 if (LayoutBox* snap_container = FindSnapContainer(snap_area)) {
55 snap_area.SetSnapContainer(snap_container); 55 snap_area.SetSnapContainer(snap_container);
56 } else { 56 } else {
57 // TODO(majidvp): keep track of snap areas that do not have any 57 // TODO(majidvp): keep track of snap areas that do not have any
58 // container so that we check them again when a new container is 58 // container so that we check them again when a new container is
59 // added to the page. 59 // added to the page.
60 } 60 }
61 } 61 }
62 62
63 void SnapCoordinator::SnapContainerDidChange(LayoutBox& snap_container, 63 void SnapCoordinator::SnapContainerDidChange(LayoutBox& snap_container,
64 ScrollSnapType scroll_snap_type) { 64 ScrollSnapType scroll_snap_type) {
65 if (scroll_snap_type == kScrollSnapTypeNone) { 65 if (scroll_snap_type.is_none) {
66 // TODO(majidvp): Track and report these removals to CompositorWorker 66 // TODO(majidvp): Track and report these removals to CompositorWorker
67 // instance responsible for snapping 67 // instance responsible for snapping
68 snap_containers_.erase(&snap_container); 68 snap_containers_.erase(&snap_container);
69 snap_container.ClearSnapAreas(); 69 snap_container.ClearSnapAreas();
70 } else { 70 } else {
71 snap_containers_.insert(&snap_container); 71 snap_containers_.insert(&snap_container);
72 } 72 }
73 73
74 // TODO(majidvp): Add logic to correctly handle orphaned snap areas here. 74 // TODO(majidvp): Add logic to correctly handle orphaned snap areas here.
75 // 1. Removing container: find a new snap container for its orphan snap 75 // 1. Removing container: find a new snap container for its orphan snap
76 // areas (most likely nearest ancestor of current container) otherwise add 76 // areas (most likely nearest ancestor of current container) otherwise add
77 // them to an orphan list. 77 // them to an orphan list.
78 // 2. Adding container: may take over snap areas from nearest ancestor snap 78 // 2. Adding container: may take over snap areas from nearest ancestor snap
79 // container or from existing areas in orphan pool. 79 // container or from existing areas in orphan pool.
80 } 80 }
81 81
82 // Translate local snap coordinates into snap container's scrolling content
83 // coordinate space.
84 static Vector<FloatPoint> LocalToContainerSnapCoordinates(
85 const LayoutBox& container_box,
86 const LayoutBox& snap_area) {
87 Vector<FloatPoint> result;
88 LayoutPoint scroll_offset(container_box.ScrollLeft(),
89 container_box.ScrollTop());
90
91 const Vector<LengthPoint>& snap_coordinates =
92 snap_area.Style()->ScrollSnapCoordinate();
93 for (auto& coordinate : snap_coordinates) {
94 FloatPoint local_point =
95 FloatPointForLengthPoint(coordinate, FloatSize(snap_area.Size()));
96 FloatPoint container_point =
97 snap_area.LocalToAncestorPoint(local_point, &container_box);
98 container_point.MoveBy(scroll_offset);
99 result.push_back(container_point);
100 }
101 return result;
102 }
103
104 Vector<double> SnapCoordinator::SnapOffsets(const ContainerNode& element,
105 ScrollbarOrientation orientation) {
106 const ComputedStyle* style = element.GetComputedStyle();
107 const LayoutBox* snap_container = element.GetLayoutBox();
108 DCHECK(style);
109 DCHECK(snap_container);
110
111 Vector<double> result;
112
113 if (style->GetScrollSnapType() == kScrollSnapTypeNone)
114 return result;
115
116 const ScrollSnapPoints& snap_points = (orientation == kHorizontalScrollbar)
117 ? style->ScrollSnapPointsX()
118 : style->ScrollSnapPointsY();
119
120 LayoutUnit client_size = (orientation == kHorizontalScrollbar)
121 ? snap_container->ClientWidth()
122 : snap_container->ClientHeight();
123 LayoutUnit scroll_size = (orientation == kHorizontalScrollbar)
124 ? snap_container->ScrollWidth()
125 : snap_container->ScrollHeight();
126
127 if (snap_points.has_repeat) {
128 LayoutUnit repeat = ValueForLength(snap_points.repeat_offset, client_size);
129
130 // calc() values may be negative or zero in which case we clamp them to 1px.
131 // See: https://lists.w3.org/Archives/Public/www-style/2015Jul/0075.html
132 repeat = std::max<LayoutUnit>(repeat, LayoutUnit(1));
133 for (LayoutUnit offset = repeat; offset <= (scroll_size - client_size);
134 offset += repeat) {
135 result.push_back(offset.ToFloat());
136 }
137 }
138
139 // Compute element-based snap points by mapping the snap coordinates from
140 // snap areas to snap container.
141 bool did_add_snap_area_offset = false;
142 if (SnapAreaSet* snap_areas = snap_container->SnapAreas()) {
143 for (auto& snap_area : *snap_areas) {
144 Vector<FloatPoint> snap_coordinates =
145 LocalToContainerSnapCoordinates(*snap_container, *snap_area);
146 for (const FloatPoint& snap_coordinate : snap_coordinates) {
147 float snap_offset = (orientation == kHorizontalScrollbar)
148 ? snap_coordinate.X()
149 : snap_coordinate.Y();
150 if (snap_offset > scroll_size - client_size)
151 continue;
152 result.push_back(snap_offset);
153 did_add_snap_area_offset = true;
154 }
155 }
156 }
157
158 if (did_add_snap_area_offset)
159 std::sort(result.begin(), result.end());
160
161 return result;
162 }
163
164 #ifndef NDEBUG 82 #ifndef NDEBUG
165 83
166 void SnapCoordinator::ShowSnapAreaMap() { 84 void SnapCoordinator::ShowSnapAreaMap() {
167 for (auto& container : snap_containers_) 85 for (auto& container : snap_containers_)
168 ShowSnapAreasFor(container); 86 ShowSnapAreasFor(container);
169 } 87 }
170 88
171 void SnapCoordinator::ShowSnapAreasFor(const LayoutBox* container) { 89 void SnapCoordinator::ShowSnapAreasFor(const LayoutBox* container) {
172 LOG(INFO) << *container->GetNode(); 90 LOG(INFO) << *container->GetNode();
173 if (SnapAreaSet* snap_areas = container->SnapAreas()) { 91 if (SnapAreaSet* snap_areas = container->SnapAreas()) {
174 for (auto& snap_area : *snap_areas) { 92 for (auto& snap_area : *snap_areas) {
175 LOG(INFO) << " " << *snap_area->GetNode(); 93 LOG(INFO) << " " << *snap_area->GetNode();
176 } 94 }
177 } 95 }
178 } 96 }
179 97
180 #endif 98 #endif
181 99
182 } // namespace blink 100 } // namespace blink
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698