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

Side by Side Diff: Source/web/LinkHighlight.cpp

Issue 687313002: Fix LinkHighlight to position correctly w.r.t. squashed layers. (Closed) Base URL: svn://svn.chromium.org/blink/trunk
Patch Set: Fixed composited scrolling Created 6 years, 1 month 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 | Annotate | Revision Log
« no previous file with comments | « Source/web/LinkHighlight.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2012 Google Inc. All rights reserved. 2 * Copyright (C) 2012 Google Inc. All rights reserved.
3 * 3 *
4 * Redistribution and use in source and binary forms, with or without 4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions 5 * modification, are permitted provided that the following conditions
6 * are met: 6 * are met:
7 * 7 *
8 * 1. Redistributions of source code must retain the above copyright 8 * 1. Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer. 9 * notice, this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright 10 * 2. Redistributions in binary form must reproduce the above copyright
(...skipping 88 matching lines...) Expand 10 before | Expand all | Expand 10 after
99 WebLayer* LinkHighlight::clipLayer() 99 WebLayer* LinkHighlight::clipLayer()
100 { 100 {
101 return m_clipLayer.get(); 101 return m_clipLayer.get();
102 } 102 }
103 103
104 void LinkHighlight::releaseResources() 104 void LinkHighlight::releaseResources()
105 { 105 {
106 m_node.clear(); 106 m_node.clear();
107 } 107 }
108 108
109 RenderLayer* LinkHighlight::computeEnclosingCompositingLayer() 109 void LinkHighlight::attachLinkHighlightToCompositingLayer(const RenderLayerModel Object* paintInvalidationContainer)
110 { 110 {
111 if (!m_node || !m_node->renderer()) 111 GraphicsLayer* newGraphicsLayer = paintInvalidationContainer->layer()->graph icsLayerBackingForScrolling();
112 return 0; 112 if (!newGraphicsLayer)
113 113 return;
114 RenderLayer* renderLayer = m_node->renderer()->enclosingLayer()->enclosingLa yerForPaintInvalidationCrossingFrameBoundaries();
115
116 ASSERT(renderLayer->compositingState() != NotComposited);
117
118 GraphicsLayer* newGraphicsLayer = renderLayer->graphicsLayerBackingForScroll ing();
119 114
120 m_clipLayer->setTransform(SkMatrix44(SkMatrix44::kIdentity_Constructor)); 115 m_clipLayer->setTransform(SkMatrix44(SkMatrix44::kIdentity_Constructor));
121 116
122 if (m_currentGraphicsLayer != newGraphicsLayer) { 117 if (m_currentGraphicsLayer != newGraphicsLayer) {
123 if (m_currentGraphicsLayer) 118 if (m_currentGraphicsLayer)
124 clearGraphicsLayerLinkHighlightPointer(); 119 clearGraphicsLayerLinkHighlightPointer();
125 120
126 m_currentGraphicsLayer = newGraphicsLayer; 121 m_currentGraphicsLayer = newGraphicsLayer;
127 m_currentGraphicsLayer->addLinkHighlight(this); 122 m_currentGraphicsLayer->addLinkHighlight(this);
128 } 123 }
129
130 return renderLayer;
131 } 124 }
132 125
133 static void convertTargetSpaceQuadToCompositedLayer(const FloatQuad& targetSpace Quad, RenderObject* targetRenderer, RenderObject* compositedRenderer, FloatQuad& compositedSpaceQuad) 126 static void convertTargetSpaceQuadToCompositedLayer(const FloatQuad& targetSpace Quad, RenderObject* targetRenderer, const RenderLayerModelObject* paintInvalidat ionContainer, FloatQuad& compositedSpaceQuad)
134 { 127 {
135 ASSERT(targetRenderer); 128 ASSERT(targetRenderer);
136 ASSERT(compositedRenderer); 129 ASSERT(paintInvalidationContainer);
137
138 for (unsigned i = 0; i < 4; ++i) { 130 for (unsigned i = 0; i < 4; ++i) {
139 IntPoint point; 131 IntPoint point;
140 switch (i) { 132 switch (i) {
141 case 0: point = roundedIntPoint(targetSpaceQuad.p1()); break; 133 case 0: point = roundedIntPoint(targetSpaceQuad.p1()); break;
142 case 1: point = roundedIntPoint(targetSpaceQuad.p2()); break; 134 case 1: point = roundedIntPoint(targetSpaceQuad.p2()); break;
143 case 2: point = roundedIntPoint(targetSpaceQuad.p3()); break; 135 case 2: point = roundedIntPoint(targetSpaceQuad.p3()); break;
144 case 3: point = roundedIntPoint(targetSpaceQuad.p4()); break; 136 case 3: point = roundedIntPoint(targetSpaceQuad.p4()); break;
145 } 137 }
146 138
139 // FIXME: this does not need to be absolute, just in the paint invalidat ion container's space.
147 point = targetRenderer->frame()->view()->contentsToWindow(point); 140 point = targetRenderer->frame()->view()->contentsToWindow(point);
148 point = compositedRenderer->frame()->view()->windowToContents(point); 141 point = paintInvalidationContainer->frame()->view()->windowToContents(po int);
149 FloatPoint floatPoint = compositedRenderer->absoluteToLocal(point, UseTr ansforms); 142 FloatPoint floatPoint = paintInvalidationContainer->absoluteToLocal(poin t, UseTransforms);
143 RenderLayer::mapPointToPaintBackingCoordinates(paintInvalidationContaine r, floatPoint);
150 144
151 switch (i) { 145 switch (i) {
152 case 0: compositedSpaceQuad.setP1(floatPoint); break; 146 case 0: compositedSpaceQuad.setP1(floatPoint); break;
153 case 1: compositedSpaceQuad.setP2(floatPoint); break; 147 case 1: compositedSpaceQuad.setP2(floatPoint); break;
154 case 2: compositedSpaceQuad.setP3(floatPoint); break; 148 case 2: compositedSpaceQuad.setP3(floatPoint); break;
155 case 3: compositedSpaceQuad.setP4(floatPoint); break; 149 case 3: compositedSpaceQuad.setP4(floatPoint); break;
156 } 150 }
157 } 151 }
158 } 152 }
159 153
(...skipping 16 matching lines...) Expand all
176 170
177 // For inline elements, absoluteQuads will return a line box based on the li ne-height 171 // For inline elements, absoluteQuads will return a line box based on the li ne-height
178 // and font metrics, which is technically incorrect as replaced elements lik e images 172 // and font metrics, which is technically incorrect as replaced elements lik e images
179 // should use their intristic height and expand the linebox as needed. To g et an 173 // should use their intristic height and expand the linebox as needed. To g et an
180 // appropriately sized highlight we descend into the children and have them add their 174 // appropriately sized highlight we descend into the children and have them add their
181 // boxes. 175 // boxes.
182 if (renderer->isRenderInline()) { 176 if (renderer->isRenderInline()) {
183 for (Node* child = NodeRenderingTraversal::firstChild(&node); child; chi ld = NodeRenderingTraversal::nextSibling(child)) 177 for (Node* child = NodeRenderingTraversal::firstChild(&node); child; chi ld = NodeRenderingTraversal::nextSibling(child))
184 computeQuads(*child, outQuads); 178 computeQuads(*child, outQuads);
185 } else { 179 } else {
180 // FIXME: this does not need to be absolute, just in the paint invalidat ion container's space.
186 renderer->absoluteQuads(outQuads); 181 renderer->absoluteQuads(outQuads);
187 } 182 }
188 } 183 }
189 184
190 bool LinkHighlight::computeHighlightLayerPathAndPosition(RenderLayer* compositin gLayer) 185 bool LinkHighlight::computeHighlightLayerPathAndPosition(const RenderLayerModelO bject* paintInvalidationContainer)
191 { 186 {
192 if (!m_node || !m_node->renderer() || !m_currentGraphicsLayer) 187 if (!m_node || !m_node->renderer() || !m_currentGraphicsLayer)
193 return false; 188 return false;
194 189 ASSERT(paintInvalidationContainer);
195 ASSERT(compositingLayer);
196 190
197 // Get quads for node in absolute coordinates. 191 // Get quads for node in absolute coordinates.
198 Vector<FloatQuad> quads; 192 Vector<FloatQuad> quads;
199 computeQuads(*m_node, quads); 193 computeQuads(*m_node, quads);
200 ASSERT(quads.size()); 194 ASSERT(quads.size());
195 Path newPath;
201 196
202 // Adjust for offset between target graphics layer and the node's renderer. 197 FloatPoint positionAdjustForCompositedScrolling = IntPoint(m_currentGraphics Layer->offsetFromRenderer());
203 FloatPoint positionAdjust = IntPoint(m_currentGraphicsLayer->offsetFromRende rer());
204 198
205 Path newPath;
206 for (size_t quadIndex = 0; quadIndex < quads.size(); ++quadIndex) { 199 for (size_t quadIndex = 0; quadIndex < quads.size(); ++quadIndex) {
207 FloatQuad absoluteQuad = quads[quadIndex]; 200 FloatQuad absoluteQuad = quads[quadIndex];
208 absoluteQuad.move(-positionAdjust.x(), -positionAdjust.y()); 201
202 // FIXME: this hack should not be necessary. It's a consequence of the f act that composited layers for scrolling are represented
203 // differently in Blink than other composited layers.
204 if (paintInvalidationContainer->layer()->needsCompositedScrolling() && m _node->renderer() != paintInvalidationContainer)
205 absoluteQuad.move(-positionAdjustForCompositedScrolling.x(), -positi onAdjustForCompositedScrolling.y());
209 206
210 // Transform node quads in target absolute coords to local coordinates i n the compositor layer. 207 // Transform node quads in target absolute coords to local coordinates i n the compositor layer.
211 FloatQuad transformedQuad; 208 FloatQuad transformedQuad;
212 convertTargetSpaceQuadToCompositedLayer(absoluteQuad, m_node->renderer() , compositingLayer->renderer(), transformedQuad); 209 convertTargetSpaceQuadToCompositedLayer(absoluteQuad, m_node->renderer() , paintInvalidationContainer, transformedQuad);
213 210
214 // FIXME: for now, we'll only use rounded paths if we have a single node quad. The reason for this is that 211 // FIXME: for now, we'll only use rounded paths if we have a single node quad. The reason for this is that
215 // we may sometimes get a chain of adjacent boxes (e.g. for text nodes) which end up looking like sausage 212 // we may sometimes get a chain of adjacent boxes (e.g. for text nodes) which end up looking like sausage
216 // links: these should ideally be merged into a single rect before creat ing the path, but that's 213 // links: these should ideally be merged into a single rect before creat ing the path, but that's
217 // another CL. 214 // another CL.
218 if (quads.size() == 1 && transformedQuad.isRectilinear() 215 if (quads.size() == 1 && transformedQuad.isRectilinear()
219 && !m_owningWebViewImpl->settingsImpl()->mockGestureTapHighlightsEna bled()) { 216 && !m_owningWebViewImpl->settingsImpl()->mockGestureTapHighlightsEna bled()) {
220 FloatSize rectRoundingRadii(3, 3); 217 FloatSize rectRoundingRadii(3, 3);
221 newPath.addRoundedRect(transformedQuad.boundingBox(), rectRoundingRa dii); 218 newPath.addRoundedRect(transformedQuad.boundingBox(), rectRoundingRa dii);
222 } else 219 } else
(...skipping 89 matching lines...) Expand 10 before | Expand all | Expand 10 after
312 309
313 void LinkHighlight::updateGeometry() 310 void LinkHighlight::updateGeometry()
314 { 311 {
315 // To avoid unnecessary updates (e.g. other entities have requested animatio ns from our WebViewImpl), 312 // To avoid unnecessary updates (e.g. other entities have requested animatio ns from our WebViewImpl),
316 // only proceed if we actually requested an update. 313 // only proceed if we actually requested an update.
317 if (!m_geometryNeedsUpdate) 314 if (!m_geometryNeedsUpdate)
318 return; 315 return;
319 316
320 m_geometryNeedsUpdate = false; 317 m_geometryNeedsUpdate = false;
321 318
322 RenderLayer* compositingLayer = computeEnclosingCompositingLayer(); 319 bool hasRenderer = m_node && m_node->renderer();
323 if (compositingLayer && computeHighlightLayerPathAndPosition(compositingLaye r)) { 320 const RenderLayerModelObject* paintInvalidationContainer = hasRenderer ? m_n ode->renderer()->containerForPaintInvalidation() : 0;
321 if (paintInvalidationContainer)
322 attachLinkHighlightToCompositingLayer(paintInvalidationContainer);
323 if (paintInvalidationContainer && computeHighlightLayerPathAndPosition(paint InvalidationContainer)) {
324 // We only need to invalidate the layer if the highlight size has change d, otherwise 324 // We only need to invalidate the layer if the highlight size has change d, otherwise
325 // we can just re-position the layer without needing to repaint. 325 // we can just re-position the layer without needing to repaint.
326 m_contentLayer->layer()->invalidate(); 326 m_contentLayer->layer()->invalidate();
327 327
328 if (m_currentGraphicsLayer) 328 if (m_currentGraphicsLayer)
329 m_currentGraphicsLayer->addRepaintRect(FloatRect(layer()->position() .x, layer()->position().y, layer()->bounds().width, layer()->bounds().height)); 329 m_currentGraphicsLayer->addRepaintRect(FloatRect(layer()->position() .x, layer()->position().y, layer()->bounds().width, layer()->bounds().height));
330 } else if (!m_node || !m_node->renderer()) { 330 } else if (!hasRenderer) {
331 clearGraphicsLayerLinkHighlightPointer(); 331 clearGraphicsLayerLinkHighlightPointer();
332 releaseResources(); 332 releaseResources();
333 } 333 }
334 } 334 }
335 335
336 void LinkHighlight::clearCurrentGraphicsLayer() 336 void LinkHighlight::clearCurrentGraphicsLayer()
337 { 337 {
338 m_currentGraphicsLayer = 0; 338 m_currentGraphicsLayer = 0;
339 m_geometryNeedsUpdate = true; 339 m_geometryNeedsUpdate = true;
340 } 340 }
341 341
342 void LinkHighlight::invalidate() 342 void LinkHighlight::invalidate()
343 { 343 {
344 // Make sure we update geometry on the next callback from WebViewImpl::layou t(). 344 // Make sure we update geometry on the next callback from WebViewImpl::layou t().
345 m_geometryNeedsUpdate = true; 345 m_geometryNeedsUpdate = true;
346 } 346 }
347 347
348 WebLayer* LinkHighlight::layer() 348 WebLayer* LinkHighlight::layer()
349 { 349 {
350 return clipLayer(); 350 return clipLayer();
351 } 351 }
352 352
353 } // namespace blink 353 } // namespace blink
OLDNEW
« no previous file with comments | « Source/web/LinkHighlight.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698