绘制鼠标

1.简介

有了桌面背景,能够显示字符串,现在在图形界面上还少了点东西,那就是鼠标指针,如果有个鼠标能在桌面里动来动去,那系统就有点意思了。

2.实现

通过一个二维数组:

static char cursor[16][16] = {
        "**************..",
        "*OOOOOOOOOOO*...",
        "*OOOOOOOOOO*....",
        "*OOOOOOOOO*.....",
        "*OOOOOOOO*......",
        "*OOOOOOO*.......",
        "*OOOOOOO*.......",
        "*OOOOOOOO*......",
        "*OOOO**OOO*.....",
        "*OOO*..*OOO*....",
        "*OO*....*OOO*...",
        "*O*......*OOO*..",
        "**........*OOO*.",
        "*..........*OOO*",
        "............*OO*",
        ".............***"
    };

*对应的像素点画成黑色

0代表的像素点画成白色

.代表的像素点设置成背景色

那么一个鼠标的图像就出来了

那么对应的代码就成了:

void init_mouse_cursor(char* mouse, char bc) {
    static char cursor[16][16] = {
        "**************..",
        "*OOOOOOOOOOO*...",
        "*OOOOOOOOOO*....",
        "*OOOOOOOOO*.....",
        "*OOOOOOOO*......",
        "*OOOOOOO*.......",
        "*OOOOOOO*.......",
        "*OOOOOOOO*......",
        "*OOOO**OOO*.....",
        "*OOO*..*OOO*....",
        "*OO*....*OOO*...",
        "*O*......*OOO*..",
        "**........*OOO*.",
        "*..........*OOO*",
        "............*OO*",
        ".............***"
    };

      int x, y;
      for (y = 0; y < 16; y++) {
          for (x = 0; x < 16; x++) {
             if (cursor[y][x] == '*') {
                 mouse[y*16 + x] = COL8_000000;
             }
             if (cursor[y][x] == 'O') {
                mouse[y*16 + x] = COL8_FFFFFF;
             }
             if (cursor[y][x] == '.') {
                 mouse[y*16 + x] = bc;
             }
          }
      }
}

代码中把

*设置成黑色

O设置成白色

. 设置成背景色

有了上面的颜色二维数组后,我们需要把该数组的数值写入显存,但显存是一维数组,所以需要将上面的16*16的二维数组转换为一个256字节的数组然后写入显存

代码如下:

void putblock(char* vram, int vxsize, int pxsize,
int pysize, int px0, int py0, char* buf, int bxsize) {
    int x, y;
    for (y = 0; y < pysize; y++)
      for (x = 0; x < pxsize; x++) {
          vram[(py0+y) * vxsize + (px0+x)] = buf[y * bxsize + x];
      }
}

vxsize是整个屏幕的宽度 也就是320

pxsize,pysize, bxsize 等于16,也就是二维数值的行和列值

px0,py0是鼠标所在的左上角坐标

在主函数中通过以下调用就能画出鼠标:

void CMain() {
  ....
  init_mouse_cursor(mcursor, COL8_008484);
  putblock(vram, xsize, 16, 16, 80, 80, mcursor, 16);
  for(;;){
  io_hlt();
}

3.编译走起来

编译C文件

i386-elf-gcc -m32 -fno-asynchronous-unwind-tables -s -c -o write_vga_cursor.o write_vga_cursor.c

反汇编o文件

./objconv -fnasm write_vga_cursor.o write_vga_cursor.asm

删除无用部分

修改kernel

%include "write_vga_cursor.asm"

修改boot(直接放大一点)直接读了20个扇区 肯定够用了

mov          AL,  20        ; AL 表示要练习读取几个扇区

编译boot

nasm -o boot.bat boot.asm

编译kernel

nasm -o kernel.bat kernel.asm

运行java 生成system.img

MacOS环境-手写操作系统-10-绘制系统鼠标_c语言