Linux C语言解析.bmp格式图片并显示汉字
bmp.h 文件
#ifndef __BMP_H__
#define __BMP_H__ #include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
#include <fcntl.h>
#include <string.h>
#include <linux/fb.h>
#include <sys/mman.h>
#include <sys/ioctl.h>
#include <arpa/inet.h> //文件头
typedef struct
{
unsigned char bfType[]; //文件类型
unsigned long bfSize; //位图大小
unsigned short bfReserved1; //位0
unsigned short bfReserved2; //位0
unsigned long bfOffBits; //到数据偏移量
} __attribute__((packed)) BitMapFileHeader; //信息头
typedef struct
{
unsigned long biSize; // BitMapFileHeader 字节数
long biWidth; //位图宽度
long biHeight; //位图高度,正位正向,反之为倒图
unsigned short biPlanes; //为目标设备说明位面数,其值将总是被设为1
unsigned short biBitCount; //说明比特数/象素,为1、4、8、16、24、或32。
unsigned long biCompression; //图象数据压缩的类型没有压缩的类型:BI_RGB
unsigned long biSizeImage; //说明图象的大小,以字节为单位
long biXPelsPerMeter; //说明水平分辨率
long biYPelsPerMeter; //说明垂直分辨率
unsigned long biClrUsed; //说明位图实际使用的彩色表中的颜色索引数
unsigned long biClrImportant; //对图象显示有重要影响的索引数,0都重要。
} __attribute__((packed)) BitMapInfoHeader; //位图颜色分量
typedef struct
{
unsigned char Blue; //该颜色的蓝色分量
unsigned char Green; //该颜色的绿色分量
unsigned char Red; //该颜色的红色分量
unsigned char Reserved; //保留值
} __attribute__((packed)) RgbQuad; typedef struct DealInfo
{
unsigned char tmp;
unsigned char hum;
unsigned char light;
unsigned char fan;
unsigned char buzz;
}DealInfo; typedef struct QNode
{
DealInfo buf;
struct QNode *pNext;
}QNode; void plan();
int show_photo(const char *fbp, struct fb_var_screeninfo *scrinfo); //显示图片 #endif //__BMP_H__
bmp.c 文件
#include "bmp.h"
#include "word.h" extern char photo_name[];
extern QNode heard; //汉字字模
unsigned char word[WORD_DATA_HEIGTH][WORD_DATA_WIDTH] = { 0x08,0x40,0x08,0x40,0x0B,0xFC,0x10,0x40,0x10,0x40,0x30,0x40,0x3F,0xFE,0x50,0x00,
0x90,0x40,0x10,0x40,0x13,0xFC,0x10,0x40,0x10,0x40,0x10,0x40,0x1F,0xFE,0x10,0x00, 0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x02,0x80,0x02,0x80,
0x04,0x40,0x04,0x40,0x08,0x20,0x08,0x20,0x10,0x10,0x20,0x08,0x40,0x04,0x80,0x02, 0x08,0x20,0x04,0x40,0x7F,0xFC,0x01,0x00,0x01,0x00,0x3F,0xF8,0x01,0x00,0x01,0x00,
0xFF,0xFE,0x01,0x00,0x01,0x00,0x7F,0xFC,0x02,0x80,0x04,0x40,0x18,0x30,0xE0,0x0E, 0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x7C,0xFE,0x44,0x22,0x44,0x22,0x44,0x22,0x44,
0x42,0x44,0x24,0x44,0x14,0x44,0x08,0x44,0x14,0x44,0x22,0x7C,0x42,0x44,0x80,0x00, 0x00,0x00,0xFF,0xFE,0x00,0x00,0x00,0x00,0x4F,0xE4,0x49,0x24,0x49,0x24,0x4F,0xE4,
0x49,0x24,0x49,0x24,0x49,0x24,0x4F,0xE4,0x40,0x04,0x40,0x04,0x7F,0xFC,0x00,0x04, 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, 0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x21,0x08,0x21,0x08,0x21,0x08,0x21,0x08,
0x21,0x08,0x21,0x08,0x21,0x08,0x21,0x08,0x21,0x08,0x3F,0xF8,0x00,0x08,0x00,0x00, 0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x08,0x01,0x08,0x7D,0x90,0x05,0xA0,0x09,0x40,
0x09,0x40,0x11,0x20,0x11,0x10,0x21,0x08,0x41,0x06,0x81,0x00,0x05,0x00,0x02,0x00, 0x00,0x00,0xFF,0xFE,0x00,0x00,0x00,0x00,0x4F,0xE4,0x49,0x24,0x49,0x24,0x4F,0xE4,
0x49,0x24,0x49,0x24,0x49,0x24,0x4F,0xE4,0x40,0x04,0x40,0x04,0x7F,0xFC,0x00,0x04, 0x10,0x40,0x10,0x40,0x10,0x40,0x10,0x40,0x3E,0x40,0x22,0x60,0x42,0x50,0x42,0x48,
0xA4,0x44,0x14,0x44,0x08,0x40,0x08,0x40,0x10,0x40,0x20,0x40,0x40,0x40,0x80,0x40, 0x00,0x00,0x20,0x80,0x13,0x3C,0x12,0x24,0x02,0x24,0x02,0x24,0xF2,0x24,0x12,0x24,
0x12,0x24,0x12,0xB4,0x13,0x28,0x12,0x20,0x10,0x20,0x28,0x20,0x47,0xFE,0x00,0x00 }; void plan(void)
{
//映射内存地址,屏幕信息
char *fbp = NULL;
struct fb_var_screeninfo scrinfo; //设备文件的操作
int devfb = open("/dev/fb0", O_RDWR);
if(!devfb)
{
printf("devfb open error!\r\n");
exit();
} //屏幕信息
if(ioctl(devfb, FBIOGET_VSCREENINFO, &scrinfo))
{
printf("get screen infomation error!\r\n");
exit();
}
//设置参数(图片大小为1280*168)
scrinfo.xres = ;
scrinfo.yres = ; if(ioctl(devfb, FBIOPUT_VSCREENINFO, &scrinfo))
{
printf("set screen infomation error!\r\n");
exit();
} //内存映射
unsigned long screensize = scrinfo.xres_virtual * scrinfo.yres_virtual * scrinfo.bits_per_pixel / ;
fbp = (char *)mmap(NULL, screensize, PROT_READ | PROT_WRITE, MAP_SHARED, devfb, );
if(- == (int)fbp)
{
printf("mmap error!\r\n");
exit();
} //字形处理和视频显示
//update_word(&heard);
show_photo(fbp, &scrinfo); //结束
munmap(fbp, screensize);
close(devfb); return ;
} int show_photo(const char *fbp, struct fb_var_screeninfo *scrinfo)
{
if(NULL == fbp || NULL == scrinfo)
return -; int xres = scrinfo->xres_virtual;
int bits_per_pixel = scrinfo->bits_per_pixel;
BitMapFileHeader FileHead;
BitMapInfoHeader InfoHead;
RgbQuad rgb;
unsigned long location = ; //打开.bmp文件
FILE *fb = fopen(photo_name, "rb");
if (fb == NULL)
{
printf("fopen bmp error\r\n");
return -;
} //读文件头,并判断是否为.bmp文件
if ( != fread( &FileHead, sizeof(BitMapFileHeader),, fb))
{
printf("read BitMapFileHeader error!\n");
fclose(fb);
return -;
}
if (memcmp(FileHead.bfType, "BM", ) != )
{
printf("it's not a BMP file\n");
fclose(fb);
return -;
} //获取.bmp文件信息
if ( != fread( (char *)&InfoHead, sizeof(BitMapInfoHeader),, fb))
{
printf("read BitMapInfoHeader error!\n");
fclose(fb);
return -;
} //移动至数据段,准备读数据
fseek(fb, FileHead.bfOffBits, SEEK_SET); //图片行,列,像素信息
int line_x = , line_y = ;
unsigned long tmp = ; int len = InfoHead.biBitCount / ; //原图像素点所占字节数,24/8=3
int bits_len = bits_per_pixel / ; //屏幕像素点所占字节数,32/8=4 //右上角文字显示区相关信息
int word_line_y = WORD_DATA_HEIGTH - ; //三行文字最底端的行
int word_line_x; //三行文字最左端的列
int k; //字模移动位数
unsigned char data = , one = ; while(!feof(fb))
{
tmp = ;
rgb.Reserved = 0xFF; //对应的内存相对映射首地址的偏移量
location = line_x * bits_len + (InfoHead.biHeight - - line_y ) * xres * bits_len; tmp = rgb.Reserved << | rgb.Red << | rgb.Green << | rgb.Blue; //文字显示区
if(line_x > WORD_WIDTH && line_x < InfoHead.biWidth - &&
line_y > WORD_HEIGTH && line_y < InfoHead.biHeight - && word_line_y >= )
{
tmp = ; for(word_line_x = ; word_line_x < WORD_DATA_WIDTH; word_line_x++)
{ //读字模
data = word[word_line_y][word_line_x]; one = 0x80; for(k = ; k < BIT_WIDTH; k++)
{ fread((char *)&rgb, , len, fb); //确定有效位
if(data & one)
tmp = ; //黑色字体 else
tmp = rgb.Reserved << | rgb.Red << | rgb.Green << | rgb.Blue; location = line_x * bits_len + (InfoHead.biHeight - - line_y ) * xres * bits_len;
*((unsigned long *)(fbp + location)) = tmp; one >>= ; //自增列
line_x++;
if (line_x == InfoHead.biWidth )
{
line_x = ; //自增行
line_y++;
if(line_y == InfoHead.biHeight)
break;
}
}
} //字模从下往上读和显示
word_line_y--;
continue; } //读.bmp文件
if (len != fread((char *)&rgb, , len, fb))
break; //显示非文字区的图片
*((unsigned long *)(fbp + location)) = tmp; //自增列
line_x++;
if (line_x == InfoHead.biWidth )
{
line_x = ; //自增行
line_y++;
if(line_y == InfoHead.biHeight)
break;
}
} fclose(fb); return ;
}
main函数
int main()
{ plan(); return ;
}
效果图(我不是给这游戏打广告)
说明:1.图片是24位或32位bmp图
2.屏幕是32位屏幕
3.不同的设备,可能设备文件不同
4.需要在root用户下执行
Linux C语言解析.bmp格式图片并显示汉字的更多相关文章
- C语言解析Ini格式文件
引用别人的博文: http://www.open-open.com/lib/view/open1402278076447.html 可以解析 INI 格式的字符串.解析文件.保存到文件. 下面是头文件 ...
- Bmp格式图片与16进制的互相转换简解 Python
BMP TO HEX 首先介绍Github上一个简单的Bmp转成16进制的py: https://github.com/robertgallup/bmp2hex 网上这种例子很多.思路也简单:将bmp ...
- Linux C语言解析并显示.bmp格式图片
/************************* *bmp.h文件 *************************/ #ifndef __BMP_H__ #define __BMP_H__ # ...
- bmp格式图片文件读取
C++读取bmp图片 #include <windows.h> #include <stdio.h> #include <stdlib.h> #include &l ...
- 微信小程序 base64格式图片的显示及保存
当我们拿到如下base64格式的图片(如下图)时, base64格式的图片数据: 如何显示 ? 使用image标签,src属性添加data:image/png;base64, (注意:若imgData ...
- 006--VS2013 C++ 加载其他格式图片,并显示半透明化
//--------------------------------------------MyPaint() 函数------------------------------------------ ...
- PNG,JPEG,BMP,JIF图片格式详解及其对比
原文地址:http://blog.csdn.net/u012611878/article/details/52215985 图片格式详解 不知道大家有没有注意过网页里,手机里,平板里的图片,事实上,图 ...
- [自制操作系统] BMP格式文件读取&图形界面系统框架/应用接口设计
本文将介绍在本人JOS中实现的简单图形界面应用程序接口,应用程序启动器,以及一些利用了图形界面的示例应用程序. 本文主要涉及以下部分: 内核/用户RW/RW调色板framebuffer共享区域 8bi ...
- 图片bmp格式转换为jpg格式
一下代码经过个人测试,可用 注意:将jpg格式的图片重命名为bmp格式,在该代码中是不能转换的,会报空值异常!而且IE10是显示不了这样的图片的 import java.awt.Image; impo ...
随机推荐
- SSH框架整合(代码加文字解释)
一.创建数据库并设置编码. A) create database oa default character set utf8. 二.MyEclipse工程 A) 在Myeclipse里创建web工程, ...
- WCF学习之旅—实现REST服务(二十二)
一.什么是REST 表述性状态转移(Representational State Transfer,REST),不是一种标准,而是一种软件架构风格. 基于REST的服务与基于SOAP的服务相比,性能. ...
- java终端获取输入
上一篇博客已经介绍了System.in这个输入流这次谈谈java如何获取终端(控制台)的输入 (1)BufferedReader JDK 1.4 及以下的版本中要想从控制台中输入数据只有一种办法,即使 ...
- 05. Web大前端时代之:HTML5+CSS3入门系列~H5 多媒体系
Web大前端时代之:HTML5+CSS3入门系列:http://www.cnblogs.com/dunitian/p/5121725.html 1.引入 概述 音频文件或视频文件都可以看做是一个容器文 ...
- JS中的数学计算<之简单实例讲解>
1.取余数 % var a=10%3; //a=1 2.取绝对值 Math.abs() var a=Math.abs(-102.1); var b=Math.abs(102.1); //a=10 ...
- 设计模式(九): 从醋溜土豆丝和清炒苦瓜中来学习"模板方法模式"(Template Method Pattern)
今天是五.四青年节,祝大家节日快乐.看着今天这标题就有食欲,夏天到了,醋溜土豆丝和清炒苦瓜适合夏天吃,好吃不上火.这两道菜大部分人都应该吃过,特别是醋溜土豆丝,作为“鲁菜”的代表作之一更是为大众所熟知 ...
- JVM学习(2)——技术文章里常说的堆,栈,堆栈到底是什么,从os的角度总结
俗话说,自己写的代码,6个月后也是别人的代码……复习!复习!复习!涉及到的知识点总结如下: 堆栈是栈 JVM栈和本地方法栈划分 Java中的堆,栈和c/c++中的堆,栈 数据结构层面的堆,栈 os层面 ...
- java笔记--理解java类加载器以及ClassLoader类
类加载器概述: java类的加载是由虚拟机来完成的,虚拟机把描述类的Class文件加载到内存,并对数据进行校验,解析和初始化,最终形成能被java虚拟机直接使用的java类型,这就是虚拟机的类加载机制 ...
- 图标字体 VS 雪碧图——图标字体应用实践
本文介绍使用图标字体和SVG取代雪碧图的方法.雪碧图是很多网站经常用到的一种技术,但是它有缺点:高清屏会模糊.无法动态变化如hover时候反色.而使用图标字体可以完美解决上述问题,同时具备兼容性好,生 ...
- 【QuickHit项目实例】
关于java面向对象QuickHit项目实例 Game类:用来得到随机出现的字符串(随机打印的字符串,然后玩家进行输入字符串) public class Game { private String s ...