diff options
author | Xianzhu Wang <wangxianzhu@chromium.org> | 2016-01-15 12:13:28 -0800 |
---|---|---|
committer | Xianzhu Wang <wangxianzhu@chromium.org> | 2016-01-15 20:15:49 +0000 |
commit | 680029cb8956f604743d5c7697aa6d1c253bf28b (patch) | |
tree | 4358dd1bb16773b191fd8195ff6c8906689502af | |
parent | c90754a6e47b67178102b77c34fa67c43a8ded4c (diff) | |
download | chromium_src-680029cb8956f604743d5c7697aa6d1c253bf28b.zip chromium_src-680029cb8956f604743d5c7697aa6d1c253bf28b.tar.gz chromium_src-680029cb8956f604743d5c7697aa6d1c253bf28b.tar.bz2 |
Merge "Output url destination points with correct transformations" again
(This was incorrectly reverted by an unrelated change:
crrev.com/5246859cf14b0ef21bd1c2f55c9d00e6a2bc642c
Now merge it again.)
Previously we output url destination points after spooling a page.
The drawPoints() operations are not under control of the transformations
of the page, so they may be in wrong coordinates and rejected by skia
because they are out of the clip area of the canvas.
Now output url destination points during spooling a page. Added
GraphicsContext::setURLDestinationLocation() so that we can output
display items for the points.
BTW, this CL also fixes bug 564884.
BUG=521894,564884
TBR=wangxianzhu@chromium.org
> Review URL: https://codereview.chromium.org/1509643002
> Cr-Commit-Position: refs/heads/master@{#363978}
Review URL: https://codereview.chromium.org/1519563002 .
Cr-Commit-Position: refs/branch-heads/2564@{#303}
Cr-Branched-From: 1283eca15bd9f772387f75241576cde7bdec7f54-refs/heads/master@{#359700}
Review URL: https://codereview.chromium.org/1582963008 .
Cr-Commit-Position: refs/branch-heads/2564@{#568}
Cr-Branched-From: 1283eca15bd9f772387f75241576cde7bdec7f54-refs/heads/master@{#359700}
9 files changed, 63 insertions, 22 deletions
diff --git a/third_party/WebKit/Source/core/page/PrintContext.cpp b/third_party/WebKit/Source/core/page/PrintContext.cpp index 3cfff3d..7622d03 100644 --- a/third_party/WebKit/Source/core/page/PrintContext.cpp +++ b/third_party/WebKit/Source/core/page/PrintContext.cpp @@ -24,7 +24,7 @@ #include "core/frame/FrameView.h" #include "core/frame/LocalFrame.h" #include "core/layout/LayoutView.h" -#include "third_party/skia/include/core/SkAnnotation.h" +#include "platform/graphics/GraphicsContext.h" namespace blink { @@ -230,7 +230,7 @@ void PrintContext::collectLinkedDestinations(Node* node) } } -void PrintContext::outputLinkedDestinations(SkCanvas* canvas, const IntRect& pageRect) +void PrintContext::outputLinkedDestinations(GraphicsContext& context, const IntRect& pageRect) { if (!m_linkedDestinationsValid) { // Collect anchors in the top-level frame only because our PrintContext @@ -244,13 +244,11 @@ void PrintContext::outputLinkedDestinations(SkCanvas* canvas, const IntRect& pag if (!layoutObject || !layoutObject->frameView()) continue; IntRect boundingBox = layoutObject->absoluteBoundingBoxRect(); - boundingBox = layoutObject->frameView()->convertToContainingWindow(boundingBox); - if (!pageRect.intersects(boundingBox)) + IntPoint point = layoutObject->frameView()->convertToRootFrame(boundingBox.location()); + if (!pageRect.contains(point)) continue; - IntPoint point = boundingBox.minXMinYCorner(); point.clampNegativeToZero(); - SkAutoDataUnref nameData(SkData::NewWithCString(entry.key.utf8().data())); - SkAnnotateNamedDestination(canvas, SkPoint::Make(point.x(), point.y()), nameData); + context.setURLDestinationLocation(entry.key, point); } } diff --git a/third_party/WebKit/Source/core/page/PrintContext.h b/third_party/WebKit/Source/core/page/PrintContext.h index e1365ba..402595b 100644 --- a/third_party/WebKit/Source/core/page/PrintContext.h +++ b/third_party/WebKit/Source/core/page/PrintContext.h @@ -28,14 +28,13 @@ #include "wtf/Vector.h" #include "wtf/text/WTFString.h" -class SkCanvas; - namespace blink { class Element; class LocalFrame; class FloatRect; class FloatSize; +class GraphicsContext; class IntRect; class Node; @@ -79,7 +78,7 @@ public: DECLARE_VIRTUAL_TRACE(); protected: - void outputLinkedDestinations(SkCanvas*, const IntRect& pageRect); + void outputLinkedDestinations(GraphicsContext&, const IntRect& pageRect); RawPtrWillBeMember<LocalFrame> m_frame; Vector<IntRect> m_pageRects; diff --git a/third_party/WebKit/Source/core/page/PrintContextTest.cpp b/third_party/WebKit/Source/core/page/PrintContextTest.cpp index c51acd4..1f4997f 100644 --- a/third_party/WebKit/Source/core/page/PrintContextTest.cpp +++ b/third_party/WebKit/Source/core/page/PrintContextTest.cpp @@ -16,6 +16,7 @@ #include "core/paint/PaintLayerPainter.h" #include "core/testing/DummyPageHolder.h" #include "platform/graphics/GraphicsContext.h" +#include "platform/graphics/paint/DrawingRecorder.h" #include "platform/graphics/paint/SkPictureBuilder.h" #include "platform/scroll/ScrollbarTheme.h" #include "platform/testing/SkiaForCoreTesting.h" @@ -31,9 +32,9 @@ class MockPrintContext : public PrintContext { public: MockPrintContext(LocalFrame* frame) : PrintContext(frame) { } - void outputLinkedDestinations(SkCanvas* canvas, const IntRect& pageRect) + void outputLinkedDestinations(GraphicsContext& context, const IntRect& pageRect) { - PrintContext::outputLinkedDestinations(canvas, pageRect); + PrintContext::outputLinkedDestinations(context, pageRect); } }; @@ -100,8 +101,11 @@ protected: GraphicsContext& context = pictureBuilder.context(); context.setPrinting(true); document().view()->paintContents(&context, GlobalPaintPrinting, pageRect); + { + DrawingRecorder recorder(context, *document().layoutView(), DisplayItem::PrintedContentDestinationLocations, pageRect); + printContext().outputLinkedDestinations(context, pageRect); + } pictureBuilder.endRecording()->playback(&canvas); - printContext().outputLinkedDestinations(&canvas, pageRect); printContext().end(); } @@ -120,10 +124,10 @@ protected: return ts.release(); } - static String htmlForAnchor(int x, int y, const char* name) + static String htmlForAnchor(int x, int y, const char* name, const char* textContent) { TextStream ts; - ts << "<a name='" << name << "' style='position: absolute; left: " << x << "px; top: " << y << "px'>" << name << "</a>"; + ts << "<a name='" << name << "' style='position: absolute; left: " << x << "px; top: " << y << "px'>" << textContent << "</a>"; return ts.release(); } @@ -265,8 +269,24 @@ TEST_F(PrintContextTest, LinkedTarget) document().setBaseURLOverride(KURL(ParsedURLString, "http://a.com/")); setBodyInnerHTML(absoluteBlockHtmlForLink(50, 60, 70, 80, "#fragment") // Generates a Link_Named_Dest_Key annotation + absoluteBlockHtmlForLink(150, 160, 170, 180, "#not-found") // Generates no annotation - + htmlForAnchor(250, 260, "fragment") // Generates a Define_Named_Dest_Key annotation - + htmlForAnchor(350, 360, "fragment-not-used")); // Generates no annotation + + htmlForAnchor(250, 260, "fragment", "fragment") // Generates a Define_Named_Dest_Key annotation + + htmlForAnchor(350, 360, "fragment-not-used", "fragment-not-used")); // Generates no annotation + printSinglePage(canvas); + + const Vector<MockCanvas::Operation>& operations = canvas.recordedOperations(); + ASSERT_EQ(2u, operations.size()); + EXPECT_EQ(MockCanvas::DrawRect, operations[0].type); + EXPECT_SKRECT_EQ(50, 60, 70, 80, operations[0].rect); + EXPECT_EQ(MockCanvas::DrawPoint, operations[1].type); + EXPECT_SKRECT_EQ(250, 260, 0, 0, operations[1].rect); +} + +TEST_F(PrintContextTest, EmptyLinkedTarget) +{ + MockCanvas canvas; + document().setBaseURLOverride(KURL(ParsedURLString, "http://a.com/")); + setBodyInnerHTML(absoluteBlockHtmlForLink(50, 60, 70, 80, "#fragment") + + htmlForAnchor(250, 260, "fragment", "")); printSinglePage(canvas); const Vector<MockCanvas::Operation>& operations = canvas.recordedOperations(); diff --git a/third_party/WebKit/Source/platform/graphics/GraphicsContext.cpp b/third_party/WebKit/Source/platform/graphics/GraphicsContext.cpp index 18eb9a0..90ef32b 100644 --- a/third_party/WebKit/Source/platform/graphics/GraphicsContext.cpp +++ b/third_party/WebKit/Source/platform/graphics/GraphicsContext.cpp @@ -1183,6 +1183,16 @@ void GraphicsContext::setURLFragmentForRect(const String& destName, const IntRec SkAnnotateLinkToDestination(m_canvas, rect, skDestName.get()); } +void GraphicsContext::setURLDestinationLocation(const String& name, const IntPoint& location) +{ + if (contextDisabled()) + return; + ASSERT(m_canvas); + + SkAutoDataUnref skName(SkData::NewWithCString(name.utf8().data())); + SkAnnotateNamedDestination(m_canvas, SkPoint::Make(location.x(), location.y()), skName); +} + void GraphicsContext::concatCTM(const AffineTransform& affine) { concat(affineTransformToSkMatrix(affine)); diff --git a/third_party/WebKit/Source/platform/graphics/GraphicsContext.h b/third_party/WebKit/Source/platform/graphics/GraphicsContext.h index be487e6..2c9d439 100644 --- a/third_party/WebKit/Source/platform/graphics/GraphicsContext.h +++ b/third_party/WebKit/Source/platform/graphics/GraphicsContext.h @@ -245,10 +245,17 @@ public: SkFilterQuality computeFilterQuality(Image*, const FloatRect& dest, const FloatRect& src) const; - // URL drawing + // Sets target URL of a clickable area. void setURLForRect(const KURL&, const IntRect&); + + // Sets destination of a URL fragment (in a URL pointing to the same web page) of a clickable area. + // When the area is clicked, the page should be scrolled to the location set by setURLDestinationLocation() + // for the destination whose name equals the fragment. void setURLFragmentForRect(const String& name, const IntRect&); + // Sets location of a URL destination (a.k.a. anchor) in the page. + void setURLDestinationLocation(const String& name, const IntPoint&); + static void adjustLineToPixelBoundaries(FloatPoint& p1, FloatPoint& p2, float strokeWidth, StrokeStyle); static int focusRingOutsetExtent(int offset, int width) diff --git a/third_party/WebKit/Source/platform/graphics/paint/DisplayItem.cpp b/third_party/WebKit/Source/platform/graphics/paint/DisplayItem.cpp index fa72aa8..e1ce822 100644 --- a/third_party/WebKit/Source/platform/graphics/paint/DisplayItem.cpp +++ b/third_party/WebKit/Source/platform/graphics/paint/DisplayItem.cpp @@ -83,6 +83,7 @@ static WTF::String specialDrawingTypeAsDebugString(DisplayItem::Type type) DEBUG_STRING_CASE(PopupListBoxBackground); DEBUG_STRING_CASE(PopupListBoxRow); DEBUG_STRING_CASE(PrintedContentBackground); + DEBUG_STRING_CASE(PrintedContentDestinationLocations); DEBUG_STRING_CASE(PrintedContentLineBoundary); DEBUG_STRING_CASE(PrintedContentPDFURLRect); DEBUG_STRING_CASE(Resizer); diff --git a/third_party/WebKit/Source/platform/graphics/paint/DisplayItem.h b/third_party/WebKit/Source/platform/graphics/paint/DisplayItem.h index 2670d44..3040c0f 100644 --- a/third_party/WebKit/Source/platform/graphics/paint/DisplayItem.h +++ b/third_party/WebKit/Source/platform/graphics/paint/DisplayItem.h @@ -70,6 +70,7 @@ public: PopupListBoxBackground, PopupListBoxRow, PrintedContentBackground, + PrintedContentDestinationLocations, PrintedContentLineBoundary, PrintedContentPDFURLRect, Resizer, diff --git a/third_party/WebKit/Source/platform/graphics/paint/SkPictureBuilder.h b/third_party/WebKit/Source/platform/graphics/paint/SkPictureBuilder.h index a9341ac..dcf6d06 100644 --- a/third_party/WebKit/Source/platform/graphics/paint/SkPictureBuilder.h +++ b/third_party/WebKit/Source/platform/graphics/paint/SkPictureBuilder.h @@ -26,6 +26,7 @@ public: disabledMode = GraphicsContext::FullyDisabled; m_paintController = PaintController::create(); + m_paintController->beginSkippingCache(); m_context = adoptPtr(new GraphicsContext(*m_paintController, disabledMode, metaData)); if (containingContext) { @@ -39,6 +40,7 @@ public: PassRefPtr<const SkPicture> endRecording() { m_context->beginRecording(m_bounds); + m_paintController->endSkippingCache(); m_paintController->commitNewDisplayItems(); m_paintController->paintArtifact().replay(*m_context); return m_context->endRecording(); diff --git a/third_party/WebKit/Source/web/WebLocalFrameImpl.cpp b/third_party/WebKit/Source/web/WebLocalFrameImpl.cpp index d0e9bbb..5950cb6 100644 --- a/third_party/WebKit/Source/web/WebLocalFrameImpl.cpp +++ b/third_party/WebKit/Source/web/WebLocalFrameImpl.cpp @@ -374,7 +374,6 @@ public: float scale = spoolPage(pictureBuilder.context(), pageNumber); pictureBuilder.endRecording()->playback(canvas); - outputLinkedDestinations(canvas, pageRect); return scale; } @@ -402,7 +401,7 @@ public: GraphicsContext& context = pictureBuilder.context(); // Fill the whole background by white. - if (!DrawingRecorder::useCachedDrawingIfPossible(context, *this, DisplayItem::PrintedContentBackground)) { + { DrawingRecorder backgroundRecorder(context, *this, DisplayItem::PrintedContentBackground, allPagesRect); context.fillRect(FloatRect(0, 0, pageWidth, totalHeight), Color::white); } @@ -411,7 +410,7 @@ public: for (size_t pageIndex = 0; pageIndex < numPages; pageIndex++) { ScopeRecorder scopeRecorder(context); // Draw a line for a page boundary if this isn't the first page. - if (pageIndex > 0 && !DrawingRecorder::useCachedDrawingIfPossible(context, *this, DisplayItem::PrintedContentLineBoundary)) { + if (pageIndex > 0) { DrawingRecorder lineBoundaryRecorder(context, *this, DisplayItem::PrintedContentLineBoundary, allPagesRect); context.save(); context.setStrokeColor(Color(0, 0, 255)); @@ -434,7 +433,6 @@ public: currentHeight += pageSizeInPixels.height() + 1; } pictureBuilder.endRecording()->playback(canvas); - outputLinkedDestinations(canvas, allPagesRect); } DisplayItemClient displayItemClient() const { return toDisplayItemClient(this); } @@ -463,6 +461,11 @@ protected: frame()->view()->paintContents(&context, GlobalPaintNormalPhase, pageRect); + { + DrawingRecorder lineBoundaryRecorder(context, *this, DisplayItem::PrintedContentDestinationLocations, pageRect); + outputLinkedDestinations(context, pageRect); + } + return scale; } |