当前位置:首页 > 技术 > 单片机 > 正文内容

CharacterMatrix 生成带索引的字体库文件解析

Watrt2周前 (01-23)单片机330

按照官方的说明是:字库格式为 C+O+D,C和O两个域为可选域。其中C为32 Bits[4 Bytes]的数据,表示该字库文件中包含的字模总数;O占用的字节数为C*10,即每个字符各占80 Bits,前16 Bits[2 Bytes]为该字模的编码值[MBCS或UNICODE码值,可设置],第二个16 Bits[2 Bytes]为该字模的宽度,第三个16 Bits[2 Bytes]为字模的高度,最后32 Bits[4 Bytes]表示该字模的点阵数据在字库文件中的偏移量[偏移量从D起始处开始计算,即第一个字模的偏移量值为0];D用来描述字库中各字模的点阵数据,占用的字节数与字模大小及生成字库时使用的设置相关;C和O两个域的字节顺序为BigEndian,即高字节在前;

对于图形字模以及使用MBCS编码时添加的UNICODE专有字符,将使用0x0A00~0x0E7F区间作为字模的编码值使用 [覆盖UNICODE编码的果鲁穆奇语、古吉拉特语、奥里雅语、泰米尔语、泰卢固语、卡纳达语、马拉雅拉姆语区间];

下面开始用python进行解析:

def parse_font_library(file_path):
    with open(file_path, 'rb') as f:
        # 读取 C 域,获取字模总数
        font_count = int.from_bytes(f.read(4), byteorder='big')
        print(f"字库中包含的字模总数: {font_count}")
        font_info = {}
        # 读取 O 域,获取每个字模的信息
        for _ in range(font_count):
            # 读取编码值,占 2 字节
            code = int.from_bytes(f.read(2), byteorder='big')
            # 读取宽度,占 2 字节
            width = int.from_bytes(f.read(2), byteorder='big')
            # 读取高度,占 2 字节
            height = int.from_bytes(f.read(2), byteorder='big')
            # 读取偏移量,占 4 字节
            offset = int.from_bytes(f.read(4), byteorder='big')
            font_info[code] = {
                'width': width,
                'height': height,
                'offset': offset
            }
        # 记录 D 域起始位置
        d_start = f.tell()
        # 读取 D 域,即字模点阵数据
        font_data = f.read()
    return font_info, font_data, d_start
def get_font_matrix(font_info, font_data, d_start, ascii_code):
    if ascii_code not in font_info:
        print(f"未找到编码为 {ascii_code} 对应的字模。")
        return None
    info = font_info[ascii_code]
    width = info['width']
    height = info['height']
    offset = info['offset'] + d_start
    # 计算字模数据长度
    data_length = (width * height + 7) // 8
    # 提取对应字模数据
    matrix_data = font_data[offset - d_start:offset - d_start + data_length]
    matrix = []
    for byte in matrix_data:
        binary_str = bin(byte)[2:].zfill(8)
        matrix.extend([int(bit) for bit in binary_str])
    result_matrix = [matrix[i * width:(i + 1) * width] for i in range(height)]
    return result_matrix
def print_font_matrix(matrix):
    if matrix is None:
        return
    for row in matrix:
        for bit in row:
            if bit == 1:
                print('*', end=' ')
            else:
                print(' ', end=' ')
        print()
if __name__ == "__main__":
    file_path = "your_font_file.bin"
    font_info, font_data, d_start = parse_font_library(file_path)
    while True:
        try:
            ascii_input = input("请输入字符的编码(十六进制,如 0x41;输入 'q' 退出):")
            if ascii_input.lower() == 'q':
                break
            if ascii_input.startswith('0x'):
                ascii_code = int(ascii_input, 16)
            else:
                print("输入格式有误,请输入十六进制编码,如 0x41。")
                continue
            matrix = get_font_matrix(font_info, font_data, d_start, ascii_code)
            print_font_matrix(matrix)
        except ValueError:
            print("输入无效,请输入有效的十六进制编码。")

代码解释

parse_font_library 函数

读取 C 域:从文件开头读取 4 个字节,以大端字节序转换为整数,得到字库中包含的字模总数,并打印该信息。

读取 O 域:循环 font_count 次,每次读取 10 个字节,分别获取字模的编码值、宽度、高度和偏移量,并将这些信息存储在 font_info 字典中。

记录 D 域起始位置:使用 f.tell() 记录 D 域的起始位置,方便后续计算偏移量。

读取 D 域:读取文件剩余部分,即字模的点阵数据。

get_font_matrix 函数

检查编码是否存在:检查输入的编码是否在 font_info 字典中,如果不存在则提示未找到对应字模。

计算偏移量:将存储的偏移量加上 D 域的起始位置,得到字模点阵数据在文件中的实际偏移量。

提取字模数据:根据宽度和高度计算字模数据的长度,并从 font_data 中提取对应的数据。

转换为矩阵:将提取的字节数据转换为二进制矩阵。

print_font_matrix 函数

遍历矩阵,将值为 1 的位置打印为 *,值为 0 的位置打印为空格。

主程序

加载字库:调用 parse_font_library 函数加载字库文件,并获取字模信息、点阵数据和 D 域起始位置。

循环输入:提示用户输入字符的十六进制编码,输入 q 退出。

获取并打印字模矩阵:根据用户输入的编码调用 get_font_matrix 函数获取字模矩阵,并调用 print_font_matrix 函数打印矩阵。

使用说明

将 "your_font_file.bin" 替换为实际的字库文件路径。

运行代码后,程序会显示字库中包含的字模总数。

按照提示输入字符的十六进制编码(如 0x41),程序会打印对应的字模矩阵。输入 q 可退出程序。

1.png


字体解析.zip


分享给朋友:

相关文章

T12恒温铬铁参考

T12恒温铬铁参考

电路上采用标准的T12 控制:加热部分:PWM 信号控制MOS给烙铁头加热烙铁头热电偶信号放大:一个标准的运算放大电路,放大信号约200倍电源部分:40V以下均可以输入,转成5V,供屏幕和单片机使用 其中C12预留焊盘全部的原理图,请参见: https://lceda.cn/zhqsoft/shmictrl-28-t12实际PCB以及接法图中预留了ESP12s的位置,理论上可以做成物联网烙铁,但是没有什么实际用途,只是预留。核心控制算法有人觉得控制算法很神秘,其实很简单;的意思是每次获...

ESP32S 数据手册

ESP32S 数据手册

1. 概述ESP32-S 是一款通用型WiFi-BT-BLE MCU模组,功能强大,用途广泛,可以用于低功耗传感器网络和要求极高的任务,例如语音编码、音频流和MP3解码等。此款模组的核心是ESP32芯片,具有可扩展、自适应的特点。两个CPU核可以被单独控制或上电。时钟频率的调节范围为80 MHz到240 MHz。用户可以切断CPU的电源,利用低功耗协处理器来不断地监测外设的状态变化或某些模拟量是否超出阈值。ESP32还集成了丰富的外设,包括电容式触摸传感器、霍尔传感器、低噪声传感放大器,SD卡接...

ESP32使用SD卡注意事项

ESP32使用SD卡注意事项

有两种方法可以使用:上拉电阻为47K和上拉电阻为10K。                                           上拉电阻为47K。按照ESP32-CAM开发板的接法。           ...

mcu 8051 ide 使用测试

mcu 8051 ide 使用测试

今天无意中发现在有一个叫mcu 8051 ide 的软件,试了一下。发现在功能强大,能进行很多硬件的防真。包括了,LED、数码管、矩阵、按钮、矩阵键盘、HD44780(与1602兼容),并且还支持中文,支持widnwos\linux\mac多平台,还是免费软件,这么强大的软件必须玩一下。1、首先:下载mcu8051ide: 下载地址:https://sourceforge.net/projects/mcu8051ide/files/ 2、然后下载编译器:sdcc: 下载地址:...

发表评论

访客

看不清,换一张

◎欢迎参与讨论,请在这里发表您的看法和观点。