⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 qfontengine_qpf.cpp

📁 奇趣公司比较新的qt/emd版本
💻 CPP
📖 第 1 页 / 共 3 页
字号:
    if (!fontData || fontData == (const uchar *)MAP_FAILED) {#if defined(DEBUG_FONTENGINE)        perror("mmap failed");#endif        fontData = 0;        return;    }    if (!verifyHeader(fontData, st.st_size)) {#if defined(DEBUG_FONTENGINE)        qDebug() << "verifyHeader failed!";#endif        return;    }    const Header *header = reinterpret_cast<const Header *>(fontData);    readOnly = (header->lock == 0xffffffff);    const uchar *data = fontData + sizeof(Header) + qFromBigEndian<quint16>(header->dataSize);    const uchar *endPtr = fontData + dataSize;    while (data <= endPtr - 8) {        quint16 blockTag = readValue<quint16>(data);        data += 2; // skip padding        quint32 blockSize = readValue<quint32>(data);        if (blockTag == CMapBlock) {            cmapOffset = data - fontData;            cmapSize = blockSize;        } else if (blockTag == GMapBlock) {            glyphMapOffset = data - fontData;            glyphMapEntries = blockSize / 4;        } else if (blockTag == GlyphBlock) {            glyphDataOffset = data - fontData;            glyphDataSize = blockSize;        }        data += blockSize;    }    face_id.filename = QFile::encodeName(extractHeaderField(fontData, Tag_FileName).toString());    face_id.index = extractHeaderField(fontData, Tag_FileIndex).toInt();#if !defined(QT_NO_FREETYPE)    freetype = QFreetypeFace::getFace(face_id);    if (!freetype) {        QString newPath =#ifndef QT_NO_SETTINGS            QLibraryInfo::location(QLibraryInfo::LibrariesPath) +#endif                          QLatin1String("/fonts/") +                          QFileInfo(QFile::decodeName(face_id.filename)).fileName();        face_id.filename = QFile::encodeName(newPath);        freetype = QFreetypeFace::getFace(face_id);    }    if (freetype) {        const quint32 qpfTtfRevision = extractHeaderField(fontData, Tag_FontRevision).toUInt();        const QByteArray head = freetype->getSfntTable(MAKE_TAG('h', 'e', 'a', 'd'));        if (head.size() < 8            || qFromBigEndian<quint32>(reinterpret_cast<const uchar *>(head.constData()) + 4) != qpfTtfRevision) {            freetype->release(face_id);            freetype = 0;        }    }    if (!cmapOffset && freetype) {        freetypeCMapTable = freetype->getSfntTable(MAKE_TAG('c', 'm', 'a', 'p'));        externalCMap = reinterpret_cast<const uchar *>(freetypeCMapTable.constData());        cmapSize = freetypeCMapTable.size();    }#endif    // get the real cmap    if (cmapOffset) {        int tableSize = cmapSize;        const uchar *cmapPtr = getCMap(fontData + cmapOffset, tableSize, &symbol, &cmapSize);        if (cmapPtr)            cmapOffset = cmapPtr - fontData;        else            cmapOffset = 0;    } else if (externalCMap) {        int tableSize = cmapSize;        externalCMap = getCMap(externalCMap, tableSize, &symbol, &cmapSize);    }    // verify all the positions in the glyphMap    if (glyphMapOffset) {        const quint32 *gmapPtr = reinterpret_cast<const quint32 *>(fontData + glyphMapOffset);        for (uint i = 0; i < glyphMapEntries; ++i) {            quint32 glyphDataPos = qFromBigEndian<quint32>(gmapPtr[i]);            if (glyphDataPos == 0xffffffff)                continue;            if (glyphDataPos >= glyphDataSize) {                // error                glyphMapOffset = 0;                glyphMapEntries = 0;                break;            }        }    }#if defined(DEBUG_FONTENGINE)    if (!isValid())        qDebug() << "fontData" <<  fontData << "dataSize" << dataSize                 << "externalCMap" << externalCMap << "cmapOffset" << cmapOffset                 << "glyphMapOffset" << glyphMapOffset << "glyphDataOffset" << glyphDataOffset                 << "fd" << fd << "glyphDataSize" << glyphDataSize;#endif#if defined(Q_WS_QWS)    if (isValid() && renderingFontEngine)        qt_fbdpy->sendFontCommand(QWSFontCommand::StartedUsingFont, QFile::encodeName(fileName));#endif}QFontEngineQPF::~QFontEngineQPF(){#if defined(Q_WS_QWS)    if (isValid() && renderingFontEngine)        qt_fbdpy->sendFontCommand(QWSFontCommand::StoppedUsingFont, QFile::encodeName(fileName));#endif    delete renderingFontEngine;    if (fontData)        munmap((void *)fontData, dataSize);    if (fd != -1)        ::close(fd);#if !defined(QT_NO_FREETYPE)    delete _openType;    _openType = 0;    if (freetype)        freetype->release(face_id);#endif}QByteArray QFontEngineQPF::getSfntTable(uint tag) const{#if !defined(QT_NO_FREETYPE)    if (freetype)        return freetype->getSfntTable(tag);#else    Q_UNUSED(tag);#endif    return QByteArray();}bool QFontEngineQPF::stringToCMap(const QChar *str, int len, QGlyphLayout *glyphs, int *nglyphs, QTextEngine::ShaperFlags flags) const{    if (!externalCMap && !cmapOffset && renderingFontEngine) {        if (!renderingFontEngine->stringToCMap(str, len, glyphs, nglyphs, flags))            return false;#ifndef QT_NO_FREETYPE        const_cast<QFontEngineQPF *>(this)->ensureGlyphsLoaded(glyphs, *nglyphs);#endif        return true;    }    if (*nglyphs < len) {        *nglyphs = len;        return false;    }#if defined(DEBUG_FONTENGINE)    QSet<QChar> seenGlyphs;#endif    const uchar *cmap = externalCMap ? externalCMap : (fontData + cmapOffset);    int glyph_pos = 0;    if (symbol) {        for (int i = 0; i < len; ++i) {            unsigned int uc = getChar(str, i, len);            glyphs[glyph_pos].glyph = getTrueTypeGlyphIndex(cmap, uc);            if(!glyphs[glyph_pos].glyph && uc < 0x100)                glyphs[glyph_pos].glyph = getTrueTypeGlyphIndex(cmap, uc + 0xf000);            ++glyph_pos;        }    } else {        for (int i = 0; i < len; ++i) {            unsigned int uc = getChar(str, i, len);            glyphs[glyph_pos].glyph = getTrueTypeGlyphIndex(cmap, uc);#if 0 && defined(DEBUG_FONTENGINE)            QChar c(uc);            if (!findGlyph(glyphs[glyph_pos].glyph) && !seenGlyphs.contains(c))                qDebug() << "glyph for character" << c << "/" << hex << uc << "is" << dec << glyphs[glyph_pos].glyph;            seenGlyphs.insert(c);#endif            ++glyph_pos;        }    }    *nglyphs = glyph_pos;    recalcAdvances(*nglyphs, glyphs, flags);    return true;}void QFontEngineQPF::recalcAdvances(int len, QGlyphLayout *glyphs, QTextEngine::ShaperFlags) const{#ifndef QT_NO_FREETYPE    const_cast<QFontEngineQPF *>(this)->ensureGlyphsLoaded(glyphs, len);#endif    for (int i = 0; i < len; ++i) {        const Glyph *g = findGlyph(glyphs[i].glyph);        if (!g) {            glyphs[i].glyph = 0;            continue;        }        glyphs[i].advance.x = g->advance;        glyphs[i].advance.y = 0;    }}void QFontEngineQPF::draw(QPaintEngine *p, qreal _x, qreal _y, const QTextItemInt &si){    QPaintEngineState *pState = p->state;    QRasterPaintEngine *paintEngine = static_cast<QRasterPaintEngine*>(p);    QTransform matrix = pState->transform();    matrix.translate(_x, _y);    QFixed x = QFixed::fromReal(matrix.dx());    QFixed y = QFixed::fromReal(matrix.dy());    QVarLengthArray<QFixedPoint> positions;    QVarLengthArray<glyph_t> glyphs;    getGlyphPositions(si.glyphs, si.num_glyphs, matrix, si.flags, glyphs, positions);    if (glyphs.size() == 0)        return;    for(int i = 0; i < glyphs.size(); i++) {        const Glyph *glyph = findGlyph(glyphs[i]);        if (!glyph)            continue;        const bool mono = false; // ###        paintEngine->alphaPenBlt(reinterpret_cast<const uchar *>(glyph) + sizeof(Glyph), glyph->bytesPerLine, mono,                                     qRound(positions[i].x) + glyph->x,                                     qRound(positions[i].y) + glyph->y,                                     glyph->width, glyph->height);    }}void QFontEngineQPF::addOutlineToPath(qreal x, qreal y, const QGlyphLayout *glyphs, int numGlyphs, QPainterPath *path, QTextItem::RenderFlags flags){    if (renderingFontEngine &&        (renderingFontEngine->type() != QFontEngine::Proxy         || static_cast<QProxyFontEngine *>(renderingFontEngine)->capabilities() & QAbstractFontEngine::CanOutlineGlyphs)) {        renderingFontEngine->addOutlineToPath(x, y, glyphs, numGlyphs, path, flags);        return;    }    addBitmapFontToPath(x, y, glyphs, numGlyphs, path, flags);}glyph_metrics_t QFontEngineQPF::boundingBox(const QGlyphLayout *glyphs, int numGlyphs){#ifndef QT_NO_FREETYPE    const_cast<QFontEngineQPF *>(this)->ensureGlyphsLoaded(glyphs, numGlyphs);#endif    glyph_metrics_t overall;    // initialize with line height, we get the same behaviour on all platforms    overall.y = -ascent();    overall.height = ascent() + descent() + 1;    QFixed ymax = 0;    QFixed xmax = 0;    for (int i = 0; i < numGlyphs; i++) {        const Glyph *g = findGlyph(glyphs[i].glyph);        if (!g)            continue;        QFixed x = overall.xoff + glyphs[i].offset.x + g->x;        QFixed y = overall.yoff + glyphs[i].offset.y + g->y;        overall.x = qMin(overall.x, x);        overall.y = qMin(overall.y, y);        xmax = qMax(xmax, x + g->width);        ymax = qMax(ymax, y + g->height);        overall.xoff += g->advance;    }    overall.height = qMax(overall.height, ymax - overall.y);    overall.width = xmax - overall.x;    return overall;}glyph_metrics_t QFontEngineQPF::boundingBox(glyph_t glyph){#ifndef QT_NO_FREETYPE    {        QGlyphLayout tmp;        tmp.glyph = glyph;        const_cast<QFontEngineQPF *>(this)->ensureGlyphsLoaded(&tmp, 1);    }#endif    glyph_metrics_t overall;    const Glyph *g = findGlyph(glyph);    if (!g)        return overall;    overall.x = g->x;    overall.y = g->y;    overall.width = g->width;    overall.height = g->height;    overall.xoff = g->advance;    return overall;}QFixed QFontEngineQPF::ascent() const{    return QFixed::fromReal(extractHeaderField(fontData, Tag_Ascent).value<qreal>());}QFixed QFontEngineQPF::descent() const{    return QFixed::fromReal(extractHeaderField(fontData, Tag_Descent).value<qreal>());}QFixed QFontEngineQPF::leading() const{    return QFixed::fromReal(extractHeaderField(fontData, Tag_Leading).value<qreal>());}qreal QFontEngineQPF::maxCharWidth() const{    return extractHeaderField(fontData, Tag_MaxCharWidth).value<qreal>();}qreal QFontEngineQPF::minLeftBearing() const{    return extractHeaderField(fontData, Tag_MinLeftBearing).value<qreal>();}qreal QFontEngineQPF::minRightBearing() const{    return extractHeaderField(fontData, Tag_MinRightBearing).value<qreal>();}QFixed QFontEngineQPF::underlinePosition() const{    return QFixed::fromReal(extractHeaderField(fontData, Tag_UnderlinePosition).value<qreal>());}QFixed QFontEngineQPF::lineThickness() const{    return QFixed::fromReal(extractHeaderField(fontData, Tag_LineThickness).value<qreal>());}QFontEngine::Type QFontEngineQPF::type() const{    return QFontEngine::QPF2;}bool QFontEngineQPF::canRender(const QChar *string, int len){    const uchar *cmap = externalCMap ? externalCMap : (fontData + cmapOffset);    if (symbol) {        for (int i = 0; i < len; ++i) {            unsigned int uc = getChar(string, i, len);            glyph_t g = getTrueTypeGlyphIndex(cmap, uc);            if(!g && uc < 0x100)                g = getTrueTypeGlyphIndex(cmap, uc + 0xf000);            if (!g)                return false;        }    } else {        for (int i = 0; i < len; ++i) {            unsigned int uc = getChar(string, i, len);            if (!getTrueTypeGlyphIndex(cmap, uc))                return false;        }    }    return true;}bool QFontEngineQPF::isValid() const{    return fontData && dataSize && (cmapOffset || externalCMap || renderingFontEngine)           && glyphMapOffset && glyphDataOffset && (fd >= 0 || glyphDataSize > 0);}#if !defined(QT_NO_FREETYPE)FT_Face QFontEngineQPF::lockFace() const{

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -