Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 /* | 1 /* |
| 2 * Copyright (C) 2004, 2006, 2007 Apple Inc. All rights reserved. | 2 * Copyright (C) 2004, 2006, 2007 Apple Inc. All rights reserved. |
| 3 * Copyright (C) 2007 Alp Toker <alp@atoker.com> | 3 * Copyright (C) 2007 Alp Toker <alp@atoker.com> |
| 4 * Copyright (C) 2010 Torch Mobile (Beijing) Co. Ltd. All rights reserved. | 4 * Copyright (C) 2010 Torch Mobile (Beijing) Co. Ltd. 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 111 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 122 return StaticBitmapImage::create(adoptRef(surface->newImageSnapshot())); | 122 return StaticBitmapImage::create(adoptRef(surface->newImageSnapshot())); |
| 123 } | 123 } |
| 124 | 124 |
| 125 } // namespace | 125 } // namespace |
| 126 | 126 |
| 127 inline HTMLCanvasElement::HTMLCanvasElement(Document& document) | 127 inline HTMLCanvasElement::HTMLCanvasElement(Document& document) |
| 128 : HTMLElement(canvasTag, document) | 128 : HTMLElement(canvasTag, document) |
| 129 , DocumentVisibilityObserver(document) | 129 , DocumentVisibilityObserver(document) |
| 130 , m_size(DefaultWidth, DefaultHeight) | 130 , m_size(DefaultWidth, DefaultHeight) |
| 131 , m_ignoreReset(false) | 131 , m_ignoreReset(false) |
| 132 , m_externallyAllocatedMemory(0) | |
| 133 , m_originClean(true) | 132 , m_originClean(true) |
| 134 , m_didFailToCreateImageBuffer(false) | 133 , m_didFailToCreateImageBuffer(false) |
| 135 , m_imageBufferIsClear(false) | 134 , m_imageBufferIsClear(false) |
| 136 { | 135 { |
| 137 setHasCustomStyleCallbacks(); | 136 setHasCustomStyleCallbacks(); |
| 138 CanvasMetrics::countCanvasContextUsage(CanvasMetrics::CanvasCreated); | 137 CanvasMetrics::countCanvasContextUsage(CanvasMetrics::CanvasCreated); |
| 139 } | 138 } |
| 140 | 139 |
| 141 DEFINE_NODE_FACTORY(HTMLCanvasElement) | 140 DEFINE_NODE_FACTORY(HTMLCanvasElement) |
| 142 | 141 |
| 143 HTMLCanvasElement::~HTMLCanvasElement() | 142 HTMLCanvasElement::~HTMLCanvasElement() |
| 144 { | 143 { |
| 145 v8::Isolate::GetCurrent()->AdjustAmountOfExternalAllocatedMemory(-m_external lyAllocatedMemory); | |
| 146 #if !ENABLE(OILPAN) | 144 #if !ENABLE(OILPAN) |
| 147 // Ensure these go away before the ImageBuffer. | 145 // Ensure these go away before the ImageBuffer. |
| 148 m_context.clear(); | 146 m_context.clear(); |
| 149 #endif | 147 #endif |
| 150 } | 148 } |
| 151 | 149 |
| 152 void HTMLCanvasElement::parseAttribute(const QualifiedName& name, const AtomicSt ring& oldValue, const AtomicString& value) | 150 void HTMLCanvasElement::parseAttribute(const QualifiedName& name, const AtomicSt ring& oldValue, const AtomicString& value) |
| 153 { | 151 { |
| 154 if (name == widthAttr || name == heightAttr) | 152 if (name == widthAttr || name == heightAttr) |
| 155 reset(); | 153 reset(); |
| (...skipping 102 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 258 } | 256 } |
| 259 | 257 |
| 260 m_context = factory->create(this, attributes, document()); | 258 m_context = factory->create(this, attributes, document()); |
| 261 if (!m_context) | 259 if (!m_context) |
| 262 return nullptr; | 260 return nullptr; |
| 263 | 261 |
| 264 if (m_context->is3d()) { | 262 if (m_context->is3d()) { |
| 265 const ComputedStyle* style = ensureComputedStyle(); | 263 const ComputedStyle* style = ensureComputedStyle(); |
| 266 if (style) | 264 if (style) |
| 267 m_context->setFilterQuality(style->imageRendering() == ImageRenderin gPixelated ? kNone_SkFilterQuality : kLow_SkFilterQuality); | 265 m_context->setFilterQuality(style->imageRendering() == ImageRenderin gPixelated ? kNone_SkFilterQuality : kLow_SkFilterQuality); |
| 268 updateExternallyAllocatedMemory(); | |
| 269 } | 266 } |
| 270 setNeedsCompositingUpdate(); | 267 setNeedsCompositingUpdate(); |
| 271 | 268 |
| 272 return m_context.get(); | 269 return m_context.get(); |
| 273 } | 270 } |
| 274 | 271 |
| 275 bool HTMLCanvasElement::shouldBeDirectComposited() const | 272 bool HTMLCanvasElement::shouldBeDirectComposited() const |
| 276 { | 273 { |
| 277 return (m_context && m_context->isAccelerated()) || (hasImageBuffer() && buf fer()->isExpensiveToPaint()); | 274 return (m_context && m_context->isAccelerated()) || (hasImageBuffer() && buf fer()->isExpensiveToPaint()); |
| 278 } | 275 } |
| (...skipping 498 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 777 if (!m_imageBuffer) | 774 if (!m_imageBuffer) |
| 778 return; | 775 return; |
| 779 m_imageBuffer->setClient(this); | 776 m_imageBuffer->setClient(this); |
| 780 | 777 |
| 781 document().updateLayoutTreeIfNeeded(); | 778 document().updateLayoutTreeIfNeeded(); |
| 782 const ComputedStyle* style = ensureComputedStyle(); | 779 const ComputedStyle* style = ensureComputedStyle(); |
| 783 m_imageBuffer->setFilterQuality((style && (style->imageRendering() == ImageR enderingPixelated)) ? kNone_SkFilterQuality : kLow_SkFilterQuality); | 780 m_imageBuffer->setFilterQuality((style && (style->imageRendering() == ImageR enderingPixelated)) ? kNone_SkFilterQuality : kLow_SkFilterQuality); |
| 784 | 781 |
| 785 m_didFailToCreateImageBuffer = false; | 782 m_didFailToCreateImageBuffer = false; |
| 786 | 783 |
| 787 updateExternallyAllocatedMemory(); | |
| 788 | |
| 789 if (is3D()) { | 784 if (is3D()) { |
| 790 // Early out for WebGL canvases | 785 // Early out for WebGL canvases |
| 791 return; | 786 return; |
| 792 } | 787 } |
| 793 | 788 |
| 794 m_imageBuffer->setClient(this); | 789 m_imageBuffer->setClient(this); |
| 795 // Enabling MSAA overrides a request to disable antialiasing. This is true r egardless of whether the | 790 // Enabling MSAA overrides a request to disable antialiasing. This is true r egardless of whether the |
| 796 // rendering mode is accelerated or not. For consistency, we don't want to a pply AA in accelerated | 791 // rendering mode is accelerated or not. For consistency, we don't want to a pply AA in accelerated |
| 797 // canvases but not in unaccelerated canvases. | 792 // canvases but not in unaccelerated canvases. |
| 798 if (!msaaSampleCount && document().settings() && !document().settings()->ant ialiased2dCanvasEnabled()) | 793 if (!msaaSampleCount && document().settings() && !document().settings()->ant ialiased2dCanvasEnabled()) |
| (...skipping 10 matching lines...) Expand all Loading... | |
| 809 } | 804 } |
| 810 | 805 |
| 811 DEFINE_TRACE(HTMLCanvasElement) | 806 DEFINE_TRACE(HTMLCanvasElement) |
| 812 { | 807 { |
| 813 visitor->trace(m_listeners); | 808 visitor->trace(m_listeners); |
| 814 visitor->trace(m_context); | 809 visitor->trace(m_context); |
| 815 DocumentVisibilityObserver::trace(visitor); | 810 DocumentVisibilityObserver::trace(visitor); |
| 816 HTMLElement::trace(visitor); | 811 HTMLElement::trace(visitor); |
| 817 } | 812 } |
| 818 | 813 |
| 819 void HTMLCanvasElement::updateExternallyAllocatedMemory() const | |
| 820 { | |
| 821 int bufferCount = 0; | |
| 822 if (m_imageBuffer) { | |
| 823 bufferCount++; | |
| 824 if (m_imageBuffer->isAccelerated()) { | |
| 825 // The number of internal GPU buffers vary between one (stable | |
| 826 // non-displayed state) and three (triple-buffered animations). | |
| 827 // Adding 2 is a pessimistic but relevant estimate. | |
| 828 // Note: These buffers might be allocated in GPU memory. | |
| 829 bufferCount += 2; | |
| 830 } | |
| 831 } | |
| 832 if (m_copiedImage) | |
| 833 bufferCount++; | |
| 834 | |
| 835 // Four bytes per pixel per buffer. | |
| 836 Checked<intptr_t, RecordOverflow> checkedExternallyAllocatedMemory = 4 * buf ferCount; | |
| 837 if (is3D()) | |
| 838 checkedExternallyAllocatedMemory += m_context->externallyAllocatedBytesP erPixel(); | |
| 839 | |
| 840 checkedExternallyAllocatedMemory *= width(); | |
| 841 checkedExternallyAllocatedMemory *= height(); | |
| 842 intptr_t externallyAllocatedMemory; | |
| 843 if (checkedExternallyAllocatedMemory.safeGet(externallyAllocatedMemory) == C heckedState::DidOverflow) | |
| 844 externallyAllocatedMemory = std::numeric_limits<intptr_t>::max(); | |
| 845 | |
| 846 // Subtracting two intptr_t that are known to be positive will never underfl ow. | |
| 847 v8::Isolate::GetCurrent()->AdjustAmountOfExternalAllocatedMemory(externallyA llocatedMemory - m_externallyAllocatedMemory); | |
|
haraken
2016/02/08 11:17:20
This AdjustAmountOfMemory is explaining GPU's memo
peria
2016/02/09 06:39:59
You're right. reverted.
| |
| 848 m_externallyAllocatedMemory = externallyAllocatedMemory; | |
| 849 } | |
| 850 | |
| 851 SkCanvas* HTMLCanvasElement::drawingCanvas() const | 814 SkCanvas* HTMLCanvasElement::drawingCanvas() const |
| 852 { | 815 { |
| 853 return buffer() ? m_imageBuffer->canvas() : nullptr; | 816 return buffer() ? m_imageBuffer->canvas() : nullptr; |
| 854 } | 817 } |
| 855 | 818 |
| 856 void HTMLCanvasElement::disableDeferral() const | 819 void HTMLCanvasElement::disableDeferral() const |
| 857 { | 820 { |
| 858 if (buffer()) | 821 if (buffer()) |
| 859 m_imageBuffer->disableDeferral(); | 822 m_imageBuffer->disableDeferral(); |
| 860 } | 823 } |
| (...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 900 return nullptr; | 863 return nullptr; |
| 901 if (!m_context) | 864 if (!m_context) |
| 902 return createTransparentImage(size()); | 865 return createTransparentImage(size()); |
| 903 | 866 |
| 904 bool needToUpdate = !m_copiedImage; | 867 bool needToUpdate = !m_copiedImage; |
| 905 // The concept of SourceDrawingBuffer is valid on only WebGL. | 868 // The concept of SourceDrawingBuffer is valid on only WebGL. |
| 906 if (m_context->is3d()) | 869 if (m_context->is3d()) |
| 907 needToUpdate |= m_context->paintRenderingResultsToCanvas(sourceBuffer); | 870 needToUpdate |= m_context->paintRenderingResultsToCanvas(sourceBuffer); |
| 908 if (needToUpdate && buffer()) { | 871 if (needToUpdate && buffer()) { |
| 909 m_copiedImage = buffer()->newImageSnapshot(hint); | 872 m_copiedImage = buffer()->newImageSnapshot(hint); |
| 910 updateExternallyAllocatedMemory(); | |
| 911 } | 873 } |
| 912 return m_copiedImage; | 874 return m_copiedImage; |
| 913 } | 875 } |
| 914 | 876 |
| 915 void HTMLCanvasElement::discardImageBuffer() | 877 void HTMLCanvasElement::discardImageBuffer() |
| 916 { | 878 { |
| 917 m_imageBuffer.clear(); | 879 m_imageBuffer.clear(); |
| 918 m_dirtyRect = FloatRect(); | 880 m_dirtyRect = FloatRect(); |
| 919 updateExternallyAllocatedMemory(); | |
| 920 } | 881 } |
| 921 | 882 |
| 922 void HTMLCanvasElement::clearCopiedImage() | 883 void HTMLCanvasElement::clearCopiedImage() |
| 923 { | 884 { |
| 924 if (m_copiedImage) { | 885 if (m_copiedImage) { |
| 925 m_copiedImage.clear(); | 886 m_copiedImage.clear(); |
| 926 updateExternallyAllocatedMemory(); | |
| 927 } | 887 } |
| 928 } | 888 } |
| 929 | 889 |
| 930 AffineTransform HTMLCanvasElement::baseTransform() const | 890 AffineTransform HTMLCanvasElement::baseTransform() const |
| 931 { | 891 { |
| 932 ASSERT(hasImageBuffer() && !m_didFailToCreateImageBuffer); | 892 ASSERT(hasImageBuffer() && !m_didFailToCreateImageBuffer); |
| 933 return m_imageBuffer->baseTransform(); | 893 return m_imageBuffer->baseTransform(); |
| 934 } | 894 } |
| 935 | 895 |
| 936 void HTMLCanvasElement::didChangeVisibilityState(PageVisibilityState visibility) | 896 void HTMLCanvasElement::didChangeVisibilityState(PageVisibilityState visibility) |
| (...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1016 } | 976 } |
| 1017 return ImageBitmapSource::fulfillImageBitmap(scriptState, isPaintable() ? Im ageBitmap::create(this, IntRect(sx, sy, sw, sh), options) : nullptr); | 977 return ImageBitmapSource::fulfillImageBitmap(scriptState, isPaintable() ? Im ageBitmap::create(this, IntRect(sx, sy, sw, sh), options) : nullptr); |
| 1018 } | 978 } |
| 1019 | 979 |
| 1020 bool HTMLCanvasElement::isOpaque() const | 980 bool HTMLCanvasElement::isOpaque() const |
| 1021 { | 981 { |
| 1022 return m_context && !m_context->hasAlpha(); | 982 return m_context && !m_context->hasAlpha(); |
| 1023 } | 983 } |
| 1024 | 984 |
| 1025 } // namespace blink | 985 } // namespace blink |
| OLD | NEW |