Home | History | Annotate | Download | only in shapes
      1 /*
      2 * Copyright (C) 2012 Adobe Systems Incorporated. All rights reserved.
      3 *
      4 * Redistribution and use in source and binary forms, with or without
      5 * modification, are permitted provided that the following conditions
      6 * are met:
      7 *
      8 * 1. Redistributions of source code must retain the above
      9 *    copyright notice, this list of conditions and the following
     10 *    disclaimer.
     11 * 2. Redistributions in binary form must reproduce the above
     12 *    copyright notice, this list of conditions and the following
     13 *    disclaimer in the documentation and/or other materials
     14 *    provided with the distribution.
     15 *
     16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER "AS IS" AND ANY
     17 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
     18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
     19 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE
     20 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,
     21 * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
     22 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
     23 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
     24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
     25 * TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
     26 * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
     27 * SUCH DAMAGE.
     28 */
     29 
     30 #ifndef ShapeInfo_h
     31 #define ShapeInfo_h
     32 
     33 #include "core/rendering/shapes/Shape.h"
     34 #include "core/rendering/style/RenderStyle.h"
     35 #include "core/rendering/style/ShapeValue.h"
     36 #include "platform/LayoutUnit.h"
     37 #include "platform/geometry/FloatRect.h"
     38 #include "wtf/OwnPtr.h"
     39 #include "wtf/Vector.h"
     40 
     41 namespace WebCore {
     42 
     43 template<class KeyType, class InfoType>
     44 class MappedInfo {
     45 public:
     46     static InfoType* ensureInfo(const KeyType* key)
     47     {
     48         InfoMap& infoMap = MappedInfo<KeyType, InfoType>::infoMap();
     49         if (InfoType* info = infoMap.get(key))
     50             return info;
     51         typename InfoMap::AddResult result = infoMap.add(key, InfoType::createInfo(key));
     52         return result.iterator->value.get();
     53     }
     54     static void removeInfo(const KeyType* key) { infoMap().remove(key); }
     55     static InfoType* info(const KeyType* key) { return infoMap().get(key); }
     56 private:
     57     typedef HashMap<const KeyType*, OwnPtr<InfoType> > InfoMap;
     58     static InfoMap& infoMap()
     59     {
     60         DEFINE_STATIC_LOCAL(InfoMap, staticInfoMap, ());
     61         return staticInfoMap;
     62     }
     63 };
     64 
     65 template<class RenderType>
     66 class ShapeInfo {
     67     WTF_MAKE_FAST_ALLOCATED;
     68 public:
     69     virtual ~ShapeInfo() { }
     70 
     71     void setShapeSize(LayoutUnit logicalWidth, LayoutUnit logicalHeight)
     72     {
     73         if (shapeValue()->type() == ShapeValue::Box) {
     74             switch (shapeValue()->layoutBox()) {
     75             case MarginBox:
     76                 logicalHeight += m_renderer->marginLogicalHeight();
     77                 logicalWidth += m_renderer->marginLogicalWidth();
     78                 break;
     79             case BorderBox:
     80                 break;
     81             case PaddingBox:
     82                 logicalHeight -= m_renderer->borderLogicalHeight();
     83                 logicalWidth -= m_renderer->borderLogicalWidth();
     84                 break;
     85             case ContentBox:
     86                 logicalHeight -= m_renderer->borderAndPaddingLogicalHeight();
     87                 logicalWidth -= m_renderer->borderAndPaddingLogicalWidth();
     88                 break;
     89             }
     90         } else if (m_renderer->style()->boxSizing() == CONTENT_BOX) {
     91             logicalHeight -= m_renderer->borderAndPaddingLogicalHeight();
     92             logicalWidth -= m_renderer->borderAndPaddingLogicalWidth();
     93         }
     94 
     95         LayoutSize newLogicalSize(logicalWidth, logicalHeight);
     96         if (m_shapeLogicalSize == newLogicalSize)
     97             return;
     98         dirtyShapeSize();
     99         m_shapeLogicalSize = newLogicalSize;
    100     }
    101 
    102     SegmentList computeSegmentsForLine(LayoutUnit lineTop, LayoutUnit lineHeight) const;
    103 
    104     LayoutUnit shapeLogicalTop() const { return computedShapeLogicalBoundingBox().y() + logicalTopOffset(); }
    105     LayoutUnit shapeLogicalBottom() const { return computedShapeLogicalBoundingBox().maxY() + logicalTopOffset(); }
    106     LayoutUnit shapeLogicalLeft() const { return computedShapeLogicalBoundingBox().x() + logicalLeftOffset(); }
    107     LayoutUnit shapeLogicalRight() const { return computedShapeLogicalBoundingBox().maxX() + logicalLeftOffset(); }
    108     LayoutUnit shapeLogicalWidth() const { return computedShapeLogicalBoundingBox().width(); }
    109     LayoutUnit shapeLogicalHeight() const { return computedShapeLogicalBoundingBox().height(); }
    110 
    111     LayoutUnit logicalLineTop() const { return m_shapeLineTop + logicalTopOffset(); }
    112     LayoutUnit logicalLineBottom() const { return m_shapeLineTop + m_lineHeight + logicalTopOffset(); }
    113 
    114     LayoutUnit shapeContainingBlockHeight() const { return (m_renderer->style()->boxSizing() == CONTENT_BOX) ? (m_shapeLogicalSize.height() + m_renderer->borderAndPaddingLogicalHeight()) : m_shapeLogicalSize.height(); }
    115 
    116     virtual bool lineOverlapsShapeBounds() const = 0;
    117 
    118     void dirtyShapeSize() { m_shape.clear(); }
    119     bool shapeSizeDirty() { return !m_shape.get(); }
    120     const RenderType* owner() const { return m_renderer; }
    121     LayoutSize shapeSize() const { return m_shapeLogicalSize; }
    122 
    123 protected:
    124     ShapeInfo(const RenderType* renderer): m_renderer(renderer) { }
    125 
    126     const Shape* computedShape() const;
    127 
    128     virtual LayoutRect computedShapeLogicalBoundingBox() const = 0;
    129     virtual ShapeValue* shapeValue() const = 0;
    130     virtual void getIntervals(LayoutUnit, LayoutUnit, SegmentList&) const = 0;
    131 
    132     LayoutUnit logicalTopOffset() const
    133     {
    134         if (shapeValue()->type() == ShapeValue::Box) {
    135             switch (shapeValue()->layoutBox()) {
    136             case MarginBox:
    137                 return -m_renderer->marginBefore();
    138             case BorderBox:
    139                 return LayoutUnit();
    140             case PaddingBox:
    141                 return m_renderer->borderBefore();
    142             case ContentBox:
    143                 return m_renderer->borderAndPaddingBefore();
    144             }
    145         }
    146         return m_renderer->style()->boxSizing() == CONTENT_BOX ? m_renderer->borderAndPaddingBefore() : LayoutUnit();
    147     }
    148 
    149     LayoutUnit logicalLeftOffset() const
    150     {
    151         if (shapeValue()->type() == ShapeValue::Box) {
    152             switch (shapeValue()->layoutBox()) {
    153             case MarginBox:
    154                 return -m_renderer->marginStart();
    155             case BorderBox:
    156                 return LayoutUnit();
    157             case PaddingBox:
    158                 return m_renderer->borderStart();
    159             case ContentBox:
    160                 return m_renderer->borderAndPaddingStart();
    161             }
    162         }
    163         return (m_renderer->style()->boxSizing() == CONTENT_BOX && !m_renderer->isRenderRegion()) ? m_renderer->borderAndPaddingStart() : LayoutUnit();
    164     }
    165 
    166     LayoutUnit m_shapeLineTop;
    167     LayoutUnit m_lineHeight;
    168 
    169     const RenderType* m_renderer;
    170 
    171 private:
    172     mutable OwnPtr<Shape> m_shape;
    173     LayoutSize m_shapeLogicalSize;
    174 };
    175 
    176 bool checkShapeImageOrigin(Document&, ImageResource&);
    177 
    178 }
    179 #endif
    180