SVGPaintServerPatternCg.cpp [plain text]
#include "config.h"
#if ENABLE(SVG)
#include "SVGPaintServerPattern.h"
#include "CgSupport.h"
#include "GraphicsContext.h"
#include "ImageBuffer.h"
#include "RenderObject.h"
#include "SVGPatternElement.h"
namespace WebCore {
static void patternCallback(void* info, CGContextRef context)
{
ImageBuffer* patternImage = reinterpret_cast<ImageBuffer*>(info);
IntSize patternContentSize = patternImage->size();
CGContextDrawImage(context, CGRectMake(0, 0, patternContentSize.width(), patternContentSize.height()), patternImage->cgImage());
}
bool SVGPaintServerPattern::setup(GraphicsContext*& context, const RenderObject* object, SVGPaintTargetType type, bool isPaintingText) const
{
CGContextRef contextRef = context->platformContext();
FloatRect targetRect;
if (isPaintingText) {
IntRect textBoundary = const_cast<RenderObject*>(object)->absoluteBoundingBoxRect();
targetRect = object->absoluteTransform().inverse().mapRect(textBoundary);
} else
targetRect = CGContextGetPathBoundingBox(contextRef);
m_ownerElement->buildPattern(targetRect);
if (!tile())
return false;
CGSize cellSize = CGSize(tile()->size());
CGFloat alpha = 1;
context->save();
CGContextConcatCTM(contextRef, patternTransform());
CGSize phase = CGSizeMake(patternBoundaries().x(), -patternBoundaries().y());
CGContextSetPatternPhase(contextRef, phase);
RenderStyle* style = object->style();
CGContextSetAlpha(contextRef, style->opacity());
ASSERT(!m_pattern);
CGPatternCallbacks callbacks = {0, patternCallback, NULL};
m_pattern = CGPatternCreate(tile(),
CGRectMake(0, 0, cellSize.width, cellSize.height),
CGContextGetCTM(contextRef),
patternBoundaries().width(),
patternBoundaries().height(),
kCGPatternTilingConstantSpacing, true, &callbacks);
if (!m_patternSpace)
m_patternSpace = CGColorSpaceCreatePattern(0);
if ((type & ApplyToFillTargetType) && style->svgStyle()->hasFill()) {
CGContextSetFillColorSpace(contextRef, m_patternSpace);
CGContextSetFillPattern(contextRef, m_pattern, &alpha);
if (isPaintingText)
context->setTextDrawingMode(cTextFill);
}
if ((type & ApplyToStrokeTargetType) && style->svgStyle()->hasStroke()) {
CGContextSetStrokeColorSpace(contextRef, m_patternSpace);
CGContextSetStrokePattern(contextRef, m_pattern, &alpha);
applyStrokeStyleToContext(contextRef, style, object);
if (isPaintingText)
context->setTextDrawingMode(cTextStroke);
}
return true;
}
void SVGPaintServerPattern::teardown(GraphicsContext*& context, const RenderObject*, SVGPaintTargetType, bool) const
{
CGPatternRelease(m_pattern);
m_pattern = 0;
context->restore();
}
}
#endif