Пример #1
0
static inline void adjustFocusRingColor(Color& color)
{
#if !PLATFORM(GTK)
    // Force the alpha to 50%.  This matches what the Mac does with outline rings.
    color.setRGB(makeRGBA(color.red(), color.green(), color.blue(), 127));
#endif
}
Пример #2
0
void SVGAnimatedColorAnimator::calculateAnimatedValue(float percentage, unsigned repeatCount, SVGAnimatedType* from, SVGAnimatedType* to, SVGAnimatedType* toAtEndOfDuration, SVGAnimatedType* animated)
{
    ASSERT(m_animationElement);
    ASSERT(m_contextElement);

    StyleColor fromStyleColor = m_animationElement->animationMode() == ToAnimation ? animated->color() : from->color();
    StyleColor toStyleColor = to->color();
    StyleColor toAtEndOfDurationStyleColor = toAtEndOfDuration->color();
    StyleColor& animatedStyleColor = animated->color();

    // Apply CSS inheritance rules.
    m_animationElement->adjustForInheritance<StyleColor>(parseColorFromString, m_animationElement->fromPropertyValueType(), fromStyleColor, m_contextElement);
    m_animationElement->adjustForInheritance<StyleColor>(parseColorFromString, m_animationElement->toPropertyValueType(), toStyleColor, m_contextElement);

    // Apply currentColor rules.
    Color fallbackColor = fallbackColorForCurrentColor(m_contextElement);
    Color fromColor = fromStyleColor.resolve(fallbackColor);
    Color toColor = toStyleColor.resolve(fallbackColor);
    Color toAtEndOfDurationColor = toAtEndOfDurationStyleColor.resolve(fallbackColor);
    Color animatedColor = animatedStyleColor.resolve(fallbackColor);

    float animatedRed = animatedColor.red();
    m_animationElement->animateAdditiveNumber(percentage, repeatCount, fromColor.red(), toColor.red(), toAtEndOfDurationColor.red(), animatedRed);

    float animatedGreen = animatedColor.green();
    m_animationElement->animateAdditiveNumber(percentage, repeatCount, fromColor.green(), toColor.green(), toAtEndOfDurationColor.green(), animatedGreen);

    float animatedBlue = animatedColor.blue();
    m_animationElement->animateAdditiveNumber(percentage, repeatCount, fromColor.blue(), toColor.blue(), toAtEndOfDurationColor.blue(), animatedBlue);

    float animatedAlpha = animatedColor.alpha();
    m_animationElement->animateAdditiveNumber(percentage, repeatCount, fromColor.alpha(), toColor.alpha(), toAtEndOfDurationColor.alpha(), animatedAlpha);

    animatedStyleColor = StyleColor(makeRGBA(roundf(animatedRed), roundf(animatedGreen), roundf(animatedBlue), roundf(animatedAlpha)));
}
Пример #3
0
void SVGColorProperty::calculateAnimatedValue(SVGAnimationElement* animationElement, float percentage, unsigned repeatCount, PassRefPtr<NewSVGPropertyBase> fromValue, PassRefPtr<NewSVGPropertyBase> toValue, PassRefPtr<NewSVGPropertyBase> toAtEndOfDurationValue, SVGElement* contextElement)
{
    StyleColor fromStyleColor = toSVGColorProperty(fromValue)->m_styleColor;
    StyleColor toStyleColor = toSVGColorProperty(toValue)->m_styleColor;
    StyleColor toAtEndOfDurationStyleColor = toSVGColorProperty(toAtEndOfDurationValue)->m_styleColor;

    // Apply currentColor rules.
    ASSERT(contextElement);
    Color fallbackColor = fallbackColorForCurrentColor(contextElement);
    Color fromColor = fromStyleColor.resolve(fallbackColor);
    Color toColor = toStyleColor.resolve(fallbackColor);
    Color toAtEndOfDurationColor = toAtEndOfDurationStyleColor.resolve(fallbackColor);
    Color animatedColor = m_styleColor.resolve(fallbackColor);

    ASSERT(animationElement);
    float animatedRed = animatedColor.red();
    animationElement->animateAdditiveNumber(percentage, repeatCount, fromColor.red(), toColor.red(), toAtEndOfDurationColor.red(), animatedRed);

    float animatedGreen = animatedColor.green();
    animationElement->animateAdditiveNumber(percentage, repeatCount, fromColor.green(), toColor.green(), toAtEndOfDurationColor.green(), animatedGreen);

    float animatedBlue = animatedColor.blue();
    animationElement->animateAdditiveNumber(percentage, repeatCount, fromColor.blue(), toColor.blue(), toAtEndOfDurationColor.blue(), animatedBlue);

    float animatedAlpha = animatedColor.alpha();
    animationElement->animateAdditiveNumber(percentage, repeatCount, fromColor.alpha(), toColor.alpha(), toAtEndOfDurationColor.alpha(), animatedAlpha);

    m_styleColor = StyleColor(makeRGBA(roundf(animatedRed), roundf(animatedGreen), roundf(animatedBlue), roundf(animatedAlpha)));
}
Пример #4
0
Color::Color(CGColorRef color)
{
    if (!color) {
        m_color = 0;
        m_valid = false;
        return;
    }

    size_t numComponents = CGColorGetNumberOfComponents(color);
    const CGFloat* components = CGColorGetComponents(color);

    float r = 0;
    float g = 0;
    float b = 0;
    float a = 0;

    switch (numComponents) {
    case 2:
        r = g = b = components[0];
        a = components[1];
        break;
    case 4:
        r = components[0];
        g = components[1];
        b = components[2];
        a = components[3];
        break;
    default:
        ASSERT_NOT_REACHED();
    }

    m_color = makeRGBA(r * 255, g * 255, b * 255, a * 255);
    m_valid = true;
}
Пример #5
0
static bool parseRGBParameters(CSSParserTokenRange& range, RGBA32& result, bool parseAlpha)
{
    ASSERT(range.peek().functionId() == CSSValueRgb || range.peek().functionId() == CSSValueRgba);
    CSSParserTokenRange args = consumeFunction(range);
    CSSPrimitiveValue* colorParameter = consumeInteger(args);
    if (!colorParameter)
        colorParameter = consumePercent(args, ValueRangeAll);
    if (!colorParameter)
        return false;
    const bool isPercent = colorParameter->isPercentage();
    int colorArray[3];
    colorArray[0] = clampRGBComponent(*colorParameter);
    for (int i = 1; i < 3; i++) {
        if (!consumeCommaIncludingWhitespace(args))
            return false;
        colorParameter = isPercent ? consumePercent(args, ValueRangeAll) : consumeInteger(args);
        if (!colorParameter)
            return false;
        colorArray[i] = clampRGBComponent(*colorParameter);
    }
    if (parseAlpha) {
        if (!consumeCommaIncludingWhitespace(args))
            return false;
        double alpha;
        if (!consumeNumberRaw(args, alpha))
            return false;
        // Convert the floating pointer number of alpha to an integer in the range [0, 256),
        // with an equal distribution across all 256 values.
        int alphaComponent = static_cast<int>(clampTo<double>(alpha, 0.0, 1.0) * nextafter(256.0, 0.0));
        result = makeRGBA(colorArray[0], colorArray[1], colorArray[2], alphaComponent);
    } else {
        result = makeRGB(colorArray[0], colorArray[1], colorArray[2]);
    }
    return args.atEnd();
}
Пример #6
0
RGBA32 makeRGBAFromCMYKA(float c, float m, float y, float k, float a)
{
    double colors = 1 - k;
    int r = static_cast<int>(nextafter(256, 0) * (colors * (1 - c)));
    int g = static_cast<int>(nextafter(256, 0) * (colors * (1 - m)));
    int b = static_cast<int>(nextafter(256, 0) * (colors * (1 - y)));
    return makeRGBA(r, g, b, static_cast<float>(nextafter(256, 0) * a));
}
Пример #7
0
// all values are in the range of 0 to 1.0
RGBA32 makeRGBAFromHSLA(double hue, double saturation, double lightness, double alpha)
{
    const double scaleFactor = nextafter(256.0, 0.0);

    if (!saturation) {
        int greyValue = static_cast<int>(lightness * scaleFactor);
        return makeRGBA(greyValue, greyValue, greyValue, static_cast<int>(alpha * scaleFactor));
    }

    double temp2 = lightness < 0.5 ? lightness * (1.0 + saturation) : lightness + saturation - lightness * saturation;
    double temp1 = 2.0 * lightness - temp2;

    return makeRGBA(static_cast<int>(calcHue(temp1, temp2, hue + 1.0 / 3.0) * scaleFactor),
                    static_cast<int>(calcHue(temp1, temp2, hue) * scaleFactor),
                    static_cast<int>(calcHue(temp1, temp2, hue - 1.0 / 3.0) * scaleFactor),
                    static_cast<int>(alpha * scaleFactor));
}
Пример #8
0
static bool fastParseColorInternal(RGBA32& rgb,
                                   const CharacterType* characters,
                                   unsigned length,
                                   bool quirksMode) {
  CSSPrimitiveValue::UnitType expect = CSSPrimitiveValue::UnitType::Unknown;

  if (length >= 4 && characters[0] == '#')
    return Color::parseHexColor(characters + 1, length - 1, rgb);

  if (quirksMode && (length == 3 || length == 6)) {
    if (Color::parseHexColor(characters, length, rgb))
      return true;
  }

  // Try rgba() syntax.
  if (mightBeRGBA(characters, length)) {
    const CharacterType* current = characters + 5;
    const CharacterType* end = characters + length;
    int red;
    int green;
    int blue;
    int alpha;

    if (!parseColorIntOrPercentage(current, end, ',', expect, red))
      return false;
    if (!parseColorIntOrPercentage(current, end, ',', expect, green))
      return false;
    if (!parseColorIntOrPercentage(current, end, ',', expect, blue))
      return false;
    if (!parseAlphaValue(current, end, ')', alpha))
      return false;
    if (current != end)
      return false;
    rgb = makeRGBA(red, green, blue, alpha);
    return true;
  }

  // Try rgb() syntax.
  if (mightBeRGB(characters, length)) {
    const CharacterType* current = characters + 4;
    const CharacterType* end = characters + length;
    int red;
    int green;
    int blue;
    if (!parseColorIntOrPercentage(current, end, ',', expect, red))
      return false;
    if (!parseColorIntOrPercentage(current, end, ',', expect, green))
      return false;
    if (!parseColorIntOrPercentage(current, end, ')', expect, blue))
      return false;
    if (current != end)
      return false;
    rgb = makeRGB(red, green, blue);
    return true;
  }

  return false;
}
Пример #9
0
// all values are in the range of 0 to 1.0
RGBA32 makeRGBAFromHSLA(double h, double s, double l, double a)
{
    double temp2 = l < 0.5 ? l * (1.0 + s) : l + s - l * s;
    double temp1 = 2.0 * l - temp2;
    
    return makeRGBA(static_cast<int>(calcHue(temp1, temp2, h + 1.0 / 3.0) * 255), 
                    static_cast<int>(calcHue(temp1, temp2, h) * 255),
                    static_cast<int>(calcHue(temp1, temp2, h - 1.0 / 3.0) * 255),
                    static_cast<int>(a * 255));
}
    static RefPtrWillBeRawPtr<CSSShadowValue> createShadowValue()
    {
        RefPtrWillBeRawPtr<CSSPrimitiveValue> color = CSSPrimitiveValue::createColor(makeRGBA(112, 123, 175, 255));
        RefPtrWillBeRawPtr<CSSPrimitiveValue> x = CSSPrimitiveValue::create(10, CSSPrimitiveValue::UnitType::Pixels);
        RefPtrWillBeRawPtr<CSSPrimitiveValue> y = CSSPrimitiveValue::create(20, CSSPrimitiveValue::UnitType::Pixels);
        RefPtrWillBeRawPtr<CSSPrimitiveValue> blur = CSSPrimitiveValue::create(30, CSSPrimitiveValue::UnitType::Pixels);
        RefPtrWillBeRawPtr<CSSPrimitiveValue> spread = CSSPrimitiveValue::create(40, CSSPrimitiveValue::UnitType::Pixels);

        return CSSShadowValue::create(x, y, blur, spread, CSSPrimitiveValue::createIdentifier(CSSValueNone), color);

    }
Пример #11
0
void ScrollbarThemeOpus::paintThumb(GraphicsContext* context, ScrollbarThemeClient* scrollbar, const IntRect& rect)
{
    if (!clientOpacityMap->contains(scrollbar))
        return;
    int opacity = clientOpacityMap->get(scrollbar);
    if (!opacity)
        return;
    IntRect thumbRect = rect;
    thumbRect.inflate(-1);
    int scrollThickness = thumbRect.width() < thumbRect.height() ? thumbRect.width() : thumbRect.height();
    IntSize curveSize(scrollThickness / 2, scrollThickness / 2);
    Color fillColor(makeRGBA(128, 128, 128, opacity));
    context->fillRoundedRect(thumbRect, curveSize, curveSize, curveSize, curveSize, fillColor, ColorSpaceDeviceRGB);
}
PassRefPtrWillBeRawPtr<CSSPrimitiveValue> ColorStyleInterpolation::interpolableValueToColor(const InterpolableValue& value)
{
    ASSERT(value.isList());
    const InterpolableList* list = toInterpolableList(&value);

    double alpha = toInterpolableNumber(list->get(3))->value();
    if (!alpha)
        return CSSPrimitiveValue::createColor(Color::transparent);

    // Clamping is inside makeRGBA.
    unsigned rgba = makeRGBA(
                        round(toInterpolableNumber(list->get(0))->value() / alpha),
                        round(toInterpolableNumber(list->get(1))->value() / alpha),
                        round(toInterpolableNumber(list->get(2))->value() / alpha),
                        round(alpha));

    return CSSPrimitiveValue::createColor(rgba);
}
Пример #13
0
Color::Color(CGColorRef color)
{
    if (!color) {
        m_color = 0;
        m_valid = false;
        return;
    }

#if !PLATFORM(IOS)
    size_t numComponents = CGColorGetNumberOfComponents(color);
    const CGFloat* components = CGColorGetComponents(color);
#else
    RetainPtr<CGColorRef> correctedColor = adoptCF(createCGColorWithDeviceRGBA(color));
    if (!correctedColor)
        correctedColor = color;

    size_t numComponents = CGColorGetNumberOfComponents(correctedColor.get());
    const CGFloat* components = CGColorGetComponents(correctedColor.get());
#endif // !PLATFORM(IOS)

    float r = 0;
    float g = 0;
    float b = 0;
    float a = 0;

    switch (numComponents) {
    case 2:
        r = g = b = components[0];
        a = components[1];
        break;
    case 4:
        r = components[0];
        g = components[1];
        b = components[2];
        a = components[3];
        break;
    default:
        ASSERT_NOT_REACHED();
    }

    m_color = makeRGBA(r * 255, g * 255, b * 255, a * 255);
    m_valid = true;
}
Пример #14
0
Vector<SVGGradientStop> SVGGradientElement::buildStops() const
{
    Vector<SVGGradientStop> stops;
    RenderStyle* gradientStyle = 0;

    for (Node* n = firstChild(); n; n = n->nextSibling()) {
        SVGElement* element = n->isSVGElement() ? static_cast<SVGElement*>(n) : 0;

        if (element && element->isGradientStop()) {
            SVGStopElement* stop = static_cast<SVGStopElement*>(element);
            float stopOffset = stop->offset();

            Color color;
            float opacity;

            if (stop->renderer()) {
                RenderStyle* stopStyle = stop->renderer()->style();
                color = stopStyle->svgStyle()->stopColor();
                opacity = stopStyle->svgStyle()->stopOpacity();
            } else {
                // If there is no renderer for this stop element, then a parent element
                // set display="none" - ie. <g display="none"><linearGradient><stop>..
                // Unfortunately we have to manually rebuild the stop style. See pservers-grad-19-b.svg
                if (!gradientStyle)
                    gradientStyle = const_cast<SVGGradientElement*>(this)->styleForRenderer(parent()->renderer());

                RenderStyle* stopStyle = stop->resolveStyle(gradientStyle);

                color = stopStyle->svgStyle()->stopColor();
                opacity = stopStyle->svgStyle()->stopOpacity();

                stopStyle->deref(document()->renderArena());
            }

            stops.append(makeGradientStop(stopOffset, makeRGBA(color.red(), color.green(), color.blue(), int(opacity * 255.))));
        }
    }

    if (gradientStyle)
        gradientStyle->deref(document()->renderArena());

    return stops;
}
Пример #15
0
/* =============================================================================
 =============================================================================== */
int C3DSceneMgr::createUITexture(string strFileName, int &width, int &height, int &txWidth)
{
	Fl_Image * img = openTextureFile(strFileName);
	if (img == NULL) {
		return -1;
	}

	width = img->w();
	height = img->h();

	//  need to add an alpha channel to properly overlay on existing textures
	const unsigned char *pData = NULL;
	if (img->d() == 3)
		pData = makeRGBA((const unsigned char *) img->data()[0], width, height);
	else
		pData = (const unsigned char *) img->data()[0];

	GLuint	textureID;
	glGenTextures(1, &textureID);
	glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
	glBindTexture(GL_TEXTURE_2D, textureID);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR);

	int txHeight = height;
	txWidth = (width <= 64) ? 64 : (width <= 128) ? 128 : width;

	const unsigned char *pDataNew = NULL;
	if (width != txWidth)
	{
		pDataNew = padOut(pData, width, height, txWidth);
		txHeight = txWidth;
	}

	glTexParameteri(GL_TEXTURE_2D, GL_GENERATE_MIPMAP, GL_TRUE); 
	glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, txWidth, txHeight, 0, GL_RGBA, GL_UNSIGNED_BYTE, pDataNew ? pDataNew : pData);

	if (pDataNew) delete[] pDataNew;
	if (img->d() == 3) delete[] pData;
	delete img;

	return textureID;
}
Color CSSColorInterpolationType::resolveInterpolableColor(const InterpolableValue& interpolableColor, const StyleResolverState& state, bool isVisited, bool isTextDecoration)
{
    const InterpolableList& list = toInterpolableList(interpolableColor);
    ASSERT(list.length() == InterpolableColorIndexCount);

    double red = toInterpolableNumber(list.get(Red))->value();
    double green = toInterpolableNumber(list.get(Green))->value();
    double blue = toInterpolableNumber(list.get(Blue))->value();
    double alpha = toInterpolableNumber(list.get(Alpha))->value();

    if (double currentcolorFraction = toInterpolableNumber(list.get(Currentcolor))->value()) {
        auto currentColorGetter = isVisited ? ColorPropertyFunctions::getVisitedColor : ColorPropertyFunctions::getUnvisitedColor;
        StyleColor currentStyleColor = StyleColor::currentColor();
        if (isTextDecoration)
            currentStyleColor = currentColorGetter(CSSPropertyWebkitTextFillColor, *state.style());
        if (currentStyleColor.isCurrentColor())
            currentStyleColor = currentColorGetter(CSSPropertyColor, *state.style());
        addPremultipliedColor(red, green, blue, alpha, currentcolorFraction, currentStyleColor.getColor());
    }
    const TextLinkColors& colors = state.document().textLinkColors();
    if (double webkitActivelinkFraction = toInterpolableNumber(list.get(WebkitActivelink))->value())
        addPremultipliedColor(red, green, blue, alpha, webkitActivelinkFraction, colors.activeLinkColor());
    if (double webkitLinkFraction = toInterpolableNumber(list.get(WebkitLink))->value())
        addPremultipliedColor(red, green, blue, alpha, webkitLinkFraction, isVisited ? colors.visitedLinkColor() : colors.linkColor());
    if (double quirkInheritFraction = toInterpolableNumber(list.get(QuirkInherit))->value())
        addPremultipliedColor(red, green, blue, alpha, quirkInheritFraction, colors.textColor());

    alpha = clampTo<double>(alpha, 0, 255);
    if (alpha == 0)
        return Color::transparent;

    return makeRGBA(
        round(red / alpha),
        round(green / alpha),
        round(blue / alpha),
        round(alpha));
}
Пример #17
0
Color DragData::asColor() const
{
    return makeRGBA(0, 0, 0, 0);
}
Пример #18
0
Color::Color(const rgb_color& color)
    : m_color(makeRGBA(color.red, color.green, color.blue, color.alpha))
    , m_valid(true)
{
}
Пример #19
0
Color::Color(const ClutterColor& c)
    : m_color(makeRGBA(c.red, c.green, c.blue, c.alpha))
    , m_valid(true)
{
}
Пример #20
0
void QtWebPageEventHandler::handleInputMethodEvent(QInputMethodEvent* ev)
{
    QString commit = ev->commitString();
    QString composition = ev->preeditString();

    int replacementStart = ev->replacementStart();
    int replacementLength = ev->replacementLength();

    // NOTE: We might want to handle events of one char as special
    // and resend them as key events to make web site completion work.

    int cursorPositionWithinComposition = 0;

    Vector<CompositionUnderline> underlines;

    for (int i = 0; i < ev->attributes().size(); ++i) {
        const QInputMethodEvent::Attribute& attr = ev->attributes().at(i);
        switch (attr.type) {
        case QInputMethodEvent::TextFormat: {
            if (composition.isEmpty())
                break;

            QTextCharFormat textCharFormat = attr.value.value<QTextFormat>().toCharFormat();
            QColor qcolor = textCharFormat.underlineColor();
            Color color = makeRGBA(qcolor.red(), qcolor.green(), qcolor.blue(), qcolor.alpha());
            int start = qMin(attr.start, (attr.start + attr.length));
            int end = qMax(attr.start, (attr.start + attr.length));
            underlines.append(CompositionUnderline(start, end, color, false));
            break;
        }
        case QInputMethodEvent::Cursor:
            if (attr.length)
                cursorPositionWithinComposition = attr.start;
            break;
        // Selection is handled further down.
        default: break;
        }
    }

    if (composition.isEmpty()) {
        int selectionStart = -1;
        int selectionLength = 0;
        for (int i = 0; i < ev->attributes().size(); ++i) {
            const QInputMethodEvent::Attribute& attr = ev->attributes().at(i);
            if (attr.type == QInputMethodEvent::Selection) {
                selectionStart = attr.start;
                selectionLength = attr.length;

                ASSERT(selectionStart >= 0);
                ASSERT(selectionLength >= 0);
                break;
            }
        }

        m_webPageProxy->confirmComposition(commit, selectionStart, selectionLength);
    } else {
        ASSERT(cursorPositionWithinComposition >= 0);
        ASSERT(replacementStart >= 0);

        m_webPageProxy->setComposition(composition, underlines,
            cursorPositionWithinComposition, cursorPositionWithinComposition,
            replacementStart, replacementLength);
    }

    ev->accept();
}
void GraphicsContext::setPlatformShadow(const FloatSize& offset, float blur, const Color& color, ColorSpace)
{
    if (paintingDisabled())
        return;

    FloatSize adjustedOffset = offset;

    if (m_state.shadowsIgnoreTransforms) {
        // Meaning that this graphics context is associated with a CanvasRenderingContext
        // We flip the height since CG and HTML5 Canvas have opposite Y axis
        adjustedOffset.setHeight(-offset.height());
    }

    // if there is an invalid shadow color, we're supposed to use Apple's CG default
    platformContext()->setShadow(adjustedOffset, blur, color.isValid() ? color.rgb() : makeRGBA(0, 0, 0, 0xFF / 3), m_state.shadowsIgnoreTransforms);
}
Пример #22
0
Color::Color(const QColor& c)
    : m_color(makeRGBA(c.red(), c.green(), c.blue(), c.alpha()))
{
    m_valid = c.isValid();
}
Пример #23
0
void Font::drawGlyphs(GraphicsContext* context, const SimpleFontData* font, const GlyphBuffer& glyphBuffer, int from, int numGlyphs, const FloatPoint& point) const
{
    FS_STATE* iType = font->platformData().scaledFont(context->getCTM().yScale());
    if (!iType)
        return;

    FloatPoint adjustedPoint = point;

    if (font->platformData().orientation() == Vertical)
        adjustedPoint.move(-(font->fontMetrics().floatAscent(IdeographicBaseline) - font->fontMetrics().floatAscent()), 0);

    bool softwareBlurRequired = context->state().shadowBlur / font->fontMetrics().xHeight() > 0.5;

    FloatSize currentShadowOffset;
    float currentShadowBlur;
    Color currentShadowColor;
    ColorSpace currentColorSpace;

    // If we have a shadow blur, and it is too big to apply at text-render time, we must render it now.
    if (context->hasShadow() && softwareBlurRequired) {
        context->getShadow(currentShadowOffset, currentShadowBlur, currentShadowColor, currentColorSpace);

        const GraphicsContextState state = context->state();
        FloatSize offset = state.shadowOffset;
        if (state.shadowsIgnoreTransforms)
            offset.setHeight(-offset.height());
        ShadowBlur shadow(FloatSize(state.shadowBlur, state.shadowBlur), offset, state.shadowColor, state.shadowColorSpace);
        FloatPoint minPoint(adjustedPoint.x(), adjustedPoint.y() - fontMetrics().ascent());
        FloatPoint maxPoint(adjustedPoint.x(), adjustedPoint.y() + fontMetrics().descent());
        FloatPoint currentPoint = adjustedPoint;
        for (int i = 0; i < numGlyphs; ++i) {
            currentPoint += *glyphBuffer.advances(from + i);
            minPoint.setX(std::min(minPoint.x(), currentPoint.x()));
            minPoint.setY(std::min(minPoint.y(), currentPoint.y()));
            maxPoint = maxPoint.expandedTo(currentPoint);
        }
        const FloatRect boundingRect(minPoint.x(), minPoint.y(), maxPoint.x() - minPoint.x(), maxPoint.y() - minPoint.y());
        GraphicsContext* shadowContext = shadow.beginShadowLayer(context, boundingRect);
        if (shadowContext) {
            iType = font->platformData().scaledFont(shadowContext->getCTM().yScale());
            shadowContext->platformContext()->addGlyphs(glyphBuffer.glyphs(from),
                    reinterpret_cast<const BlackBerry::Platform::FloatSize*>(glyphBuffer.advances(from)),
                    numGlyphs, adjustedPoint, iType, 0, 0);
            iType = font->platformData().scaledFont(context->getCTM().yScale());
            shadow.endShadowLayer(context);
        }
        context->platformContext()->clearShadow();
    }

    context->platformContext()->addGlyphs(glyphBuffer.glyphs(from),
                                          reinterpret_cast<const BlackBerry::Platform::FloatSize*>(glyphBuffer.advances(from)),
                                          numGlyphs, adjustedPoint, iType,
                                          context->fillGradient() ? context->fillGradient()->platformGradient() : (context->fillPattern() ? context->fillPattern()->platformPattern(AffineTransform()) : static_cast<BlackBerry::Platform::Graphics::Paint*>(0)),
                                          context->strokeGradient() ? context->strokeGradient()->platformGradient() : (context->strokePattern() ? context->strokePattern()->platformPattern(AffineTransform()) : static_cast<BlackBerry::Platform::Graphics::Paint*>(0)));

    if (softwareBlurRequired)
        context->platformContext()->setShadow(currentShadowOffset, currentShadowBlur, currentShadowColor.isValid() ? currentShadowColor.rgb() : makeRGBA(0, 0, 0, 0xFF / 3), context->state().shadowsIgnoreTransforms);
}