zoukankan      html  css  js  c++  java
  • 图片叠加文字

    项目上有个小需求,在处理过和图片上叠加文字.本以为很简单.结果找字模都找了半天,找到了中英文又不通用.

    后来,又被图片的上下次序,字节正序倒序,按行,还是按列等搞的晕头转向......

    还好从网上下了个批量生成字模的软件"PCtoLCD2002.exe"

    自己写程序生成个GB2312编码表.

    主要是生成源码表.代码很简单,效率格式一律不考虑:

    1 int get_hzk_index(const char* str)
    2 {
    3 char ch;
    4 int n;
    5
    6 ch = *str;
    7
    8 if (ch < 0)
    9 {
    10 n = ch - 0xA1;
    11
    12 if (n > 14 && n < 87)
    13 {
    14 return ((n - 4) * 94 + str[1] - 0xA1) * 72;
    15 }
    16 else if (n < 9)
    17 {
    18 return (n * 94 + str[1] - 0xA1) * 72;
    19 }
    20 else
    21 {
    22 return -1;
    23 }
    24 }
    25
    26 return (9 * 94 + ch) * 72;;
    27 }
    28
    29
    30  int generate_src()
    31 {
    32 FILE *fp;
    33 int i, j;
    34 unsigned char buff[2];
    35
    36 fp = fopen("src.txt", "wb");
    37
    38 for (i = 0; i < 9; i ++)
    39 {
    40 for (j = 0; j < 94; j ++)
    41 {
    42 buff[0] = i + 0xA1;
    43 buff[1] = j + 0xA1;
    44 fwrite(buff, 2, 1, fp);
    45 }
    46 }
    47
    48
    49 for (i = 0; i < 128; i ++)
    50 {
    51 if (isprint(i))
    52 {
    53 buff[0] = i;
    54 }
    55 else
    56 {
    57 buff[0] = ' ';
    58 }
    59 buff[1] = ' ';
    60 fwrite(buff, 2, 1, fp);
    61 }
    62
    63 for (i = 0; i < 60; i ++)
    64 {
    65 buff[0] = ' ';
    66 buff[1] = ' ';
    67 fwrite(buff, 2, 1, fp);
    68 }
    69
    70 for (i = 15; i < 87; i ++)
    71 {
    72 for (j = 0; j < 94; j ++)
    73 {
    74 buff[0] = i + 0xA1;
    75 buff[1] = j + 0xA1;
    76 fwrite(buff, 2, 1, fp);
    77 }
    78 }
    79
    80 fclose(fp);
    81
    82 return 0;
    83 }

    09 10区本来是空的..我把英文的前128个写了进去..为了方便处理每个英文字符后面跟一个空格.

    这样的话就和汉字对齐了.

    后面的汉字区,按空间往前移.详细的看get_hzk_index函数.

    然后通过上述软件把src.txt变为字模文件 (阴码,按列,逆向)  按列主要是处理英文..要不很麻烦.

    生成des.txt....然后用EDITPLUS,调格式.去{}等....最后生成一个数组

    写入文件 hzk24.h

    再用FREEIMAGE把JPG解码,,自己写函数叠加

    1 extern unsigned char g_hzk24[561744];
    2
    3
    4  /**
    5 * @brief 载入任何可能的图像文件
    6 * @param fname {const char *} [in] 所要载入文件名
    7 * @return {FIBITMAP *} 成功返回句柄 不成功NULL
    8 */
    9 FIBITMAP* ImageLoad(const char* fname)
    10 {
    11 FREE_IMAGE_FORMAT fif;
    12 FIBITMAP *dib;
    13
    14 /* 文件名称非法,直接返回 */
    15 if (fname == NULL || strlen(fname) < 2)
    16 {
    17 fprintf(stderr, "非法文件名\n");
    18 return NULL;
    19 }
    20
    21 /* 从文件结构判断类型 */
    22 if ((fif = FreeImage_GetFileType(fname, 0)) == FIF_UNKNOWN)
    23 {
    24 fprintf(stderr, "无法从结构本身判断文件类型\n");
    25
    26 /* 如果从结构判断不成功,改为从扩展名判断 */
    27 if ((fif = FreeImage_GetFIFFromFilename(fname)) == FIF_UNKNOWN)
    28 {
    29 fprintf(stderr, "无法从扩展名判断类型\n");
    30 /* 依然不成功 */
    31 return NULL;
    32 }
    33 }
    34
    35 if (!FreeImage_FIFSupportsReading(fif))
    36 {
    37 /* 不支持该类型 */
    38 fprintf(stderr, "不支持该类型\n");
    39 return NULL;
    40 }
    41
    42 /* 载入文件 */
    43 if ((dib = FreeImage_Load(fif, fname, 0)) == NULL)
    44 {
    45 fprintf(stderr, "无法载入文件\n");
    46 return NULL;
    47 }
    48
    49 return dib;
    50 }
    51
    52  /**
    53 * @brief 释放图像
    54 * @param dib {FIBITMAP *} [in] 输入句柄
    55 * @return {void} 无返回值
    56 */
    57  void ImageUnload(FIBITMAP *dib)
    58 {
    59 if (dib != NULL)
    60 {
    61 /* 释放内存 */
    62 FreeImage_Unload(dib);
    63 }
    64 }
    65
    66
    67  /**
    68 * @brief 获得字符在字模表中的地址
    69 * @param str {const char *} [in] 输入字符
    70 * @return {int} 成功返回地址 不成功-1
    71 */
    72  int get_hzk_index(const char* str)
    73 {
    74 char ch;
    75 int n;
    76
    77 /* 字符非法 */
    78 if (str == NULL || str[0] == 0)
    79 {
    80 return -1;
    81 }
    82
    83 ch = *str;
    84
    85 /* 中文 */
    86 if (ch < 0)
    87 {
    88 n = (unsigned char)ch - 0xA1;
    89
    90 /* 汉字 */
    91 if (n > 14 && n < 87)
    92 {
    93 return ((n - 4) * 94 + (unsigned char)str[1] - 0xA1) * 72;
    94 }
    95 /* 中文符号 */
    96 else if (n < 9)
    97 {
    98 return (n * 94 + (unsigned char)str[1] - 0xA1) * 72;
    99 }
    100 else
    101 {
    102 return -1;
    103 }
    104 }
    105
    106 /* 英文 */
    107 return (9 * 94 + ch) * 72;;
    108 }
    109
    110  /**
    111 * @brief 在图片文件上叠加文字
    112 * @param src {const char *} [in] 输入文件
    113 * @param des {const char *} [in] 输出文件
    114 * @param sx {int} [in] 起始X像素(以1开始,下同)
    115 * @param sy {int} [in] 起始Y像素
    116 * @param str {const char *} [in] 所要叠加的字符串
    117 * @return {int} 成功 0 否则 -1
    118 */
    119  int img_draw_text(const char *src, const char *des, int sx, int sy, const char *str)
    120 {
    121 int loc;
    122 FIBITMAP *dib;
    123 int width, height, pitch, bpp;
    124 int i, j, k, m, n, x, y;
    125 int len;
    126 unsigned char *img, *ptr1, *ptr2;
    127 unsigned char pix[4];
    128
    129
    130 /* 参数非法 */
    131 if (src == NULL || strlen(src) < 2 || \
    132 des == NULL || strlen(des) < 2 || \
    133 str == NULL || strlen(str) < 2 || \
    134 sx < 1)
    135 {
    136 return -1;
    137 }
    138
    139 /* 无法载入图片 */
    140 if ((dib = ImageLoad(src)) == NULL)
    141 {
    142 return -1;
    143 }
    144
    145 width = FreeImage_GetWidth(dib);
    146 height = FreeImage_GetHeight(dib);
    147 pitch = FreeImage_GetPitch(dib);
    148 bpp = FreeImage_GetBPP(dib) >> 3;
    149
    150 /* 计算起始X,Y(像素位置) */
    151 x = (sx - 1);
    152
    153 if (sy < 0)
    154 {
    155 y = -1 - sy;
    156 }
    157 else
    158 {
    159 y = height - sy;
    160 }
    161
    162 if (x >= width || y < 23 || y > height - 1)
    163 {
    164 ImageUnload(dib);
    165 return -1;
    166 }
    167
    168 /* 得出一点 */
    169 memset(pix, 255, sizeof(pix));
    170
    171 /* 求出内存中图像矩阵位置 */
    172 img = (unsigned char *)FreeImage_GetBits(dib);
    173
    174 /* 遍历字符串 */
    175 len = strlen(str);
    176
    177 for (i = 0; i < len; i ++)
    178 {
    179 /* 求出字模位置 */
    180 loc = get_hzk_index(str + i);
    181 ptr1 = g_hzk24 + loc;
    182
    183 /* 中文 */
    184 if (str[i] < 0)
    185 {
    186 if (x + 24 > width)
    187 {
    188 ptr2 = img + y * pitch + x * bpp;
    189
    190 for (n = 0; n < 24; n ++)
    191 {
    192 memset(ptr2 - n * pitch, 0, (width - x) * bpp);
    193 }
    194
    195 x = 0;
    196 y -= 24;
    197 }
    198
    199 if (y < 23)
    200 {
    201 break;
    202 }
    203
    204 // 在XY处画
    205   ptr2 = img + y * pitch + x * bpp;
    206
    207 for (m = 0; m < 24; m ++)
    208 {
    209 for (j = 0; j < 3; j ++)
    210 {
    211 for(k = 0; k < 8; k ++)
    212 {
    213 if (ptr1[m * 3 + j] & (0x01 << k))
    214 {
    215 memcpy(ptr2 + (-j * 8 - k) * pitch + m * bpp, pix, bpp);
    216 }
    217 else
    218 {
    219 memset(ptr2 + (-j * 8 - k) * pitch + m * bpp, 0, bpp);
    220 }
    221 }
    222 }
    223 }
    224
    225 x += 24;
    226
    227 i ++;
    228 }
    229 /* 英文 */
    230 else
    231 {
    232 if (x + 12 > width)
    233 {
    234 ptr2 = img + y * pitch + x * bpp;
    235
    236 for (n = 0; n < 24; n ++)
    237 {
    238 memset(ptr2 - n * pitch, 0, (width - x) * bpp);
    239 }
    240
    241 x = 0;
    242 y -= 24;
    243 }
    244
    245 if (y < 23)
    246 {
    247 break;
    248 }
    249
    250 ptr2 = img + y * pitch + x * bpp;
    251
    252 for (m = 0; m < 12; m ++)
    253 {
    254 for (j = 0; j < 3; j ++)
    255 {
    256 for(k = 0; k < 8; k ++)
    257 {
    258 if (ptr1[m * 3 + j] & (0x01 << k))
    259 {
    260 memcpy(ptr2 + (-j * 8 - k) * pitch + m * bpp, pix, bpp);
    261 }
    262 else
    263 {
    264 memset(ptr2 + (-j * 8 - k) * pitch + m * bpp, 0, bpp);
    265 }
    266 }
    267 }
    268 }
    269
    270 x += 12;
    271 }
    272 }
    273
    274 if (x < width && y >= 23)
    275 {
    276 ptr2 = img + y * pitch + x * bpp;
    277 width -= x;
    278 width *= bpp;
    279
    280 for (i = 0; i < 24; i ++)
    281 {
    282 memset(ptr2 - i * pitch, 0, width);
    283 }
    284 }
    285
    286 FreeImage_Save(FIF_JPEG, dib, des, 0);
    287 FreeImage_Unload(dib);
    288 return 0;
    289 }

    至此大功告成..呵呵...

  • 相关阅读:
    January 25th, 2018 Week 04th Thursday
    January 24th, 2018 Week 04th Wednesday
    January 23rd, 2018 Week 04th Tuesday
    January 22nd, 2018 Week 04th Monday
    January 21st, 2018 Week 3rd Sunday
    January 20th, 2018 Week 3rd Saturday
    January 19th, 2018 Week 3rd Friday
    January 18th, 2018 Week 03rd Thursday
    January 17th, 2018 Week 03rd Wednesday
    January 16th, 2018 Week 03rd Tuesday
  • 原文地址:https://www.cnblogs.com/javado/p/1892007.html
Copyright © 2011-2022 走看看