OLD | NEW |
1 /* | 1 /* |
2 * Copyright (C) 2006 Eric Seidel <eric@webkit.org> | 2 * Copyright (C) 2006 Eric Seidel <eric@webkit.org> |
3 * Copyright (C) 2008, 2009 Apple Inc. All rights reserved. | 3 * Copyright (C) 2008, 2009 Apple Inc. All rights reserved. |
4 * Copyright (C) Research In Motion Limited 2011. All rights reserved. | 4 * Copyright (C) Research In Motion Limited 2011. All rights reserved. |
5 * | 5 * |
6 * Redistribution and use in source and binary forms, with or without | 6 * Redistribution and use in source and binary forms, with or without |
7 * modification, are permitted provided that the following conditions | 7 * modification, are permitted provided that the following conditions |
8 * are met: | 8 * are met: |
9 * 1. Redistributions of source code must retain the above copyright | 9 * 1. Redistributions of source code must retain the above copyright |
10 * notice, this list of conditions and the following disclaimer. | 10 * notice, this list of conditions and the following disclaimer. |
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
57 #include "platform/graphics/paint/CullRect.h" | 57 #include "platform/graphics/paint/CullRect.h" |
58 #include "platform/graphics/paint/DrawingRecorder.h" | 58 #include "platform/graphics/paint/DrawingRecorder.h" |
59 #include "platform/graphics/paint/SkPictureBuilder.h" | 59 #include "platform/graphics/paint/SkPictureBuilder.h" |
60 #include "third_party/skia/include/core/SkPicture.h" | 60 #include "third_party/skia/include/core/SkPicture.h" |
61 #include "wtf/PassRefPtr.h" | 61 #include "wtf/PassRefPtr.h" |
62 | 62 |
63 namespace blink { | 63 namespace blink { |
64 | 64 |
65 SVGImage::SVGImage(ImageObserver* observer) | 65 SVGImage::SVGImage(ImageObserver* observer) |
66 : Image(observer) | 66 : Image(observer) |
| 67 , m_hasPendingTimelineRewind(false) |
67 { | 68 { |
68 } | 69 } |
69 | 70 |
70 SVGImage::~SVGImage() | 71 SVGImage::~SVGImage() |
71 { | 72 { |
72 if (m_page) { | 73 if (m_page) { |
73 // Store m_page in a local variable, clearing m_page, so that SVGImageCh
romeClient knows we're destructed. | 74 // Store m_page in a local variable, clearing m_page, so that SVGImageCh
romeClient knows we're destructed. |
74 Page* currentPage = m_page.release(); | 75 Page* currentPage = m_page.release(); |
75 // Break both the loader and view references to the frame | 76 // Break both the loader and view references to the frame |
76 currentPage->willBeDestroyed(); | 77 currentPage->willBeDestroyed(); |
(...skipping 268 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
345 RespectImageOrientationEnum, ImageClampingMode, const KURL& url) | 346 RespectImageOrientationEnum, ImageClampingMode, const KURL& url) |
346 { | 347 { |
347 DCHECK(m_page); | 348 DCHECK(m_page); |
348 FrameView* view = toLocalFrame(m_page->mainFrame())->view(); | 349 FrameView* view = toLocalFrame(m_page->mainFrame())->view(); |
349 view->resize(containerSize()); | 350 view->resize(containerSize()); |
350 | 351 |
351 // Always call processUrlFragment, even if the url is empty, because | 352 // Always call processUrlFragment, even if the url is empty, because |
352 // there may have been a previous url/fragment that needs to be reset. | 353 // there may have been a previous url/fragment that needs to be reset. |
353 view->processUrlFragment(url); | 354 view->processUrlFragment(url); |
354 | 355 |
| 356 // If the image was reset, we need to rewind the timeline back to 0. This |
| 357 // needs to be done before painting, or else we wouldn't get the correct |
| 358 // reset semantics (we'd paint the "last" frame rather than the one at |
| 359 // time=0.) The reason we do this here and not in resetAnimation() is to |
| 360 // avoid setting timers from the latter. |
| 361 flushPendingTimelineRewind(); |
| 362 |
355 SkPictureBuilder imagePicture(dstRect); | 363 SkPictureBuilder imagePicture(dstRect); |
356 { | 364 { |
357 ClipRecorder clipRecorder(imagePicture.context(), imagePicture, DisplayI
tem::ClipNodeImage, enclosingIntRect(dstRect)); | 365 ClipRecorder clipRecorder(imagePicture.context(), imagePicture, DisplayI
tem::ClipNodeImage, enclosingIntRect(dstRect)); |
358 | 366 |
359 // We can only draw the entire frame, clipped to the rect we want. So co
mpute where the top left | 367 // We can only draw the entire frame, clipped to the rect we want. So co
mpute where the top left |
360 // of the image would be if we were drawing without clipping, and transl
ate accordingly. | 368 // of the image would be if we were drawing without clipping, and transl
ate accordingly. |
361 FloatSize scale(dstRect.width() / srcRect.width(), dstRect.height() / sr
cRect.height()); | 369 FloatSize scale(dstRect.width() / srcRect.width(), dstRect.height() / sr
cRect.height()); |
362 FloatSize topLeftOffset(srcRect.location().x() * scale.width(), srcRect.
location().y() * scale.height()); | 370 FloatSize topLeftOffset(srcRect.location().x() * scale.width(), srcRect.
location().y() * scale.height()); |
363 FloatPoint destOffset = dstRect.location() - topLeftOffset; | 371 FloatPoint destOffset = dstRect.location() - topLeftOffset; |
364 AffineTransform transform = AffineTransform::translation(destOffset.x(),
destOffset.y()); | 372 AffineTransform transform = AffineTransform::translation(destOffset.x(),
destOffset.y()); |
(...skipping 25 matching lines...) Expand all Loading... |
390 } | 398 } |
391 | 399 |
392 LayoutReplaced* SVGImage::embeddedReplacedContent() const | 400 LayoutReplaced* SVGImage::embeddedReplacedContent() const |
393 { | 401 { |
394 SVGSVGElement* rootElement = svgRootElement(m_page.get()); | 402 SVGSVGElement* rootElement = svgRootElement(m_page.get()); |
395 if (!rootElement) | 403 if (!rootElement) |
396 return nullptr; | 404 return nullptr; |
397 return toLayoutSVGRoot(rootElement->layoutObject()); | 405 return toLayoutSVGRoot(rootElement->layoutObject()); |
398 } | 406 } |
399 | 407 |
| 408 void SVGImage::scheduleTimelineRewind() |
| 409 { |
| 410 m_hasPendingTimelineRewind = true; |
| 411 } |
| 412 |
| 413 void SVGImage::flushPendingTimelineRewind() |
| 414 { |
| 415 if (!m_hasPendingTimelineRewind) |
| 416 return; |
| 417 if (SVGSVGElement* rootElement = svgRootElement(m_page.get())) |
| 418 rootElement->setCurrentTime(0); |
| 419 m_hasPendingTimelineRewind = false; |
| 420 } |
| 421 |
400 // FIXME: support CatchUpAnimation = CatchUp. | 422 // FIXME: support CatchUpAnimation = CatchUp. |
401 void SVGImage::startAnimation(CatchUpAnimation) | 423 void SVGImage::startAnimation(CatchUpAnimation) |
402 { | 424 { |
403 SVGSVGElement* rootElement = svgRootElement(m_page.get()); | 425 SVGSVGElement* rootElement = svgRootElement(m_page.get()); |
404 if (!rootElement) | 426 if (!rootElement) |
405 return; | 427 return; |
406 m_chromeClient->resumeAnimation(); | 428 m_chromeClient->resumeAnimation(); |
407 if (rootElement->animationsPaused()) | 429 if (rootElement->animationsPaused()) |
408 rootElement->unpauseAnimations(); | 430 rootElement->unpauseAnimations(); |
409 } | 431 } |
410 | 432 |
411 void SVGImage::stopAnimation() | 433 void SVGImage::stopAnimation() |
412 { | 434 { |
413 SVGSVGElement* rootElement = svgRootElement(m_page.get()); | 435 SVGSVGElement* rootElement = svgRootElement(m_page.get()); |
414 if (!rootElement) | 436 if (!rootElement) |
415 return; | 437 return; |
416 m_chromeClient->suspendAnimation(); | 438 m_chromeClient->suspendAnimation(); |
417 rootElement->pauseAnimations(); | 439 rootElement->pauseAnimations(); |
418 } | 440 } |
419 | 441 |
420 void SVGImage::resetAnimation() | 442 void SVGImage::resetAnimation() |
421 { | 443 { |
422 SVGSVGElement* rootElement = svgRootElement(m_page.get()); | 444 SVGSVGElement* rootElement = svgRootElement(m_page.get()); |
423 if (!rootElement) | 445 if (!rootElement) |
424 return; | 446 return; |
425 m_chromeClient->suspendAnimation(); | 447 m_chromeClient->suspendAnimation(); |
426 rootElement->pauseAnimations(); | 448 rootElement->pauseAnimations(); |
427 rootElement->setCurrentTime(0); | 449 scheduleTimelineRewind(); |
428 } | 450 } |
429 | 451 |
430 bool SVGImage::hasAnimations() const | 452 bool SVGImage::hasAnimations() const |
431 { | 453 { |
432 SVGSVGElement* rootElement = svgRootElement(m_page.get()); | 454 SVGSVGElement* rootElement = svgRootElement(m_page.get()); |
433 if (!rootElement) | 455 if (!rootElement) |
434 return false; | 456 return false; |
435 return rootElement->timeContainer()->hasAnimations() | 457 return rootElement->timeContainer()->hasAnimations() |
436 || toLocalFrame(m_page->mainFrame())->document()->timeline().hasPendingU
pdates(); | 458 || toLocalFrame(m_page->mainFrame())->document()->timeline().hasPendingU
pdates(); |
437 } | 459 } |
(...skipping 129 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
567 | 589 |
568 return m_page ? SizeAvailable : SizeUnavailable; | 590 return m_page ? SizeAvailable : SizeUnavailable; |
569 } | 591 } |
570 | 592 |
571 String SVGImage::filenameExtension() const | 593 String SVGImage::filenameExtension() const |
572 { | 594 { |
573 return "svg"; | 595 return "svg"; |
574 } | 596 } |
575 | 597 |
576 } // namespace blink | 598 } // namespace blink |
OLD | NEW |