示例#1
0
HRESULT opentype_get_font_table(IDWriteFontFileStream *stream, DWRITE_FONT_FACE_TYPE type, UINT32 font_index, UINT32 tag,
    const void **table_data, void **table_context, UINT32 *table_size, BOOL *found)
{
    HRESULT hr;
    TTC_SFNT_V1 *font_header = NULL;
    void *sfnt_context;
    TT_TableRecord *table_record = NULL;
    void *table_record_context;
    int table_count, table_offset = 0;
    int i;

    if (found) *found = FALSE;
    if (table_size) *table_size = 0;

    if (type == DWRITE_FONT_FACE_TYPE_TRUETYPE_COLLECTION) {
        const TTC_Header_V1 *ttc_header;
        void * ttc_context;
        hr = IDWriteFontFileStream_ReadFileFragment(stream, (const void**)&ttc_header, 0, sizeof(*ttc_header), &ttc_context);
        if (SUCCEEDED(hr)) {
            table_offset = GET_BE_DWORD(ttc_header->OffsetTable[0]);
            if (font_index >= GET_BE_DWORD(ttc_header->numFonts))
                hr = E_INVALIDARG;
            else
                hr = IDWriteFontFileStream_ReadFileFragment(stream, (const void**)&font_header, table_offset, sizeof(*font_header), &sfnt_context);
            IDWriteFontFileStream_ReleaseFileFragment(stream, ttc_context);
        }
    }
    else
        hr = IDWriteFontFileStream_ReadFileFragment(stream, (const void**)&font_header, 0, sizeof(*font_header), &sfnt_context);

    if (FAILED(hr))
        return hr;

    table_count = GET_BE_WORD(font_header->numTables);
    table_offset += sizeof(*font_header);
    for (i = 0; i < table_count; i++)
    {
        hr = IDWriteFontFileStream_ReadFileFragment(stream, (const void**)&table_record, table_offset, sizeof(*table_record), &table_record_context);
        if (FAILED(hr))
            break;
        if (DWRITE_MAKE_OPENTYPE_TAG(table_record->tag[0], table_record->tag[1], table_record->tag[2], table_record->tag[3]) == tag)
            break;
        IDWriteFontFileStream_ReleaseFileFragment(stream, table_record_context);
        table_offset += sizeof(*table_record);
    }

    IDWriteFontFileStream_ReleaseFileFragment(stream, sfnt_context);
    if (SUCCEEDED(hr) && i < table_count)
    {
        int offset = GET_BE_DWORD(table_record->offset);
        int length = GET_BE_DWORD(table_record->length);
        IDWriteFontFileStream_ReleaseFileFragment(stream, table_record_context);

        if (found) *found = TRUE;
        if (table_size) *table_size = length;
        hr = IDWriteFontFileStream_ReadFileFragment(stream, table_data, offset, length, table_context);
    }

    return hr;
}
示例#2
0
文件: opentype.c 项目: Dietr1ch/wine
HRESULT analyze_opentype_font(const void* font_data, UINT32* font_count, DWRITE_FONT_FILE_TYPE *file_type, DWRITE_FONT_FACE_TYPE *face_type, BOOL *supported)
{
    /* TODO: Do font validation */
    const char* tag = font_data;

    *supported = FALSE;
    *file_type = DWRITE_FONT_FILE_TYPE_UNKNOWN;
    if (face_type)
        *face_type = DWRITE_FONT_FACE_TYPE_UNKNOWN;
    *font_count = 0;

    if (DWRITE_MAKE_OPENTYPE_TAG(tag[0], tag[1], tag[2], tag[3]) == MS_TTCF_TAG)
    {
        const TTC_Header_V1 *header = font_data;
        *font_count = GET_BE_DWORD(header->numFonts);
        *file_type = DWRITE_FONT_FILE_TYPE_TRUETYPE_COLLECTION;
        if (face_type)
            *face_type = DWRITE_FONT_FACE_TYPE_TRUETYPE_COLLECTION;
        *supported = TRUE;
    }
    else if (GET_BE_DWORD(*(DWORD*)font_data) == 0x10000)
    {
        *font_count = 1;
        *file_type = DWRITE_FONT_FILE_TYPE_TRUETYPE;
        if (face_type)
            *face_type = DWRITE_FONT_FACE_TYPE_TRUETYPE;
        *supported = TRUE;
    }
    else if (DWRITE_MAKE_OPENTYPE_TAG(tag[0], tag[1], tag[2], tag[3]) == MS_OTTO_TAG)
    {
        *file_type = DWRITE_FONT_FILE_TYPE_CFF;
    }
    return S_OK;
}
示例#3
0
static int compare_group(const void *a, const void* b)
{
    const DWORD *chr = a;
    const CMAP_SegmentedCoverage_group *group = b;

    if (*chr < GET_BE_DWORD(group->startCharCode))
        return -1;
    if (*chr > GET_BE_DWORD(group->endCharCode))
        return 1;
    return 0;
}
示例#4
0
HRESULT opentype_cmap_get_unicode_ranges(void *data, UINT32 max_count, DWRITE_UNICODE_RANGE *ranges, UINT32 *count)
{
    CMAP_Header *CMAP_Table = data;
    int i, k = 0;

    if (!CMAP_Table)
        return E_FAIL;

    *count = opentype_cmap_get_unicode_ranges_count(CMAP_Table);

    for (i = 0; i < GET_BE_WORD(CMAP_Table->numTables) && k < max_count; i++)
    {
        WORD type;
        WORD *table;
        int j;

        if (GET_BE_WORD(CMAP_Table->tables[i].platformID) != 3)
            continue;

        table = (WORD*)(((BYTE*)CMAP_Table) + GET_BE_DWORD(CMAP_Table->tables[i].offset));
        type = GET_BE_WORD(*table);
        TRACE("table type %i\n", type);

        switch (type)
        {
            case OPENTYPE_CMAP_TABLE_SEGMENT_MAPPING:
            {
                CMAP_SegmentMapping_0 *format = (CMAP_SegmentMapping_0*)table;
                UINT16 segment_count = GET_BE_WORD(format->segCountX2)/2;
                UINT16 *startCode = (WORD*)((BYTE*)format + sizeof(CMAP_SegmentMapping_0) + (sizeof(WORD) * segment_count));

                for (j = 0; j < segment_count && GET_BE_WORD(format->endCode[j]) < 0xffff && k < max_count; j++, k++) {
                    ranges[k].first = GET_BE_WORD(startCode[j]);
                    ranges[k].last  = GET_BE_WORD(format->endCode[j]);
                }
                break;
            }
            case OPENTYPE_CMAP_TABLE_SEGMENTED_COVERAGE:
            {
                CMAP_SegmentedCoverage *format = (CMAP_SegmentedCoverage*)table;
                for (j = 0; j < GET_BE_DWORD(format->nGroups) && k < max_count; j++, k++) {
                    ranges[k].first = GET_BE_DWORD(format->groups[j].startCharCode);
                    ranges[k].last  = GET_BE_DWORD(format->groups[j].endCharCode);
                }
                break;
            }
            default:
                FIXME("table type %i unhandled.\n", type);
        }
    }

    return *count > max_count ? E_NOT_SUFFICIENT_BUFFER : S_OK;
}
示例#5
0
static void CMAP12_GetGlyphIndex(CMAP_SegmentedCoverage* format, UINT32 utf32c, UINT16 *pgi)
{
    CMAP_SegmentedCoverage_group *group;

    group = bsearch(&utf32c, format->groups, GET_BE_DWORD(format->nGroups),
                    sizeof(CMAP_SegmentedCoverage_group), compare_group);

    if (group)
    {
        DWORD offset = utf32c - GET_BE_DWORD(group->startCharCode);
        *pgi = GET_BE_DWORD(group->startGlyphID) + offset;
    }
}
示例#6
0
void opentype_cmap_get_glyphindex(void *data, UINT32 utf32c, UINT16 *pgi)
{
    CMAP_Header *CMAP_Table = data;
    int i;

    *pgi = 0;

    for (i = 0; i < GET_BE_WORD(CMAP_Table->numTables); i++)
    {
        WORD type;
        WORD *table;

        if (GET_BE_WORD(CMAP_Table->tables[i].platformID) != 3)
            continue;

        table = (WORD*)(((BYTE*)CMAP_Table) + GET_BE_DWORD(CMAP_Table->tables[i].offset));
        type = GET_BE_WORD(*table);
        TRACE("table type %i\n", type);

        switch (type)
        {
            case OPENTYPE_CMAP_TABLE_SEGMENT_MAPPING:
                CMAP4_GetGlyphIndex((CMAP_SegmentMapping_0*) table, utf32c, pgi);
                break;
            case OPENTYPE_CMAP_TABLE_SEGMENTED_COVERAGE:
                CMAP12_GetGlyphIndex((CMAP_SegmentedCoverage*) table, utf32c, pgi);
                break;
            default:
                TRACE("table type %i unhandled.\n", type);
        }

        if (*pgi) return;
    }
}
示例#7
0
void KeyEventHandler::process( util::Buffer *msg ) {
	if (!_onKeyEvent.empty()) {
		util::BYTE *payload = MSG_PAYLOAD(msg->buffer());
		util::DWORD value   = GET_BE_DWORD( payload );
		util::BYTE isUp     = GET_BYTE(payload+4);
		_onKeyEvent( static_cast<util::key::type>( value ), (isUp == 1) );
	}
}
示例#8
0
HRESULT opentype_analyze_font(IDWriteFontFileStream *stream, UINT32* font_count, DWRITE_FONT_FILE_TYPE *file_type, DWRITE_FONT_FACE_TYPE *face_type, BOOL *supported)
{
    /* TODO: Do font validation */
    DWRITE_FONT_FACE_TYPE face;
    const void *font_data;
    const char* tag;
    void *context;
    HRESULT hr;

    hr = IDWriteFontFileStream_ReadFileFragment(stream, &font_data, 0, sizeof(TTC_Header_V1), &context);
    if (FAILED(hr))
        return hr;

    tag = font_data;
    *file_type = DWRITE_FONT_FILE_TYPE_UNKNOWN;
    face = DWRITE_FONT_FACE_TYPE_UNKNOWN;
    *font_count = 0;

    if (DWRITE_MAKE_OPENTYPE_TAG(tag[0], tag[1], tag[2], tag[3]) == MS_TTCF_TAG)
    {
        const TTC_Header_V1 *header = font_data;
        *font_count = GET_BE_DWORD(header->numFonts);
        *file_type = DWRITE_FONT_FILE_TYPE_TRUETYPE_COLLECTION;
        face = DWRITE_FONT_FACE_TYPE_TRUETYPE_COLLECTION;
    }
    else if (GET_BE_DWORD(*(DWORD*)font_data) == 0x10000)
    {
        *font_count = 1;
        *file_type = DWRITE_FONT_FILE_TYPE_TRUETYPE;
        face = DWRITE_FONT_FACE_TYPE_TRUETYPE;
    }
    else if (DWRITE_MAKE_OPENTYPE_TAG(tag[0], tag[1], tag[2], tag[3]) == MS_OTTO_TAG)
    {
        *file_type = DWRITE_FONT_FILE_TYPE_CFF;
        face = DWRITE_FONT_FACE_TYPE_CFF;
    }

    if (face_type)
        *face_type = face;

    *supported = is_face_type_supported(face);

    IDWriteFontFileStream_ReleaseFileFragment(stream, context);
    return S_OK;
}
示例#9
0
文件: type42.c 项目: bilboed/wine
static BOOL get_glyf_pos(TYPE42 *t42, DWORD index, DWORD *start, DWORD *end)
{
    WORD loca_format = GET_BE_WORD(t42->tables[t42->head_tab].data + 50);
    TRACE("loca_format = %d\n", loca_format);
    switch(loca_format) {
    case 0:
        *start = GET_BE_WORD(((WORD*)t42->tables[t42->loca_tab].data) + index);
        *start <<= 1;
        *end = GET_BE_WORD(((WORD*)t42->tables[t42->loca_tab].data) + index + 1);
        *end <<= 1;
        break;
    case 1:
        *start = GET_BE_DWORD(((DWORD*)t42->tables[t42->loca_tab].data) + index);
        *end = GET_BE_DWORD(((DWORD*)t42->tables[t42->loca_tab].data) + index + 1);
        break;
    default:
        ERR("Unknown loca_format %d\n", loca_format);
        return FALSE;
    }
    return TRUE;
}
示例#10
0
static UINT32 opentype_cmap_get_unicode_ranges_count(const CMAP_Header *CMAP_Table)
{
    UINT32 count = 0;
    int i;

    for (i = 0; i < GET_BE_WORD(CMAP_Table->numTables); i++) {
        WORD type;
        WORD *table;

        if (GET_BE_WORD(CMAP_Table->tables[i].platformID) != 3)
            continue;

        table = (WORD*)(((BYTE*)CMAP_Table) + GET_BE_DWORD(CMAP_Table->tables[i].offset));
        type = GET_BE_WORD(*table);
        TRACE("table type %i\n", type);

        switch (type)
        {
            case OPENTYPE_CMAP_TABLE_SEGMENT_MAPPING:
            {
                CMAP_SegmentMapping_0 *format = (CMAP_SegmentMapping_0*)table;
                count += GET_BE_WORD(format->segCountX2)/2;
                break;
            }
            case OPENTYPE_CMAP_TABLE_SEGMENTED_COVERAGE:
            {
                CMAP_SegmentedCoverage *format = (CMAP_SegmentedCoverage*)table;
                count += GET_BE_DWORD(format->nGroups);
                break;
            }
            default:
                FIXME("table type %i unhandled.\n", type);
        }
    }

    return count;
}
示例#11
0
文件: opentype.c 项目: Dietr1ch/wine
VOID OpenType_CMAP_GetGlyphIndex(LPVOID data, DWORD utf32c, LPWORD pgi, DWORD flags)
{
    int i;
    CMAP_Header *CMAP_Table = NULL;

    if (flags & GGI_MARK_NONEXISTING_GLYPHS)
        *pgi = 0xffff;
    else
        *pgi = 0;

    CMAP_Table = data;

    for (i = 0; i < GET_BE_WORD(CMAP_Table->numTables); i++)
    {
        WORD type;
        WORD *table;

        if (GET_BE_WORD(CMAP_Table->tables[i].platformID) != 3)
            continue;

        table = (WORD*)(((BYTE*)CMAP_Table) + GET_BE_DWORD(CMAP_Table->tables[i].offset));
        type = GET_BE_WORD(*table);
        TRACE("Type %i\n", type);
        /* Break when we find a handled type */
        switch(type)
        {
            case 4:
                CMAP4_GetGlyphIndex((CMAP_SegmentMapping_0*) table, utf32c, pgi);
                break;
            case 12:
                CMAP12_GetGlyphIndex((CMAP_SegmentedCoverage*) table, utf32c, pgi);
                break;
            default:
                TRACE("Type %i unhandled.\n", type);
        }
    }
}