OLD | NEW |
1 /* | 1 /* |
2 * Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011, 2012 Apple Inc.
All rights reserved. | 2 * Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011, 2012 Apple Inc.
All rights reserved. |
3 * Copyright (C) 2008, 2010 Nokia Corporation and/or its subsidiary(-ies) | 3 * Copyright (C) 2008, 2010 Nokia Corporation and/or its subsidiary(-ies) |
4 * Copyright (C) 2007 Alp Toker <alp@atoker.com> | 4 * Copyright (C) 2007 Alp Toker <alp@atoker.com> |
5 * Copyright (C) 2008 Eric Seidel <eric@webkit.org> | 5 * Copyright (C) 2008 Eric Seidel <eric@webkit.org> |
6 * Copyright (C) 2008 Dirk Schulze <krit@webkit.org> | 6 * Copyright (C) 2008 Dirk Schulze <krit@webkit.org> |
7 * Copyright (C) 2010 Torch Mobile (Beijing) Co. Ltd. All rights reserved. | 7 * Copyright (C) 2010 Torch Mobile (Beijing) Co. Ltd. All rights reserved. |
8 * Copyright (C) 2012, 2013 Intel Corporation. All rights reserved. | 8 * Copyright (C) 2012, 2013 Intel Corporation. All rights reserved. |
9 * Copyright (C) 2013 Adobe Systems Incorporated. All rights reserved. | 9 * Copyright (C) 2013 Adobe Systems Incorporated. All rights reserved. |
10 * | 10 * |
(...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
75 #include "wtf/text/StringBuilder.h" | 75 #include "wtf/text/StringBuilder.h" |
76 | 76 |
77 namespace blink { | 77 namespace blink { |
78 | 78 |
79 static const char defaultFont[] = "10px sans-serif"; | 79 static const char defaultFont[] = "10px sans-serif"; |
80 static const char inherit[] = "inherit"; | 80 static const char inherit[] = "inherit"; |
81 static const char rtl[] = "rtl"; | 81 static const char rtl[] = "rtl"; |
82 static const char ltr[] = "ltr"; | 82 static const char ltr[] = "ltr"; |
83 static const double TryRestoreContextInterval = 0.5; | 83 static const double TryRestoreContextInterval = 0.5; |
84 static const unsigned MaxTryRestoreContextAttempts = 4; | 84 static const unsigned MaxTryRestoreContextAttempts = 4; |
85 static const float cDeviceScaleFactor = 1.0f; // Canvas is device independent | 85 static const double cDeviceScaleFactor = 1.0; // Canvas is device independent |
86 | 86 |
87 static bool contextLostRestoredEventsEnabled() | 87 static bool contextLostRestoredEventsEnabled() |
88 { | 88 { |
89 return RuntimeEnabledFeatures::experimentalCanvasFeaturesEnabled(); | 89 return RuntimeEnabledFeatures::experimentalCanvasFeaturesEnabled(); |
90 } | 90 } |
91 | 91 |
92 // Drawing methods need to use this instead of SkAutoCanvasRestore in case overd
raw | 92 // Drawing methods need to use this instead of SkAutoCanvasRestore in case overd
raw |
93 // detection substitutes the recording canvas (to discard overdrawn draw calls). | 93 // detection substitutes the recording canvas (to discard overdrawn draw calls). |
94 class CanvasRenderingContext2DAutoRestoreSkCanvas { | 94 class CanvasRenderingContext2DAutoRestoreSkCanvas { |
95 STACK_ALLOCATED(); | 95 STACK_ALLOCATED(); |
(...skipping 345 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
441 if (canvasPattern->pattern()->isTextureBacked()) | 441 if (canvasPattern->pattern()->isTextureBacked()) |
442 canvas()->disableDeferral(); | 442 canvas()->disableDeferral(); |
443 canvasStyle = CanvasStyle::createFromPattern(canvasPattern); | 443 canvasStyle = CanvasStyle::createFromPattern(canvasPattern); |
444 } | 444 } |
445 | 445 |
446 ASSERT(canvasStyle); | 446 ASSERT(canvasStyle); |
447 modifiableState().setFillStyle(canvasStyle); | 447 modifiableState().setFillStyle(canvasStyle); |
448 modifiableState().setUnparsedFillColor(colorString); | 448 modifiableState().setUnparsedFillColor(colorString); |
449 } | 449 } |
450 | 450 |
451 float CanvasRenderingContext2D::lineWidth() const | 451 double CanvasRenderingContext2D::lineWidth() const |
452 { | 452 { |
453 return state().lineWidth(); | 453 return state().lineWidth(); |
454 } | 454 } |
455 | 455 |
456 void CanvasRenderingContext2D::setLineWidth(float width) | 456 void CanvasRenderingContext2D::setLineWidth(double width) |
457 { | 457 { |
458 if (!std::isfinite(width) || width <= 0) | 458 if (!std::isfinite(width) || width <= 0) |
459 return; | 459 return; |
460 if (state().lineWidth() == width) | 460 if (state().lineWidth() == width) |
461 return; | 461 return; |
462 modifiableState().setLineWidth(width); | 462 modifiableState().setLineWidth(width); |
463 } | 463 } |
464 | 464 |
465 String CanvasRenderingContext2D::lineCap() const | 465 String CanvasRenderingContext2D::lineCap() const |
466 { | 466 { |
(...skipping 18 matching lines...) Expand all Loading... |
485 void CanvasRenderingContext2D::setLineJoin(const String& s) | 485 void CanvasRenderingContext2D::setLineJoin(const String& s) |
486 { | 486 { |
487 LineJoin join; | 487 LineJoin join; |
488 if (!parseLineJoin(s, join)) | 488 if (!parseLineJoin(s, join)) |
489 return; | 489 return; |
490 if (state().lineJoin() == join) | 490 if (state().lineJoin() == join) |
491 return; | 491 return; |
492 modifiableState().setLineJoin(join); | 492 modifiableState().setLineJoin(join); |
493 } | 493 } |
494 | 494 |
495 float CanvasRenderingContext2D::miterLimit() const | 495 double CanvasRenderingContext2D::miterLimit() const |
496 { | 496 { |
497 return state().miterLimit(); | 497 return state().miterLimit(); |
498 } | 498 } |
499 | 499 |
500 void CanvasRenderingContext2D::setMiterLimit(float limit) | 500 void CanvasRenderingContext2D::setMiterLimit(double limit) |
501 { | 501 { |
502 if (!std::isfinite(limit) || limit <= 0) | 502 if (!std::isfinite(limit) || limit <= 0) |
503 return; | 503 return; |
504 if (state().miterLimit() == limit) | 504 if (state().miterLimit() == limit) |
505 return; | 505 return; |
506 modifiableState().setMiterLimit(limit); | 506 modifiableState().setMiterLimit(limit); |
507 } | 507 } |
508 | 508 |
509 float CanvasRenderingContext2D::shadowOffsetX() const | 509 double CanvasRenderingContext2D::shadowOffsetX() const |
510 { | 510 { |
511 return state().shadowOffset().width(); | 511 return state().shadowOffset().width(); |
512 } | 512 } |
513 | 513 |
514 void CanvasRenderingContext2D::setShadowOffsetX(float x) | 514 void CanvasRenderingContext2D::setShadowOffsetX(double x) |
515 { | 515 { |
516 if (!std::isfinite(x)) | 516 if (!std::isfinite(x)) |
517 return; | 517 return; |
518 if (state().shadowOffset().width() == x) | 518 if (state().shadowOffset().width() == x) |
519 return; | 519 return; |
520 modifiableState().setShadowOffsetX(x); | 520 modifiableState().setShadowOffsetX(x); |
521 } | 521 } |
522 | 522 |
523 float CanvasRenderingContext2D::shadowOffsetY() const | 523 double CanvasRenderingContext2D::shadowOffsetY() const |
524 { | 524 { |
525 return state().shadowOffset().height(); | 525 return state().shadowOffset().height(); |
526 } | 526 } |
527 | 527 |
528 void CanvasRenderingContext2D::setShadowOffsetY(float y) | 528 void CanvasRenderingContext2D::setShadowOffsetY(double y) |
529 { | 529 { |
530 if (!std::isfinite(y)) | 530 if (!std::isfinite(y)) |
531 return; | 531 return; |
532 if (state().shadowOffset().height() == y) | 532 if (state().shadowOffset().height() == y) |
533 return; | 533 return; |
534 modifiableState().setShadowOffsetY(y); | 534 modifiableState().setShadowOffsetY(y); |
535 } | 535 } |
536 | 536 |
537 float CanvasRenderingContext2D::shadowBlur() const | 537 double CanvasRenderingContext2D::shadowBlur() const |
538 { | 538 { |
539 return state().shadowBlur(); | 539 return state().shadowBlur(); |
540 } | 540 } |
541 | 541 |
542 void CanvasRenderingContext2D::setShadowBlur(float blur) | 542 void CanvasRenderingContext2D::setShadowBlur(double blur) |
543 { | 543 { |
544 if (!std::isfinite(blur) || blur < 0) | 544 if (!std::isfinite(blur) || blur < 0) |
545 return; | 545 return; |
546 if (state().shadowBlur() == blur) | 546 if (state().shadowBlur() == blur) |
547 return; | 547 return; |
548 modifiableState().setShadowBlur(blur); | 548 modifiableState().setShadowBlur(blur); |
549 } | 549 } |
550 | 550 |
551 String CanvasRenderingContext2D::shadowColor() const | 551 String CanvasRenderingContext2D::shadowColor() const |
552 { | 552 { |
(...skipping 24 matching lines...) Expand all Loading... |
577 return true; | 577 return true; |
578 } | 578 } |
579 | 579 |
580 void CanvasRenderingContext2D::setLineDash(const Vector<float>& dash) | 580 void CanvasRenderingContext2D::setLineDash(const Vector<float>& dash) |
581 { | 581 { |
582 if (!lineDashSequenceIsValid(dash)) | 582 if (!lineDashSequenceIsValid(dash)) |
583 return; | 583 return; |
584 modifiableState().setLineDash(dash); | 584 modifiableState().setLineDash(dash); |
585 } | 585 } |
586 | 586 |
587 float CanvasRenderingContext2D::lineDashOffset() const | 587 double CanvasRenderingContext2D::lineDashOffset() const |
588 { | 588 { |
589 return state().lineDashOffset(); | 589 return state().lineDashOffset(); |
590 } | 590 } |
591 | 591 |
592 void CanvasRenderingContext2D::setLineDashOffset(float offset) | 592 void CanvasRenderingContext2D::setLineDashOffset(double offset) |
593 { | 593 { |
594 if (!std::isfinite(offset) || state().lineDashOffset() == offset) | 594 if (!std::isfinite(offset) || state().lineDashOffset() == offset) |
595 return; | 595 return; |
596 modifiableState().setLineDashOffset(offset); | 596 modifiableState().setLineDashOffset(offset); |
597 } | 597 } |
598 | 598 |
599 float CanvasRenderingContext2D::globalAlpha() const | 599 double CanvasRenderingContext2D::globalAlpha() const |
600 { | 600 { |
601 return state().globalAlpha(); | 601 return state().globalAlpha(); |
602 } | 602 } |
603 | 603 |
604 void CanvasRenderingContext2D::setGlobalAlpha(float alpha) | 604 void CanvasRenderingContext2D::setGlobalAlpha(double alpha) |
605 { | 605 { |
606 if (!(alpha >= 0 && alpha <= 1)) | 606 if (!(alpha >= 0 && alpha <= 1)) |
607 return; | 607 return; |
608 if (state().globalAlpha() == alpha) | 608 if (state().globalAlpha() == alpha) |
609 return; | 609 return; |
610 modifiableState().setGlobalAlpha(alpha); | 610 modifiableState().setGlobalAlpha(alpha); |
611 } | 611 } |
612 | 612 |
613 bool CanvasRenderingContext2D::shouldAntialias() const | 613 bool CanvasRenderingContext2D::shouldAntialias() const |
614 { | 614 { |
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
661 return SVGMatrixTearOff::create(state().transform()); | 661 return SVGMatrixTearOff::create(state().transform()); |
662 } | 662 } |
663 | 663 |
664 void CanvasRenderingContext2D::setCurrentTransform(PassRefPtrWillBeRawPtr<SVGMat
rixTearOff> passMatrixTearOff) | 664 void CanvasRenderingContext2D::setCurrentTransform(PassRefPtrWillBeRawPtr<SVGMat
rixTearOff> passMatrixTearOff) |
665 { | 665 { |
666 RefPtrWillBeRawPtr<SVGMatrixTearOff> matrixTearOff = passMatrixTearOff; | 666 RefPtrWillBeRawPtr<SVGMatrixTearOff> matrixTearOff = passMatrixTearOff; |
667 const AffineTransform& transform = matrixTearOff->value(); | 667 const AffineTransform& transform = matrixTearOff->value(); |
668 setTransform(transform.a(), transform.b(), transform.c(), transform.d(), tra
nsform.e(), transform.f()); | 668 setTransform(transform.a(), transform.b(), transform.c(), transform.d(), tra
nsform.e(), transform.f()); |
669 } | 669 } |
670 | 670 |
671 void CanvasRenderingContext2D::scale(float sx, float sy) | 671 void CanvasRenderingContext2D::scale(double sx, double sy) |
672 { | 672 { |
673 SkCanvas* c = drawingCanvas(); | 673 SkCanvas* c = drawingCanvas(); |
674 if (!c) | 674 if (!c) |
675 return; | 675 return; |
676 | 676 |
677 if (!std::isfinite(sx) || !std::isfinite(sy)) | 677 if (!std::isfinite(sx) || !std::isfinite(sy)) |
678 return; | 678 return; |
679 | 679 |
680 AffineTransform newTransform = state().transform(); | 680 AffineTransform newTransform = state().transform(); |
681 newTransform.scaleNonUniform(sx, sy); | 681 newTransform.scaleNonUniform(sx, sy); |
682 if (state().transform() == newTransform) | 682 if (state().transform() == newTransform) |
683 return; | 683 return; |
684 | 684 |
685 modifiableState().setTransform(newTransform); | 685 modifiableState().setTransform(newTransform); |
686 if (!state().isTransformInvertible()) | 686 if (!state().isTransformInvertible()) |
687 return; | 687 return; |
688 | 688 |
689 c->scale(sx, sy); | 689 c->scale(sx, sy); |
690 m_path.transform(AffineTransform().scaleNonUniform(1.0 / sx, 1.0 / sy)); | 690 m_path.transform(AffineTransform().scaleNonUniform(1.0 / sx, 1.0 / sy)); |
691 } | 691 } |
692 | 692 |
693 void CanvasRenderingContext2D::rotate(float angleInRadians) | 693 void CanvasRenderingContext2D::rotate(double angleInRadians) |
694 { | 694 { |
695 SkCanvas* c = drawingCanvas(); | 695 SkCanvas* c = drawingCanvas(); |
696 if (!c) | 696 if (!c) |
697 return; | 697 return; |
698 | 698 |
699 if (!std::isfinite(angleInRadians)) | 699 if (!std::isfinite(angleInRadians)) |
700 return; | 700 return; |
701 | 701 |
702 AffineTransform newTransform = state().transform(); | 702 AffineTransform newTransform = state().transform(); |
703 newTransform.rotateRadians(angleInRadians); | 703 newTransform.rotateRadians(angleInRadians); |
704 if (state().transform() == newTransform) | 704 if (state().transform() == newTransform) |
705 return; | 705 return; |
706 | 706 |
707 modifiableState().setTransform(newTransform); | 707 modifiableState().setTransform(newTransform); |
708 if (!state().isTransformInvertible()) | 708 if (!state().isTransformInvertible()) |
709 return; | 709 return; |
710 c->rotate(angleInRadians * (180.0f / piFloat)); | 710 c->rotate(angleInRadians * (180.0 / piFloat)); |
711 m_path.transform(AffineTransform().rotateRadians(-angleInRadians)); | 711 m_path.transform(AffineTransform().rotateRadians(-angleInRadians)); |
712 } | 712 } |
713 | 713 |
714 void CanvasRenderingContext2D::translate(float tx, float ty) | 714 void CanvasRenderingContext2D::translate(double tx, double ty) |
715 { | 715 { |
716 SkCanvas* c = drawingCanvas(); | 716 SkCanvas* c = drawingCanvas(); |
717 if (!c) | 717 if (!c) |
718 return; | 718 return; |
719 if (!state().isTransformInvertible()) | 719 if (!state().isTransformInvertible()) |
720 return; | 720 return; |
721 | 721 |
722 if (!std::isfinite(tx) || !std::isfinite(ty)) | 722 if (!std::isfinite(tx) || !std::isfinite(ty)) |
723 return; | 723 return; |
724 | 724 |
725 AffineTransform newTransform = state().transform(); | 725 AffineTransform newTransform = state().transform(); |
726 newTransform.translate(tx, ty); | 726 newTransform.translate(tx, ty); |
727 if (state().transform() == newTransform) | 727 if (state().transform() == newTransform) |
728 return; | 728 return; |
729 | 729 |
730 modifiableState().setTransform(newTransform); | 730 modifiableState().setTransform(newTransform); |
731 if (!state().isTransformInvertible()) | 731 if (!state().isTransformInvertible()) |
732 return; | 732 return; |
733 c->translate(tx, ty); | 733 c->translate(tx, ty); |
734 m_path.transform(AffineTransform().translate(-tx, -ty)); | 734 m_path.transform(AffineTransform().translate(-tx, -ty)); |
735 } | 735 } |
736 | 736 |
737 void CanvasRenderingContext2D::transform(float m11, float m12, float m21, float
m22, float dx, float dy) | 737 void CanvasRenderingContext2D::transform(double m11, double m12, double m21, dou
ble m22, double dx, double dy) |
738 { | 738 { |
739 SkCanvas* c = drawingCanvas(); | 739 SkCanvas* c = drawingCanvas(); |
740 if (!c) | 740 if (!c) |
741 return; | 741 return; |
742 | 742 |
743 if (!std::isfinite(m11) || !std::isfinite(m21) || !std::isfinite(dx) || !std
::isfinite(m12) || !std::isfinite(m22) || !std::isfinite(dy)) | 743 if (!std::isfinite(m11) || !std::isfinite(m21) || !std::isfinite(dx) || !std
::isfinite(m12) || !std::isfinite(m22) || !std::isfinite(dy)) |
744 return; | 744 return; |
745 | 745 |
746 AffineTransform transform(m11, m12, m21, m22, dx, dy); | 746 AffineTransform transform(m11, m12, m21, m22, dx, dy); |
747 AffineTransform newTransform = state().transform() * transform; | 747 AffineTransform newTransform = state().transform() * transform; |
(...skipping 24 matching lines...) Expand all Loading... |
772 // resetTransform() resolves the non-invertible CTM state. | 772 // resetTransform() resolves the non-invertible CTM state. |
773 modifiableState().resetTransform(); | 773 modifiableState().resetTransform(); |
774 c->setMatrix(affineTransformToSkMatrix(canvas()->baseTransform())); | 774 c->setMatrix(affineTransformToSkMatrix(canvas()->baseTransform())); |
775 | 775 |
776 if (invertibleCTM) | 776 if (invertibleCTM) |
777 m_path.transform(ctm); | 777 m_path.transform(ctm); |
778 // When else, do nothing because all transform methods didn't update m_path
when CTM became non-invertible. | 778 // When else, do nothing because all transform methods didn't update m_path
when CTM became non-invertible. |
779 // It means that resetTransform() restores m_path just before CTM became non
-invertible. | 779 // It means that resetTransform() restores m_path just before CTM became non
-invertible. |
780 } | 780 } |
781 | 781 |
782 void CanvasRenderingContext2D::setTransform(float m11, float m12, float m21, flo
at m22, float dx, float dy) | 782 void CanvasRenderingContext2D::setTransform(double m11, double m12, double m21,
double m22, double dx, double dy) |
783 { | 783 { |
784 SkCanvas* c = drawingCanvas(); | 784 SkCanvas* c = drawingCanvas(); |
785 if (!c) | 785 if (!c) |
786 return; | 786 return; |
787 | 787 |
788 if (!std::isfinite(m11) || !std::isfinite(m21) || !std::isfinite(dx) || !std
::isfinite(m12) || !std::isfinite(m22) || !std::isfinite(dy)) | 788 if (!std::isfinite(m11) || !std::isfinite(m21) || !std::isfinite(dx) || !std
::isfinite(m12) || !std::isfinite(m22) || !std::isfinite(dy)) |
789 return; | 789 return; |
790 | 790 |
791 resetTransform(); | 791 resetTransform(); |
792 transform(m11, m12, m21, m22, dx, dy); | 792 transform(m11, m12, m21, m22, dx, dy); |
793 } | 793 } |
794 | 794 |
795 void CanvasRenderingContext2D::beginPath() | 795 void CanvasRenderingContext2D::beginPath() |
796 { | 796 { |
797 m_path.clear(); | 797 m_path.clear(); |
798 } | 798 } |
799 | 799 |
800 static bool validateRectForCanvas(float& x, float& y, float& width, float& heigh
t) | 800 static bool validateRectForCanvas(double& x, double& y, double& width, double& h
eight) |
801 { | 801 { |
802 if (!std::isfinite(x) || !std::isfinite(y) || !std::isfinite(width) || !std:
:isfinite(height)) | 802 if (!std::isfinite(x) || !std::isfinite(y) || !std::isfinite(width) || !std:
:isfinite(height)) |
803 return false; | 803 return false; |
804 | 804 |
805 if (!width && !height) | 805 if (!width && !height) |
806 return false; | 806 return false; |
807 | 807 |
808 if (width < 0) { | 808 if (width < 0) { |
809 width = -width; | 809 width = -width; |
810 x -= width; | 810 x -= width; |
(...skipping 167 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
978 void CanvasRenderingContext2D::stroke() | 978 void CanvasRenderingContext2D::stroke() |
979 { | 979 { |
980 drawPathInternal(m_path, CanvasRenderingContext2DState::StrokePaintType); | 980 drawPathInternal(m_path, CanvasRenderingContext2DState::StrokePaintType); |
981 } | 981 } |
982 | 982 |
983 void CanvasRenderingContext2D::stroke(Path2D* domPath) | 983 void CanvasRenderingContext2D::stroke(Path2D* domPath) |
984 { | 984 { |
985 drawPathInternal(domPath->path(), CanvasRenderingContext2DState::StrokePaint
Type); | 985 drawPathInternal(domPath->path(), CanvasRenderingContext2DState::StrokePaint
Type); |
986 } | 986 } |
987 | 987 |
988 void CanvasRenderingContext2D::fillRect(float x, float y, float width, float hei
ght) | 988 void CanvasRenderingContext2D::fillRect(double x, double y, double width, double
height) |
989 { | 989 { |
990 if (!validateRectForCanvas(x, y, width, height)) | 990 if (!validateRectForCanvas(x, y, width, height)) |
991 return; | 991 return; |
992 | 992 |
993 if (!drawingCanvas()) | 993 if (!drawingCanvas()) |
994 return; | 994 return; |
995 | 995 |
996 SkRect rect = SkRect::MakeXYWH(x, y, width, height); | 996 SkRect rect = SkRect::MakeXYWH(x, y, width, height); |
997 draw( | 997 draw( |
998 [&rect, this](SkCanvas* c, const SkPaint* paint) // draw lambda | 998 [&rect, this](SkCanvas* c, const SkPaint* paint) // draw lambda |
(...skipping 14 matching lines...) Expand all Loading... |
1013 SkPath path; | 1013 SkPath path; |
1014 path.moveTo(rect.x(), rect.y()); | 1014 path.moveTo(rect.x(), rect.y()); |
1015 path.lineTo(rect.maxX(), rect.maxY()); | 1015 path.lineTo(rect.maxX(), rect.maxY()); |
1016 path.close(); | 1016 path.close(); |
1017 canvas->drawPath(path, *paint); | 1017 canvas->drawPath(path, *paint); |
1018 return; | 1018 return; |
1019 } | 1019 } |
1020 canvas->drawRect(rect, *paint); | 1020 canvas->drawRect(rect, *paint); |
1021 } | 1021 } |
1022 | 1022 |
1023 void CanvasRenderingContext2D::strokeRect(float x, float y, float width, float h
eight) | 1023 void CanvasRenderingContext2D::strokeRect(double x, double y, double width, doub
le height) |
1024 { | 1024 { |
1025 if (!validateRectForCanvas(x, y, width, height)) | 1025 if (!validateRectForCanvas(x, y, width, height)) |
1026 return; | 1026 return; |
1027 | 1027 |
1028 if (!drawingCanvas()) | 1028 if (!drawingCanvas()) |
1029 return; | 1029 return; |
1030 | 1030 |
1031 SkRect rect = SkRect::MakeXYWH(x, y, width, height); | 1031 SkRect rect = SkRect::MakeXYWH(x, y, width, height); |
1032 FloatRect bounds = rect; | 1032 FloatRect bounds = rect; |
1033 inflateStrokeRect(bounds); | 1033 inflateStrokeRect(bounds); |
(...skipping 30 matching lines...) Expand all Loading... |
1064 void CanvasRenderingContext2D::clip(const String& windingRuleString) | 1064 void CanvasRenderingContext2D::clip(const String& windingRuleString) |
1065 { | 1065 { |
1066 clipInternal(m_path, windingRuleString); | 1066 clipInternal(m_path, windingRuleString); |
1067 } | 1067 } |
1068 | 1068 |
1069 void CanvasRenderingContext2D::clip(Path2D* domPath, const String& windingRuleSt
ring) | 1069 void CanvasRenderingContext2D::clip(Path2D* domPath, const String& windingRuleSt
ring) |
1070 { | 1070 { |
1071 clipInternal(domPath->path(), windingRuleString); | 1071 clipInternal(domPath->path(), windingRuleString); |
1072 } | 1072 } |
1073 | 1073 |
1074 bool CanvasRenderingContext2D::isPointInPath(const float x, const float y, const
String& windingRuleString) | 1074 bool CanvasRenderingContext2D::isPointInPath(const double x, const double y, con
st String& windingRuleString) |
1075 { | 1075 { |
1076 return isPointInPathInternal(m_path, x, y, windingRuleString); | 1076 return isPointInPathInternal(m_path, x, y, windingRuleString); |
1077 } | 1077 } |
1078 | 1078 |
1079 bool CanvasRenderingContext2D::isPointInPath(Path2D* domPath, const float x, con
st float y, const String& windingRuleString) | 1079 bool CanvasRenderingContext2D::isPointInPath(Path2D* domPath, const double x, co
nst double y, const String& windingRuleString) |
1080 { | 1080 { |
1081 return isPointInPathInternal(domPath->path(), x, y, windingRuleString); | 1081 return isPointInPathInternal(domPath->path(), x, y, windingRuleString); |
1082 } | 1082 } |
1083 | 1083 |
1084 bool CanvasRenderingContext2D::isPointInPathInternal(const Path& path, const flo
at x, const float y, const String& windingRuleString) | 1084 bool CanvasRenderingContext2D::isPointInPathInternal(const Path& path, const dou
ble x, const double y, const String& windingRuleString) |
1085 { | 1085 { |
1086 SkCanvas* c = drawingCanvas(); | 1086 SkCanvas* c = drawingCanvas(); |
1087 if (!c) | 1087 if (!c) |
1088 return false; | 1088 return false; |
1089 if (!state().isTransformInvertible()) | 1089 if (!state().isTransformInvertible()) |
1090 return false; | 1090 return false; |
1091 | 1091 |
1092 FloatPoint point(x, y); | 1092 FloatPoint point(x, y); |
1093 if (!std::isfinite(point.x()) || !std::isfinite(point.y())) | 1093 if (!std::isfinite(point.x()) || !std::isfinite(point.y())) |
1094 return false; | 1094 return false; |
1095 AffineTransform ctm = state().transform(); | 1095 AffineTransform ctm = state().transform(); |
1096 FloatPoint transformedPoint = ctm.inverse().mapPoint(point); | 1096 FloatPoint transformedPoint = ctm.inverse().mapPoint(point); |
1097 | 1097 |
1098 return path.contains(transformedPoint, SkFillTypeToWindRule(parseWinding(win
dingRuleString))); | 1098 return path.contains(transformedPoint, SkFillTypeToWindRule(parseWinding(win
dingRuleString))); |
1099 } | 1099 } |
1100 | 1100 |
1101 bool CanvasRenderingContext2D::isPointInStroke(const float x, const float y) | 1101 bool CanvasRenderingContext2D::isPointInStroke(const double x, const double y) |
1102 { | 1102 { |
1103 return isPointInStrokeInternal(m_path, x, y); | 1103 return isPointInStrokeInternal(m_path, x, y); |
1104 } | 1104 } |
1105 | 1105 |
1106 bool CanvasRenderingContext2D::isPointInStroke(Path2D* domPath, const float x, c
onst float y) | 1106 bool CanvasRenderingContext2D::isPointInStroke(Path2D* domPath, const double x,
const double y) |
1107 { | 1107 { |
1108 return isPointInStrokeInternal(domPath->path(), x, y); | 1108 return isPointInStrokeInternal(domPath->path(), x, y); |
1109 } | 1109 } |
1110 | 1110 |
1111 bool CanvasRenderingContext2D::isPointInStrokeInternal(const Path& path, const f
loat x, const float y) | 1111 bool CanvasRenderingContext2D::isPointInStrokeInternal(const Path& path, const d
ouble x, const double y) |
1112 { | 1112 { |
1113 SkCanvas* c = drawingCanvas(); | 1113 SkCanvas* c = drawingCanvas(); |
1114 if (!c) | 1114 if (!c) |
1115 return false; | 1115 return false; |
1116 if (!state().isTransformInvertible()) | 1116 if (!state().isTransformInvertible()) |
1117 return false; | 1117 return false; |
1118 | 1118 |
1119 FloatPoint point(x, y); | 1119 FloatPoint point(x, y); |
1120 if (!std::isfinite(point.x()) || !std::isfinite(point.y())) | 1120 if (!std::isfinite(point.x()) || !std::isfinite(point.y())) |
1121 return false; | 1121 return false; |
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1163 IntRect canvasRect = layoutBox->absoluteContentBox(); | 1163 IntRect canvasRect = layoutBox->absoluteContentBox(); |
1164 pathRect.move(canvasRect.x(), canvasRect.y()); | 1164 pathRect.move(canvasRect.x(), canvasRect.y()); |
1165 | 1165 |
1166 renderer->scrollRectToVisible( | 1166 renderer->scrollRectToVisible( |
1167 pathRect, ScrollAlignment::alignCenterAlways, ScrollAlignment::alignTopA
lways); | 1167 pathRect, ScrollAlignment::alignCenterAlways, ScrollAlignment::alignTopA
lways); |
1168 | 1168 |
1169 // TODO: should implement "inform the user" that the caret and/or | 1169 // TODO: should implement "inform the user" that the caret and/or |
1170 // selection the specified rectangle of the canvas. See http://crbug.com/357
987 | 1170 // selection the specified rectangle of the canvas. See http://crbug.com/357
987 |
1171 } | 1171 } |
1172 | 1172 |
1173 void CanvasRenderingContext2D::clearRect(float x, float y, float width, float he
ight) | 1173 void CanvasRenderingContext2D::clearRect(double x, double y, double width, doubl
e height) |
1174 { | 1174 { |
1175 if (!validateRectForCanvas(x, y, width, height)) | 1175 if (!validateRectForCanvas(x, y, width, height)) |
1176 return; | 1176 return; |
1177 | 1177 |
1178 SkCanvas* c = drawingCanvas(); | 1178 SkCanvas* c = drawingCanvas(); |
1179 if (!c) | 1179 if (!c) |
1180 return; | 1180 return; |
1181 if (!state().isTransformInvertible()) | 1181 if (!state().isTransformInvertible()) |
1182 return; | 1182 return; |
1183 | 1183 |
(...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1242 if (value.isHTMLVideoElement()) | 1242 if (value.isHTMLVideoElement()) |
1243 return value.getAsHTMLVideoElement().get(); | 1243 return value.getAsHTMLVideoElement().get(); |
1244 if (value.isHTMLCanvasElement()) | 1244 if (value.isHTMLCanvasElement()) |
1245 return value.getAsHTMLCanvasElement().get(); | 1245 return value.getAsHTMLCanvasElement().get(); |
1246 if (value.isImageBitmap()) | 1246 if (value.isImageBitmap()) |
1247 return value.getAsImageBitmap().get(); | 1247 return value.getAsImageBitmap().get(); |
1248 ASSERT_NOT_REACHED(); | 1248 ASSERT_NOT_REACHED(); |
1249 return nullptr; | 1249 return nullptr; |
1250 } | 1250 } |
1251 | 1251 |
1252 void CanvasRenderingContext2D::drawImage(const CanvasImageSourceUnion& imageSour
ce, float x, float y, ExceptionState& exceptionState) | 1252 void CanvasRenderingContext2D::drawImage(const CanvasImageSourceUnion& imageSour
ce, double x, double y, ExceptionState& exceptionState) |
1253 { | 1253 { |
1254 CanvasImageSource* imageSourceInternal = toImageSourceInternal(imageSource); | 1254 CanvasImageSource* imageSourceInternal = toImageSourceInternal(imageSource); |
1255 FloatSize sourceRectSize = imageSourceInternal->elementSize(); | 1255 FloatSize sourceRectSize = imageSourceInternal->elementSize(); |
1256 FloatSize destRectSize = imageSourceInternal->defaultDestinationSize(); | 1256 FloatSize destRectSize = imageSourceInternal->defaultDestinationSize(); |
1257 drawImage(imageSourceInternal, 0, 0, sourceRectSize.width(), sourceRectSize.
height(), x, y, destRectSize.width(), destRectSize.height(), exceptionState); | 1257 drawImage(imageSourceInternal, 0, 0, sourceRectSize.width(), sourceRectSize.
height(), x, y, destRectSize.width(), destRectSize.height(), exceptionState); |
1258 } | 1258 } |
1259 | 1259 |
1260 void CanvasRenderingContext2D::drawImage(const CanvasImageSourceUnion& imageSour
ce, | 1260 void CanvasRenderingContext2D::drawImage(const CanvasImageSourceUnion& imageSour
ce, |
1261 float x, float y, float width, float height, ExceptionState& exceptionState) | 1261 double x, double y, double width, double height, ExceptionState& exceptionSt
ate) |
1262 { | 1262 { |
1263 CanvasImageSource* imageSourceInternal = toImageSourceInternal(imageSource); | 1263 CanvasImageSource* imageSourceInternal = toImageSourceInternal(imageSource); |
1264 FloatSize sourceRectSize = imageSourceInternal->elementSize(); | 1264 FloatSize sourceRectSize = imageSourceInternal->elementSize(); |
1265 drawImage(imageSourceInternal, 0, 0, sourceRectSize.width(), sourceRectSize.
height(), x, y, width, height, exceptionState); | 1265 drawImage(imageSourceInternal, 0, 0, sourceRectSize.width(), sourceRectSize.
height(), x, y, width, height, exceptionState); |
1266 } | 1266 } |
1267 | 1267 |
1268 void CanvasRenderingContext2D::drawImage(const CanvasImageSourceUnion& imageSour
ce, | 1268 void CanvasRenderingContext2D::drawImage(const CanvasImageSourceUnion& imageSour
ce, |
1269 float sx, float sy, float sw, float sh, | 1269 double sx, double sy, double sw, double sh, |
1270 float dx, float dy, float dw, float dh, ExceptionState& exceptionState) | 1270 double dx, double dy, double dw, double dh, ExceptionState& exceptionState) |
1271 { | 1271 { |
1272 CanvasImageSource* imageSourceInternal = toImageSourceInternal(imageSource); | 1272 CanvasImageSource* imageSourceInternal = toImageSourceInternal(imageSource); |
1273 drawImage(imageSourceInternal, sx, sy, sw, sh, dx, dy, dw, dh, exceptionStat
e); | 1273 drawImage(imageSourceInternal, sx, sy, sw, sh, dx, dy, dw, dh, exceptionStat
e); |
1274 } | 1274 } |
1275 | 1275 |
1276 bool CanvasRenderingContext2D::shouldDrawImageAntialiased(const FloatRect& destR
ect) const | 1276 bool CanvasRenderingContext2D::shouldDrawImageAntialiased(const FloatRect& destR
ect) const |
1277 { | 1277 { |
1278 if (!shouldAntialias()) | 1278 if (!shouldAntialias()) |
1279 return false; | 1279 return false; |
1280 SkCanvas* c = drawingCanvas(); | 1280 SkCanvas* c = drawingCanvas(); |
(...skipping 71 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1352 return true; | 1352 return true; |
1353 if (imageSource->isCanvasElement()) { | 1353 if (imageSource->isCanvasElement()) { |
1354 HTMLCanvasElement* canvas = static_cast<HTMLCanvasElement*>(imageSource)
; | 1354 HTMLCanvasElement* canvas = static_cast<HTMLCanvasElement*>(imageSource)
; |
1355 if (canvas->isAnimated2D()) | 1355 if (canvas->isAnimated2D()) |
1356 return true; | 1356 return true; |
1357 } | 1357 } |
1358 return false; | 1358 return false; |
1359 } | 1359 } |
1360 | 1360 |
1361 void CanvasRenderingContext2D::drawImage(CanvasImageSource* imageSource, | 1361 void CanvasRenderingContext2D::drawImage(CanvasImageSource* imageSource, |
1362 float sx, float sy, float sw, float sh, | 1362 double sx, double sy, double sw, double sh, |
1363 float dx, float dy, float dw, float dh, ExceptionState& exceptionState) | 1363 double dx, double dy, double dw, double dh, ExceptionState& exceptionState) |
1364 { | 1364 { |
1365 if (!drawingCanvas()) | 1365 if (!drawingCanvas()) |
1366 return; | 1366 return; |
1367 | 1367 |
1368 RefPtr<Image> image; | 1368 RefPtr<Image> image; |
1369 SourceImageStatus sourceImageStatus = InvalidSourceImageStatus; | 1369 SourceImageStatus sourceImageStatus = InvalidSourceImageStatus; |
1370 if (!imageSource->isVideoElement()) { | 1370 if (!imageSource->isVideoElement()) { |
1371 AccelerationHint hint = canvas()->buffer()->isAccelerated() ? PreferAcce
leration : PreferNoAcceleration; | 1371 AccelerationHint hint = canvas()->buffer()->isAccelerated() ? PreferAcce
leration : PreferNoAcceleration; |
1372 image = imageSource->getSourceImageForCanvas(&sourceImageStatus, hint); | 1372 image = imageSource->getSourceImageForCanvas(&sourceImageStatus, hint); |
1373 if (sourceImageStatus == UndecodableSourceImageStatus) | 1373 if (sourceImageStatus == UndecodableSourceImageStatus) |
(...skipping 71 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1445 c->clear(m_hasAlpha ? SK_ColorTRANSPARENT : SK_ColorBLACK); | 1445 c->clear(m_hasAlpha ? SK_ColorTRANSPARENT : SK_ColorBLACK); |
1446 } | 1446 } |
1447 | 1447 |
1448 bool CanvasRenderingContext2D::rectContainsTransformedRect(const FloatRect& rect
, const SkIRect& transformedRect) const | 1448 bool CanvasRenderingContext2D::rectContainsTransformedRect(const FloatRect& rect
, const SkIRect& transformedRect) const |
1449 { | 1449 { |
1450 FloatQuad quad(rect); | 1450 FloatQuad quad(rect); |
1451 FloatQuad transformedQuad(FloatRect(transformedRect.x(), transformedRect.y()
, transformedRect.width(), transformedRect.height())); | 1451 FloatQuad transformedQuad(FloatRect(transformedRect.x(), transformedRect.y()
, transformedRect.width(), transformedRect.height())); |
1452 return state().transform().mapQuad(quad).containsQuad(transformedQuad); | 1452 return state().transform().mapQuad(quad).containsQuad(transformedQuad); |
1453 } | 1453 } |
1454 | 1454 |
1455 CanvasGradient* CanvasRenderingContext2D::createLinearGradient(float x0, float y
0, float x1, float y1) | 1455 CanvasGradient* CanvasRenderingContext2D::createLinearGradient(double x0, double
y0, double x1, double y1) |
1456 { | 1456 { |
1457 CanvasGradient* gradient = CanvasGradient::create(FloatPoint(x0, y0), FloatP
oint(x1, y1)); | 1457 CanvasGradient* gradient = CanvasGradient::create(FloatPoint(x0, y0), FloatP
oint(x1, y1)); |
1458 return gradient; | 1458 return gradient; |
1459 } | 1459 } |
1460 | 1460 |
1461 CanvasGradient* CanvasRenderingContext2D::createRadialGradient(float x0, float y
0, float r0, float x1, float y1, float r1, ExceptionState& exceptionState) | 1461 CanvasGradient* CanvasRenderingContext2D::createRadialGradient(double x0, double
y0, double r0, double x1, double y1, double r1, ExceptionState& exceptionState) |
1462 { | 1462 { |
1463 if (r0 < 0 || r1 < 0) { | 1463 if (r0 < 0 || r1 < 0) { |
1464 exceptionState.throwDOMException(IndexSizeError, String::format("The %s
provided is less than 0.", r0 < 0 ? "r0" : "r1")); | 1464 exceptionState.throwDOMException(IndexSizeError, String::format("The %s
provided is less than 0.", r0 < 0 ? "r0" : "r1")); |
1465 return nullptr; | 1465 return nullptr; |
1466 } | 1466 } |
1467 | 1467 |
1468 CanvasGradient* gradient = CanvasGradient::create(FloatPoint(x0, y0), r0, Fl
oatPoint(x1, y1), r1); | 1468 CanvasGradient* gradient = CanvasGradient::create(FloatPoint(x0, y0), r0, Fl
oatPoint(x1, y1), r1); |
1469 return gradient; | 1469 return gradient; |
1470 } | 1470 } |
1471 | 1471 |
(...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1553 if (isContextLost()) | 1553 if (isContextLost()) |
1554 return nullptr; | 1554 return nullptr; |
1555 return canvas()->drawingCanvas(); | 1555 return canvas()->drawingCanvas(); |
1556 } | 1556 } |
1557 | 1557 |
1558 ImageData* CanvasRenderingContext2D::createImageData(ImageData* imageData) const | 1558 ImageData* CanvasRenderingContext2D::createImageData(ImageData* imageData) const |
1559 { | 1559 { |
1560 return ImageData::create(imageData->size()); | 1560 return ImageData::create(imageData->size()); |
1561 } | 1561 } |
1562 | 1562 |
1563 ImageData* CanvasRenderingContext2D::createImageData(float sw, float sh, Excepti
onState& exceptionState) const | 1563 ImageData* CanvasRenderingContext2D::createImageData(double sw, double sh, Excep
tionState& exceptionState) const |
1564 { | 1564 { |
1565 if (!sw || !sh) { | 1565 if (!sw || !sh) { |
1566 exceptionState.throwDOMException(IndexSizeError, String::format("The sou
rce %s is 0.", sw ? "height" : "width")); | 1566 exceptionState.throwDOMException(IndexSizeError, String::format("The sou
rce %s is 0.", sw ? "height" : "width")); |
1567 return nullptr; | 1567 return nullptr; |
1568 } | 1568 } |
1569 | 1569 |
1570 FloatSize logicalSize(fabs(sw), fabs(sh)); | 1570 FloatSize logicalSize(fabs(sw), fabs(sh)); |
1571 if (!logicalSize.isExpressibleAsIntSize()) | 1571 if (!logicalSize.isExpressibleAsIntSize()) |
1572 return nullptr; | 1572 return nullptr; |
1573 | 1573 |
1574 IntSize size = expandedIntSize(logicalSize); | 1574 IntSize size = expandedIntSize(logicalSize); |
1575 if (size.width() < 1) | 1575 if (size.width() < 1) |
1576 size.setWidth(1); | 1576 size.setWidth(1); |
1577 if (size.height() < 1) | 1577 if (size.height() < 1) |
1578 size.setHeight(1); | 1578 size.setHeight(1); |
1579 | 1579 |
1580 return ImageData::create(size); | 1580 return ImageData::create(size); |
1581 } | 1581 } |
1582 | 1582 |
1583 ImageData* CanvasRenderingContext2D::getImageData(float sx, float sy, float sw,
float sh, ExceptionState& exceptionState) const | 1583 ImageData* CanvasRenderingContext2D::getImageData(double sx, double sy, double s
w, double sh, ExceptionState& exceptionState) const |
1584 { | 1584 { |
1585 if (!canvas()->originClean()) | 1585 if (!canvas()->originClean()) |
1586 exceptionState.throwSecurityError("The canvas has been tainted by cross-
origin data."); | 1586 exceptionState.throwSecurityError("The canvas has been tainted by cross-
origin data."); |
1587 else if (!sw || !sh) | 1587 else if (!sw || !sh) |
1588 exceptionState.throwDOMException(IndexSizeError, String::format("The sou
rce %s is 0.", sw ? "height" : "width")); | 1588 exceptionState.throwDOMException(IndexSizeError, String::format("The sou
rce %s is 0.", sw ? "height" : "width")); |
1589 | 1589 |
1590 if (exceptionState.hadException()) | 1590 if (exceptionState.hadException()) |
1591 return nullptr; | 1591 return nullptr; |
1592 | 1592 |
1593 if (sw < 0) { | 1593 if (sw < 0) { |
(...skipping 21 matching lines...) Expand all Loading... |
1615 WTF::ArrayBufferContents contents; | 1615 WTF::ArrayBufferContents contents; |
1616 if (!buffer->getImageData(Unmultiplied, imageDataRect, contents)) | 1616 if (!buffer->getImageData(Unmultiplied, imageDataRect, contents)) |
1617 return nullptr; | 1617 return nullptr; |
1618 | 1618 |
1619 RefPtr<DOMArrayBuffer> arrayBuffer = DOMArrayBuffer::create(contents); | 1619 RefPtr<DOMArrayBuffer> arrayBuffer = DOMArrayBuffer::create(contents); |
1620 return ImageData::create( | 1620 return ImageData::create( |
1621 imageDataRect.size(), | 1621 imageDataRect.size(), |
1622 DOMUint8ClampedArray::create(arrayBuffer, 0, arrayBuffer->byteLength()))
; | 1622 DOMUint8ClampedArray::create(arrayBuffer, 0, arrayBuffer->byteLength()))
; |
1623 } | 1623 } |
1624 | 1624 |
1625 void CanvasRenderingContext2D::putImageData(ImageData* data, float dx, float dy,
ExceptionState& exceptionState) | 1625 void CanvasRenderingContext2D::putImageData(ImageData* data, double dx, double d
y, ExceptionState& exceptionState) |
1626 { | 1626 { |
1627 putImageData(data, dx, dy, 0, 0, data->width(), data->height(), exceptionSta
te); | 1627 putImageData(data, dx, dy, 0, 0, data->width(), data->height(), exceptionSta
te); |
1628 } | 1628 } |
1629 | 1629 |
1630 void CanvasRenderingContext2D::putImageData(ImageData* data, float dx, float dy,
float dirtyX, float dirtyY, float dirtyWidth, float dirtyHeight, ExceptionState
& exceptionState) | 1630 void CanvasRenderingContext2D::putImageData(ImageData* data, double dx, double d
y, double dirtyX, double dirtyY, double dirtyWidth, double dirtyHeight, Exceptio
nState& exceptionState) |
1631 { | 1631 { |
1632 if (data->data()->bufferBase()->isNeutered()) { | 1632 if (data->data()->bufferBase()->isNeutered()) { |
1633 exceptionState.throwDOMException(InvalidStateError, "The source data has
been neutered."); | 1633 exceptionState.throwDOMException(InvalidStateError, "The source data has
been neutered."); |
1634 return; | 1634 return; |
1635 } | 1635 } |
1636 ImageBuffer* buffer = canvas()->buffer(); | 1636 ImageBuffer* buffer = canvas()->buffer(); |
1637 if (!buffer) | 1637 if (!buffer) |
1638 return; | 1638 return; |
1639 | 1639 |
1640 if (dirtyWidth < 0) { | 1640 if (dirtyWidth < 0) { |
(...skipping 225 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1866 direction = CanvasRenderingContext2DState::DirectionLTR; | 1866 direction = CanvasRenderingContext2DState::DirectionLTR; |
1867 else | 1867 else |
1868 return; | 1868 return; |
1869 | 1869 |
1870 if (state().direction() == direction) | 1870 if (state().direction() == direction) |
1871 return; | 1871 return; |
1872 | 1872 |
1873 modifiableState().setDirection(direction); | 1873 modifiableState().setDirection(direction); |
1874 } | 1874 } |
1875 | 1875 |
1876 void CanvasRenderingContext2D::fillText(const String& text, float x, float y) | 1876 void CanvasRenderingContext2D::fillText(const String& text, double x, double y) |
1877 { | 1877 { |
1878 drawTextInternal(text, x, y, CanvasRenderingContext2DState::FillPaintType); | 1878 drawTextInternal(text, x, y, CanvasRenderingContext2DState::FillPaintType); |
1879 } | 1879 } |
1880 | 1880 |
1881 void CanvasRenderingContext2D::fillText(const String& text, float x, float y, fl
oat maxWidth) | 1881 void CanvasRenderingContext2D::fillText(const String& text, double x, double y,
double maxWidth) |
1882 { | 1882 { |
1883 drawTextInternal(text, x, y, CanvasRenderingContext2DState::FillPaintType, &
maxWidth); | 1883 drawTextInternal(text, x, y, CanvasRenderingContext2DState::FillPaintType, &
maxWidth); |
1884 } | 1884 } |
1885 | 1885 |
1886 void CanvasRenderingContext2D::strokeText(const String& text, float x, float y) | 1886 void CanvasRenderingContext2D::strokeText(const String& text, double x, double y
) |
1887 { | 1887 { |
1888 drawTextInternal(text, x, y, CanvasRenderingContext2DState::StrokePaintType)
; | 1888 drawTextInternal(text, x, y, CanvasRenderingContext2DState::StrokePaintType)
; |
1889 } | 1889 } |
1890 | 1890 |
1891 void CanvasRenderingContext2D::strokeText(const String& text, float x, float y,
float maxWidth) | 1891 void CanvasRenderingContext2D::strokeText(const String& text, double x, double y
, double maxWidth) |
1892 { | 1892 { |
1893 drawTextInternal(text, x, y, CanvasRenderingContext2DState::StrokePaintType,
&maxWidth); | 1893 drawTextInternal(text, x, y, CanvasRenderingContext2DState::StrokePaintType,
&maxWidth); |
1894 } | 1894 } |
1895 | 1895 |
1896 TextMetrics* CanvasRenderingContext2D::measureText(const String& text) | 1896 TextMetrics* CanvasRenderingContext2D::measureText(const String& text) |
1897 { | 1897 { |
1898 TextMetrics* metrics = TextMetrics::create(); | 1898 TextMetrics* metrics = TextMetrics::create(); |
1899 | 1899 |
1900 // The style resolution required for rendering text is not available in fram
e-less documents. | 1900 // The style resolution required for rendering text is not available in fram
e-less documents. |
1901 if (!canvas()->document().frame()) | 1901 if (!canvas()->document().frame()) |
(...skipping 11 matching lines...) Expand all Loading... |
1913 textRun.setNormalizeSpace(true); | 1913 textRun.setNormalizeSpace(true); |
1914 FloatRect textBounds = font.selectionRectForText(textRun, FloatPoint(), font
.fontDescription().computedSize(), 0, -1, true); | 1914 FloatRect textBounds = font.selectionRectForText(textRun, FloatPoint(), font
.fontDescription().computedSize(), 0, -1, true); |
1915 | 1915 |
1916 // x direction | 1916 // x direction |
1917 metrics->setWidth(font.width(textRun)); | 1917 metrics->setWidth(font.width(textRun)); |
1918 metrics->setActualBoundingBoxLeft(-textBounds.x()); | 1918 metrics->setActualBoundingBoxLeft(-textBounds.x()); |
1919 metrics->setActualBoundingBoxRight(textBounds.maxX()); | 1919 metrics->setActualBoundingBoxRight(textBounds.maxX()); |
1920 | 1920 |
1921 // y direction | 1921 // y direction |
1922 const FontMetrics& fontMetrics = font.fontMetrics(); | 1922 const FontMetrics& fontMetrics = font.fontMetrics(); |
1923 const float ascent = fontMetrics.floatAscent(); | 1923 const double ascent = fontMetrics.floatAscent(); |
1924 const float descent = fontMetrics.floatDescent(); | 1924 const double descent = fontMetrics.floatDescent(); |
1925 const float baselineY = getFontBaseline(fontMetrics); | 1925 const double baselineY = getFontBaseline(fontMetrics); |
1926 | 1926 |
1927 metrics->setFontBoundingBoxAscent(ascent - baselineY); | 1927 metrics->setFontBoundingBoxAscent(ascent - baselineY); |
1928 metrics->setFontBoundingBoxDescent(descent + baselineY); | 1928 metrics->setFontBoundingBoxDescent(descent + baselineY); |
1929 metrics->setActualBoundingBoxAscent(-textBounds.y() - baselineY); | 1929 metrics->setActualBoundingBoxAscent(-textBounds.y() - baselineY); |
1930 metrics->setActualBoundingBoxDescent(textBounds.maxY() + baselineY); | 1930 metrics->setActualBoundingBoxDescent(textBounds.maxY() + baselineY); |
1931 | 1931 |
1932 // Note : top/bottom and ascend/descend are currently the same, so there's n
o difference | 1932 // Note : top/bottom and ascend/descend are currently the same, so there's n
o difference |
1933 // between the EM box's top and bottom and the font's ascend and desc
end | 1933 // between the EM box's top and bottom and the font's ascend and desc
end |
1934 metrics->setEmHeightAscent(0); | 1934 metrics->setEmHeightAscent(0); |
1935 metrics->setEmHeightDescent(0); | 1935 metrics->setEmHeightDescent(0); |
1936 | 1936 |
1937 metrics->setHangingBaseline(-0.8f * ascent + baselineY); | 1937 metrics->setHangingBaseline(-0.8f * ascent + baselineY); |
1938 metrics->setAlphabeticBaseline(baselineY); | 1938 metrics->setAlphabeticBaseline(baselineY); |
1939 metrics->setIdeographicBaseline(descent + baselineY); | 1939 metrics->setIdeographicBaseline(descent + baselineY); |
1940 return metrics; | 1940 return metrics; |
1941 } | 1941 } |
1942 | 1942 |
1943 void CanvasRenderingContext2D::drawTextInternal(const String& text, float x, flo
at y, CanvasRenderingContext2DState::PaintType paintType, float* maxWidth) | 1943 void CanvasRenderingContext2D::drawTextInternal(const String& text, double x, do
uble y, CanvasRenderingContext2DState::PaintType paintType, double* maxWidth) |
1944 { | 1944 { |
1945 // The style resolution required for rendering text is not available in fram
e-less documents. | 1945 // The style resolution required for rendering text is not available in fram
e-less documents. |
1946 if (!canvas()->document().frame()) | 1946 if (!canvas()->document().frame()) |
1947 return; | 1947 return; |
1948 | 1948 |
1949 // accessFont needs the style to be up to date, but updating style can cause
script to run, | 1949 // accessFont needs the style to be up to date, but updating style can cause
script to run, |
1950 // (e.g. due to autofocus) which can free the canvas (set size to 0, for exa
mple), so update | 1950 // (e.g. due to autofocus) which can free the canvas (set size to 0, for exa
mple), so update |
1951 // style before grabbing the drawingCanvas. | 1951 // style before grabbing the drawingCanvas. |
1952 canvas()->document().updateLayoutTreeForNodeIfNeeded(canvas()); | 1952 canvas()->document().updateLayoutTreeForNodeIfNeeded(canvas()); |
1953 | 1953 |
(...skipping 13 matching lines...) Expand all Loading... |
1967 | 1967 |
1968 const ComputedStyle* computedStyle = 0; | 1968 const ComputedStyle* computedStyle = 0; |
1969 TextDirection direction = toTextDirection(state().direction(), canvas(), &co
mputedStyle); | 1969 TextDirection direction = toTextDirection(state().direction(), canvas(), &co
mputedStyle); |
1970 bool isRTL = direction == RTL; | 1970 bool isRTL = direction == RTL; |
1971 bool override = computedStyle ? isOverride(computedStyle->unicodeBidi()) : f
alse; | 1971 bool override = computedStyle ? isOverride(computedStyle->unicodeBidi()) : f
alse; |
1972 | 1972 |
1973 TextRun textRun(text, 0, 0, TextRun::AllowTrailingExpansion, direction, over
ride); | 1973 TextRun textRun(text, 0, 0, TextRun::AllowTrailingExpansion, direction, over
ride); |
1974 textRun.setNormalizeSpace(true); | 1974 textRun.setNormalizeSpace(true); |
1975 // Draw the item text at the correct point. | 1975 // Draw the item text at the correct point. |
1976 FloatPoint location(x, y + getFontBaseline(fontMetrics)); | 1976 FloatPoint location(x, y + getFontBaseline(fontMetrics)); |
1977 float fontWidth = font.width(textRun); | 1977 double fontWidth = font.width(textRun); |
1978 | 1978 |
1979 bool useMaxWidth = (maxWidth && *maxWidth < fontWidth); | 1979 bool useMaxWidth = (maxWidth && *maxWidth < fontWidth); |
1980 float width = useMaxWidth ? *maxWidth : fontWidth; | 1980 double width = useMaxWidth ? *maxWidth : fontWidth; |
1981 | 1981 |
1982 TextAlign align = state().textAlign(); | 1982 TextAlign align = state().textAlign(); |
1983 if (align == StartTextAlign) | 1983 if (align == StartTextAlign) |
1984 align = isRTL ? RightTextAlign : LeftTextAlign; | 1984 align = isRTL ? RightTextAlign : LeftTextAlign; |
1985 else if (align == EndTextAlign) | 1985 else if (align == EndTextAlign) |
1986 align = isRTL ? LeftTextAlign : RightTextAlign; | 1986 align = isRTL ? LeftTextAlign : RightTextAlign; |
1987 | 1987 |
1988 switch (align) { | 1988 switch (align) { |
1989 case CenterTextAlign: | 1989 case CenterTextAlign: |
1990 location.setX(location.x() - width / 2); | 1990 location.setX(location.x() - width / 2); |
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2024 return false; | 2024 return false; |
2025 }, | 2025 }, |
2026 textRunPaintInfo.bounds, paintType); | 2026 textRunPaintInfo.bounds, paintType); |
2027 } | 2027 } |
2028 | 2028 |
2029 void CanvasRenderingContext2D::inflateStrokeRect(FloatRect& rect) const | 2029 void CanvasRenderingContext2D::inflateStrokeRect(FloatRect& rect) const |
2030 { | 2030 { |
2031 // Fast approximation of the stroke's bounding rect. | 2031 // Fast approximation of the stroke's bounding rect. |
2032 // This yields a slightly oversized rect but is very fast | 2032 // This yields a slightly oversized rect but is very fast |
2033 // compared to Path::strokeBoundingRect(). | 2033 // compared to Path::strokeBoundingRect(). |
2034 static const float root2 = sqrtf(2); | 2034 static const double root2 = sqrtf(2); |
2035 float delta = state().lineWidth() / 2; | 2035 double delta = state().lineWidth() / 2; |
2036 if (state().lineJoin() == MiterJoin) | 2036 if (state().lineJoin() == MiterJoin) |
2037 delta *= state().miterLimit(); | 2037 delta *= state().miterLimit(); |
2038 else if (state().lineCap() == SquareCap) | 2038 else if (state().lineCap() == SquareCap) |
2039 delta *= root2; | 2039 delta *= root2; |
2040 | 2040 |
2041 rect.inflate(delta); | 2041 rect.inflate(delta); |
2042 } | 2042 } |
2043 | 2043 |
2044 const Font& CanvasRenderingContext2D::accessFont() | 2044 const Font& CanvasRenderingContext2D::accessFont() |
2045 { | 2045 { |
(...skipping 287 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2333 if (imageType == CanvasRenderingContext2DState::NonOpaqueImage) | 2333 if (imageType == CanvasRenderingContext2DState::NonOpaqueImage) |
2334 return; | 2334 return; |
2335 if (alpha < 0xFF) | 2335 if (alpha < 0xFF) |
2336 return; | 2336 return; |
2337 } | 2337 } |
2338 | 2338 |
2339 canvas()->buffer()->willOverwriteCanvas(); | 2339 canvas()->buffer()->willOverwriteCanvas(); |
2340 } | 2340 } |
2341 | 2341 |
2342 } // namespace blink | 2342 } // namespace blink |
OLD | NEW |