Diff
Modified: trunk/Source/WebCore/ChangeLog (126906 => 126907)
--- trunk/Source/WebCore/ChangeLog 2012-08-28 18:42:07 UTC (rev 126906)
+++ trunk/Source/WebCore/ChangeLog 2012-08-28 18:52:17 UTC (rev 126907)
@@ -1,3 +1,40 @@
+2012-08-28 Koji Ishii <[email protected]>
+
+ OPENTYPE_VERTICAL support for Chromium Win
+ https://bugs.webkit.org/show_bug.cgi?id=94822
+
+ Reviewed by Tony Chang.
+
+ To fix bug 51450 - Glyphs in vertical text tests are rotated 90 degrees clockwise on Chromium Windows,
+ this patch adds support of OPENTYPE_VERTICAL feature for Chromium Windows.
+ Since enabling OPENTYPE_VERTICAL feature would require rather a big number of tests to rebaseline,
+ the actual fix is separated into this patch, and the feature will be enabled in bug 51450,
+ so that it is easier to revert on any perf regressions, as suggested by Tony in comment #50 of bug 51450.
+
+ All changes in this patch are behind #if ENABLE(OPENTYPE_VERTICAL) and therefore no tests are included in this patch.
+ All tests in fast/writing-modes currently skipped will be enabled in bug 51450.
+
+ * WebCore.gyp/WebCore.gyp: Added platform/graphics/opentype/OpenType*.
+ * WebCore.gypi: Ditto.
+ * platform/graphics/FontCache.h: SKia uses uint32_t as FontFileKey.
+ * platform/graphics/GlyphPageTreeNode.cpp:
+ (WebCore::fill): Replace vertical alternate glyphs if vertical flow.
+ * platform/graphics/SimpleFontData.cpp: Added m_verticalData.
+ (WebCore::SimpleFontData::SimpleFontData):
+ * platform/graphics/SimpleFontData.h:
+ (WebCore::SimpleFontData::verticalData):
+ (SimpleFontData):
+ (WebCore::SimpleFontData::widthForGlyph):
+ * platform/graphics/chromium/FontChromiumWin.cpp:
+ (WebCore::Font::drawGlyphs): Draw glyphs verticaly if font->verticalData().
+ * platform/graphics/chromium/FontPlatformDataChromiumWin.cpp:
+ (WebCore::FontPlatformData::verticalData): Added.
+ (WebCore):
+ (WebCore::FontPlatformData::openTypeTable): Added.
+ * platform/graphics/chromium/FontPlatformDataChromiumWin.h:
+ (WebCore):
+ (FontPlatformData): Added verticalData() and openTypeTable().
+
2012-08-28 Andy Estes <[email protected]>
Add header guards to WebTileCacheLayer.h.
Modified: trunk/Source/WebCore/WebCore.gyp/WebCore.gyp (126906 => 126907)
--- trunk/Source/WebCore/WebCore.gyp/WebCore.gyp 2012-08-28 18:42:07 UTC (rev 126906)
+++ trunk/Source/WebCore/WebCore.gyp/WebCore.gyp 2012-08-28 18:52:17 UTC (rev 126907)
@@ -1844,6 +1844,10 @@
'sources/': [
['exclude', 'Posix\\.cpp$'],
+ ['include', 'platform/graphics/opentype/OpenTypeTypes\\.h$'],
+ ['include', 'platform/graphics/opentype/OpenTypeVerticalData\\.cpp$'],
+ ['include', 'platform/graphics/opentype/OpenTypeVerticalData\\.h$'],
+
# The Chromium Win currently uses GlyphPageTreeNodeChromiumWin.cpp from
# platform/graphics/chromium, included by regex above, instead.
['exclude', 'platform/graphics/skia/FontCacheSkia\\.cpp$'],
Modified: trunk/Source/WebCore/WebCore.gypi (126906 => 126907)
--- trunk/Source/WebCore/WebCore.gypi 2012-08-28 18:42:07 UTC (rev 126906)
+++ trunk/Source/WebCore/WebCore.gypi 2012-08-28 18:52:17 UTC (rev 126907)
@@ -3873,8 +3873,11 @@
'platform/graphics/opengl/GraphicsContext3DOpenGLCommon.cpp',
'platform/graphics/opentype/OpenTypeSanitizer.cpp',
'platform/graphics/opentype/OpenTypeSanitizer.h',
+ 'platform/graphics/opentype/OpenTypeTypes.h',
'platform/graphics/opentype/OpenTypeUtilities.cpp',
'platform/graphics/opentype/OpenTypeUtilities.h',
+ 'platform/graphics/opentype/OpenTypeVerticalData.cpp',
+ 'platform/graphics/opentype/OpenTypeVerticalData.h',
'platform/graphics/openvg/EGLDisplayOpenVG.cpp',
'platform/graphics/openvg/EGLDisplayOpenVG.h',
'platform/graphics/openvg/EGLUtils.h',
Modified: trunk/Source/WebCore/platform/graphics/FontCache.h (126906 => 126907)
--- trunk/Source/WebCore/platform/graphics/FontCache.h 2012-08-28 18:42:07 UTC (rev 126906)
+++ trunk/Source/WebCore/platform/graphics/FontCache.h 2012-08-28 18:52:17 UTC (rev 126907)
@@ -106,7 +106,11 @@
#endif
#if ENABLE(OPENTYPE_VERTICAL)
+#if USE(SKIA)
+ typedef uint32_t FontFileKey;
+#else
typedef AtomicString FontFileKey;
+#endif
OpenTypeVerticalData* getVerticalData(const FontFileKey&, const FontPlatformData&);
#endif
Modified: trunk/Source/WebCore/platform/graphics/GlyphPageTreeNode.cpp (126906 => 126907)
--- trunk/Source/WebCore/platform/graphics/GlyphPageTreeNode.cpp 2012-08-28 18:42:07 UTC (rev 126906)
+++ trunk/Source/WebCore/platform/graphics/GlyphPageTreeNode.cpp 2012-08-28 18:52:17 UTC (rev 126907)
@@ -29,6 +29,7 @@
#include "config.h"
#include "GlyphPageTreeNode.h"
+#include "OpenTypeVerticalData.h"
#include "PlatformString.h"
#include "SegmentedFontData.h"
#include "SimpleFontData.h"
@@ -130,7 +131,12 @@
if (SimpleFontData::AdditionalFontData* additionalFontData = fontData->fontData())
return additionalFontData->fillSVGGlyphPage(pageToFill, offset, length, buffer, bufferLength, fontData);
#endif
- return pageToFill->fill(offset, length, buffer, bufferLength, fontData);
+ bool hasGlyphs = pageToFill->fill(offset, length, buffer, bufferLength, fontData);
+#if ENABLE(OPENTYPE_VERTICAL)
+ if (hasGlyphs && fontData->verticalData())
+ fontData->verticalData()->substituteWithVerticalGlyphs(fontData, pageToFill, offset, length);
+#endif
+ return hasGlyphs;
}
void GlyphPageTreeNode::initializePage(const FontData* fontData, unsigned pageNumber)
Modified: trunk/Source/WebCore/platform/graphics/SimpleFontData.cpp (126906 => 126907)
--- trunk/Source/WebCore/platform/graphics/SimpleFontData.cpp 2012-08-28 18:42:07 UTC (rev 126906)
+++ trunk/Source/WebCore/platform/graphics/SimpleFontData.cpp 2012-08-28 18:52:17 UTC (rev 126907)
@@ -32,6 +32,7 @@
#include "Font.h"
#include "FontCache.h"
+#include "OpenTypeVerticalData.h"
#include <wtf/MathExtras.h>
#include <wtf/UnusedParam.h>
@@ -49,11 +50,20 @@
, m_isLoading(isLoading)
, m_isTextOrientationFallback(isTextOrientationFallback)
, m_isBrokenIdeographFallback(false)
+#if ENABLE(OPENTYPE_VERTICAL)
+ , m_verticalData(0)
+#endif
, m_hasVerticalGlyphs(false)
{
platformInit();
platformGlyphInit();
platformCharWidthInit();
+#if ENABLE(OPENTYPE_VERTICAL)
+ if (platformData.orientation() == Vertical && !isTextOrientationFallback) {
+ m_verticalData = platformData.verticalData();
+ m_hasVerticalGlyphs = m_verticalData && m_verticalData->hasVerticalMetrics();
+ }
+#endif
}
SimpleFontData::SimpleFontData(PassOwnPtr<AdditionalFontData> fontData, float fontSize, bool syntheticBold, bool syntheticItalic)
@@ -64,6 +74,9 @@
, m_isLoading(false)
, m_isTextOrientationFallback(false)
, m_isBrokenIdeographFallback(false)
+#if ENABLE(OPENTYPE_VERTICAL)
+ , m_verticalData(0)
+#endif
, m_hasVerticalGlyphs(false)
{
m_fontData->initializeFontData(this, fontSize);
Modified: trunk/Source/WebCore/platform/graphics/SimpleFontData.h (126906 => 126907)
--- trunk/Source/WebCore/platform/graphics/SimpleFontData.h 2012-08-28 18:42:07 UTC (rev 126906)
+++ trunk/Source/WebCore/platform/graphics/SimpleFontData.h 2012-08-28 18:52:17 UTC (rev 126907)
@@ -88,7 +88,7 @@
const FontPlatformData& platformData() const { return m_platformData; }
#if ENABLE(OPENTYPE_VERTICAL)
- const OpenTypeVerticalData* verticalData() const { return 0; } // FIXME: implement
+ const OpenTypeVerticalData* verticalData() const { return m_verticalData; }
#endif
SimpleFontData* smallCapsFontData(const FontDescription&) const;
@@ -229,6 +229,9 @@
mutable OwnPtr<GlyphMetricsMap<FloatRect> > m_glyphToBoundsMap;
mutable GlyphMetricsMap<float> m_glyphToWidthMap;
+#if ENABLE(OPENTYPE_VERTICAL)
+ const OpenTypeVerticalData* m_verticalData;
+#endif
bool m_treatAsFixedPitch;
bool m_isCustomFont; // Whether or not we are custom font loaded via @font-face
@@ -317,6 +320,14 @@
if (m_fontData)
width = m_fontData->widthForSVGGlyph(glyph, m_platformData.size());
+#if ENABLE(OPENTYPE_VERTICAL)
+ else if (m_verticalData)
+#if USE(CG) || USE(CAIRO) || PLATFORM(WX) || USE(SKIA_ON_MAC_CHROMIUM)
+ width = m_verticalData->advanceHeight(this, glyph) + m_syntheticBoldOffset;
+#else
+ width = m_verticalData->advanceHeight(this, glyph);
+#endif
+#endif
else
width = platformWidthForGlyph(glyph);
Modified: trunk/Source/WebCore/platform/graphics/chromium/FontChromiumWin.cpp (126906 => 126907)
--- trunk/Source/WebCore/platform/graphics/chromium/FontChromiumWin.cpp 2012-08-28 18:42:07 UTC (rev 126906)
+++ trunk/Source/WebCore/platform/graphics/chromium/FontChromiumWin.cpp 2012-08-28 18:52:17 UTC (rev 126907)
@@ -390,15 +390,56 @@
// We draw the glyphs in chunks to avoid having to do a heap allocation for
// the arrays of characters and advances.
const int kMaxBufferLength = 256;
- Vector<WORD, kMaxBufferLength> glyphs;
Vector<int, kMaxBufferLength> advances;
int glyphIndex = 0; // The starting glyph of the current chunk.
+ float horizontalOffset = point.x(); // The floating point offset of the left side of the current glyph.
+#if ENABLE(OPENTYPE_VERTICAL)
+ const OpenTypeVerticalData* verticalData = font->verticalData();
+ if (verticalData) {
+ Vector<FloatPoint, kMaxBufferLength> translations;
+ Vector<GOFFSET, kMaxBufferLength> offsets;
+
+ // Skia doesn't have matrix for glyph coordinate space, so we rotate back the CTM.
+ AffineTransform savedMatrix = graphicsContext->getCTM();
+ graphicsContext->concatCTM(AffineTransform(0, -1, 1, 0, point.x(), point.y()));
+ graphicsContext->concatCTM(AffineTransform(1, 0, 0, 1, -point.x(), -point.y()));
+
+ const FontMetrics& metrics = font->fontMetrics();
+ SkScalar verticalOriginX = SkFloatToScalar(point.x() + metrics.floatAscent() - metrics.floatAscent(IdeographicBaseline));
+ while (glyphIndex < numGlyphs) {
+ // How many chars will be in this chunk?
+ int curLen = std::min(kMaxBufferLength, numGlyphs - glyphIndex);
+
+ const Glyph* glyphs = glyphBuffer.glyphs(from + glyphIndex);
+ translations.resize(curLen);
+ verticalData->getVerticalTranslationsForGlyphs(font, &glyphs[0], curLen, reinterpret_cast<float*>(&translations[0]));
+ // To position glyphs vertically, we use offsets instead of advances.
+ advances.resize(curLen);
+ advances.fill(0);
+ offsets.resize(curLen);
+ float currentWidth = 0;
+ for (int i = 0; i < curLen; ++i, ++glyphIndex) {
+ offsets[i].du = lroundf(translations[i].x());
+ offsets[i].dv = -lroundf(currentWidth - translations[i].y());
+ currentWidth += glyphBuffer.advanceAt(from + glyphIndex);
+ }
+ SkPoint origin;
+ origin.set(verticalOriginX, SkFloatToScalar(point.y() + horizontalOffset - point.x()));
+ horizontalOffset += currentWidth;
+ paintSkiaText(graphicsContext, font->platformData(), curLen, &glyphs[0], &advances[0], &offsets[0], &origin);
+ }
+
+ graphicsContext->setCTM(savedMatrix);
+ return;
+ }
+#endif
+
// In order to round all offsets to the correct pixel boundary, this code keeps track of the absolute position
// of each glyph in floating point units and rounds to integer advances at the last possible moment.
- float horizontalOffset = point.x(); // The floating point offset of the left side of the current glyph.
int lastHorizontalOffsetRounded = lroundf(horizontalOffset); // The rounded offset of the left side of the last glyph rendered.
+ Vector<WORD, kMaxBufferLength> glyphs;
while (glyphIndex < numGlyphs) {
// How many chars will be in this chunk?
int curLen = std::min(kMaxBufferLength, numGlyphs - glyphIndex);
Modified: trunk/Source/WebCore/platform/graphics/chromium/FontPlatformDataChromiumWin.cpp (126906 => 126907)
--- trunk/Source/WebCore/platform/graphics/chromium/FontPlatformDataChromiumWin.cpp 2012-08-28 18:42:07 UTC (rev 126906)
+++ trunk/Source/WebCore/platform/graphics/chromium/FontPlatformDataChromiumWin.cpp 2012-08-28 18:52:17 UTC (rev 126907)
@@ -191,6 +191,31 @@
return m_scriptFontProperties;
}
+#if ENABLE(OPENTYPE_VERTICAL)
+const OpenTypeVerticalData* FontPlatformData::verticalData() const
+{
+ SkFontID id = typeface()->uniqueID();
+ return fontCache()->getVerticalData(id, *this);
+}
+
+PassRefPtr<SharedBuffer> FontPlatformData::openTypeTable(uint32_t table) const
+{
+ HWndDC hdc(0);
+ HGDIOBJ oldFont = SelectObject(hdc, hfont());
+
+ DWORD size = GetFontData(hdc, table, 0, 0, 0);
+ RefPtr<SharedBuffer> buffer;
+ if (size != GDI_ERROR) {
+ buffer = SharedBuffer::create(size);
+ DWORD result = GetFontData(hdc, table, 0, (PVOID)buffer->data(), size);
+ ASSERT(result == size);
+ }
+
+ SelectObject(hdc, oldFont);
+ return buffer.release();
+}
+#endif
+
#ifndef NDEBUG
String FontPlatformData::description() const
{
Modified: trunk/Source/WebCore/platform/graphics/chromium/FontPlatformDataChromiumWin.h (126906 => 126907)
--- trunk/Source/WebCore/platform/graphics/chromium/FontPlatformDataChromiumWin.h 2012-08-28 18:42:07 UTC (rev 126906)
+++ trunk/Source/WebCore/platform/graphics/chromium/FontPlatformDataChromiumWin.h 2012-08-28 18:52:17 UTC (rev 126907)
@@ -35,6 +35,7 @@
#include "config.h"
#include "FontOrientation.h"
+#include "SharedBuffer.h"
#include "SkTypeface.h"
#include <wtf/Forward.h>
#include <wtf/PassRefPtr.h>
@@ -53,6 +54,9 @@
SkTypeface* CreateTypefaceFromHFont(HFONT, int* size, int* lfQuality);
class FontDescription;
+#if ENABLE(OPENTYPE_VERTICAL)
+class OpenTypeVerticalData;
+#endif
class FontPlatformData {
public:
@@ -92,6 +96,11 @@
return m_font == other.m_font && m_size == other.m_size && m_orientation == other.m_orientation;
}
+#if ENABLE(OPENTYPE_VERTICAL)
+ const OpenTypeVerticalData* verticalData() const;
+ PassRefPtr<SharedBuffer> openTypeTable(uint32_t table) const;
+#endif
+
#ifndef NDEBUG
String description() const;
#endif