Subversion Repositories pentevo

Rev

Rev 716 | Blame | Last modification | View Log | Download | RSS feed

  1. #include "std.h"
  2.  
  3. #include "emul.h"
  4. #include "vars.h"
  5. #include "debug.h"
  6. #include "dbgpaint.h"
  7. #include "dx.h"
  8. #include "draw.h"
  9. #include "dxrframe.h"
  10. #include "font16.h"
  11. #include "util.h"
  12.  
  13. unsigned char txtscr[80*30*2];
  14.  
  15. static struct
  16. {
  17.    unsigned char x,y,dx,dy,c;
  18. } frames[20];
  19.  
  20. unsigned nfr;
  21.  
  22. void debugflip()
  23. {
  24.    if(!active)
  25.        return;
  26.    setpal(0);
  27.  
  28.    unsigned char * const bptr = gdibuf;
  29.  
  30.    if (show_scrshot) {
  31.       memcpy(save_buf, rbuf, rb2_offs);
  32.       paint_scr((show_scrshot == 1)? 0 : 2);
  33.       unsigned char *dst = bptr + wat_y*16*640+wat_x*8;
  34.       unsigned char *src = rbuf+temp.scx/4*(temp.b_top+192/2-wat_sz*16/2);
  35.       src += temp.scx/8-37/2*2;
  36.       for (unsigned y = 0; y < wat_sz*16; y++) {
  37.          for (unsigned x = 0; x < 37; x++) {
  38.             *(unsigned*)(dst+x*8+0) = t.sctab8[0][(src[x*2] >>  4) + src[2*x+1]*16];
  39.             *(unsigned*)(dst+x*8+4) = t.sctab8[0][(src[x*2] & 0xF) + src[2*x+1]*16];
  40.          }
  41.          src += temp.scx/4, dst += 640;
  42.       }
  43.       memcpy(rbuf, save_buf, rb2_offs);
  44.    }
  45.  
  46.    // print text
  47.    int x,y;
  48.    unsigned char *tptr = txtscr;
  49.    for (y = 0; y < 16*30*640; y+=16*640)
  50.    {
  51.       for (x = 0; x < 80; x++, tptr++)
  52.       {
  53.          unsigned ch = *tptr, at = tptr[80*30];
  54.          if (at == 0xFF) continue; // transparent color
  55.          const unsigned char *fnt = &font16[ch*16];
  56.          at <<= 4;
  57.          for (int yy = 0; yy < 16; yy++, fnt++)
  58.          {
  59.             *(unsigned*)(bptr+y+640*yy+x*8+0) = t.sctab8[0][(*fnt >>  4) + at];
  60.             *(unsigned*)(bptr+y+640*yy+x*8+4) = t.sctab8[0][(*fnt & 0xF) + at];
  61.          }
  62.       }
  63.    }
  64.  
  65.    // show frames
  66.    for (unsigned i = 0; i < nfr; i++)
  67.    {
  68.       unsigned char a1 = (frames[i].c | 0x08) * 0x11;
  69.       y = frames[i].y*16-1;
  70.       for (x = 8*frames[i].x-1; x < (frames[i].x+frames[i].dx)*8; x++) bptr[y*640+x] = a1;
  71.       y = (frames[i].y+frames[i].dy)*16;
  72.       for (x = 8*frames[i].x-1; x < (frames[i].x+frames[i].dx)*8; x++) bptr[y*640+x] = a1;
  73.       x = frames[i].x*8-1;
  74.       for (y = 16*frames[i].y; y < (frames[i].y+frames[i].dy)*16; y++) bptr[y*640+x] = a1;
  75.       x = (frames[i].x+frames[i].dx)*8;
  76.       for (y = 16*frames[i].y; y < (frames[i].y+frames[i].dy)*16; y++) bptr[y*640+x] = a1;
  77.    }
  78.  
  79.    gdibmp.header.bmiHeader.biBitCount = 8;
  80.    if(needclr)
  81.        gdi_frame();
  82.    SetDIBitsToDevice(temp.gdidc, temp.gx, temp.gy, 640, 480, 0, 0, 0, 480, bptr, &gdibmp.header, DIB_RGB_COLORS);
  83.    gdibmp.header.bmiHeader.biBitCount = temp.obpp;
  84. }
  85.  
  86. void frame(unsigned x, unsigned y, unsigned dx, unsigned dy, unsigned char attr)
  87. {
  88.    frames[nfr].x = x;
  89.    frames[nfr].y = y;
  90.    frames[nfr].dx = dx;
  91.    frames[nfr].dy = dy;
  92.    frames[nfr].c = attr;
  93.    nfr++;
  94. }
  95.  
  96. void tprint(unsigned x, unsigned y, const char *str, unsigned char attr)
  97. {
  98.    for (unsigned ptr = y*80 + x; *str; str++, ptr++) {
  99.       txtscr[ptr] = *str; txtscr[ptr+80*30] = attr;
  100.    }
  101. }
  102.  
  103. void tprint_fg(unsigned x, unsigned y, const char *str, unsigned char attr)
  104. {
  105.    for (unsigned ptr = y*80 + x; *str; str++, ptr++) {
  106.       txtscr[ptr] = *str; txtscr[ptr+80*30] = (txtscr[ptr+80*30] & 0xF0) + attr;
  107.    }
  108. }
  109.  
  110. void filledframe(unsigned x, unsigned y, unsigned dx, unsigned dy, unsigned char color)
  111. {
  112.    for (unsigned yy = y; yy < (y+dy); yy++)
  113.       for (unsigned xx = x; xx < (x+dx); xx++)
  114.          txtscr[yy*80+xx] = ' ',
  115.          txtscr[yy*80+xx+30*80] = color;
  116.    nfr = 0; // delete other frames while dialog
  117.    frame(x,y,dx,dy,FFRAME_FRAME);
  118. }
  119.  
  120. void fillattr(unsigned x, unsigned y, unsigned dx, unsigned char color)
  121. {
  122.    for (unsigned xx = x; xx < (x+dx); xx++)
  123.       txtscr[y*80+xx+30*80] = color;
  124. }
  125.  
  126. char str[0x80];
  127. unsigned inputhex(unsigned x, unsigned y, unsigned sz, bool hex)
  128. {
  129.    unsigned cr = 0;
  130.    mousepos = 0;
  131.  
  132.    for (;;)
  133.    {
  134.       str[sz] = 0;
  135.  
  136.       unsigned i;
  137.       for (i = strlen(str); i < sz; i++)
  138.           str[i] = ' ';
  139.       for (i = 0; i < sz; i++)
  140.       {
  141.          unsigned vl = (unsigned char)str[i];
  142.          tprint(x+i,y,(char*)&vl,(i==cr) ? W_INPUTCUR : W_INPUTBG);
  143.       }
  144.  
  145.       debugflip();
  146.  
  147.       unsigned key;
  148.       for (;;Sleep(20))
  149.       {
  150.          key = process_msgs();
  151.          needclr = 0;
  152.          debugflip();
  153.  
  154.          if (mousepos)
  155.              return 0;
  156.          if (key)
  157.              break;
  158.       }
  159.  
  160.       switch(key)
  161.       {
  162.       case VK_ESCAPE: return 0;
  163.       case VK_RETURN:
  164.          for (char *ptr = str+sz-1; *ptr == ' ' && ptr >= str; *ptr-- = 0);
  165.          return 1;
  166.       case VK_LEFT:
  167.           if (cr)
  168.               cr--;
  169.           continue;
  170.       case VK_BACK:
  171.           if (cr)
  172.           {
  173.               for (i = cr; i < sz; i++)
  174.                   str[i-1]=str[i];
  175.               str[sz-1] = ' ';
  176.               --cr;
  177.           }
  178.           continue;
  179.       case VK_RIGHT:
  180.           if(cr != sz-1)
  181.               cr++;
  182.           continue;
  183.       case VK_HOME:
  184.           cr=0;
  185.           continue;
  186.       case VK_END:
  187.           for (cr=sz-1; cr && str[cr]==' ' && str[cr-1] == ' '; cr--);
  188.           continue;
  189.       case VK_DELETE:
  190.           for (i = cr; i < sz-1; i++)
  191.               str[i]=str[i+1];
  192.           str[sz-1] = ' ';
  193.           continue;
  194.       case VK_INSERT:
  195.           for (i = sz-1; i > cr; i--)
  196.               str[i]=str[i-1];
  197.           str[cr] = ' ';
  198.           continue;
  199.       }
  200.  
  201.       u8 Kbd[256];
  202.       GetKeyboardState(Kbd);
  203.       unsigned short k = 0;
  204.       if (ToAscii(key, 0, Kbd, &k, 0) == 1)
  205.       {
  206.           char m;
  207.           if(CharToOemBuff((char *)&k, &m, 1))
  208.           {
  209.               int u = toupper(m);
  210.               if (hex && ((u >= '0' && u <= '9') || (u >= 'A' && u <= 'F')) || !hex)
  211.               {
  212.                   str[cr++] = hex ? u : m;
  213.               }
  214.           }
  215.       }
  216.       if (cr == sz)
  217.           cr--;
  218.    }
  219. }
  220.  
  221. unsigned input4(unsigned x, unsigned y, unsigned val)
  222. {
  223.    sprintf(str, "%04X", val);
  224.    if (inputhex(x,y,4,true))
  225.    {
  226.        sscanf(str, "%x", &val);
  227.        return val;
  228.    }
  229.    return -1;
  230. }
  231.  
  232. unsigned input2(unsigned x, unsigned y, unsigned val)
  233. {
  234.    sprintf(str, "%02X", val);
  235.    if (inputhex(x,y,2,true))
  236.    {
  237.        sscanf(str, "%x", &val);
  238.        return val;
  239.    }
  240.    return -1;
  241. }
  242.  
  243.  
  244. void format_item(char *dst, unsigned width, const char *text, MENUITEM::FLAGS flags)
  245. {
  246.    memset(dst, ' ', width+2); dst[width+2] = 0;
  247.    unsigned sz = strlen(text), left = 0;
  248.    if (sz > width) sz = width;
  249.    if (flags & MENUITEM::RIGHT) left = width - sz;
  250.    else if (flags & MENUITEM::CENTER) left = (width - sz)/2;
  251.    memcpy(dst+left+1, text, sz);
  252. }
  253.  
  254. void paint_items(MENUDEF *menu)
  255. {
  256.    char ln[80]; unsigned item;
  257.  
  258.    unsigned maxlen = strlen(menu->title);
  259.    for (item = 0; item < menu->n_items; item++) {
  260.       unsigned sz = strlen(menu->items[item].text);
  261.       maxlen = max(maxlen, sz);
  262.    }
  263.    unsigned menu_dx = maxlen+2, menu_dy = menu->n_items + 3;
  264.    unsigned menu_x = (80 - menu_dx)/2, menu_y = (30 - menu_dy)/2;
  265.    filledframe(menu_x, menu_y, menu_dx, menu_dy, MENU_INSIDE);
  266.    format_item(ln, maxlen, menu->title, MENUITEM::CENTER);
  267.    tprint(menu_x, menu_y, ln, MENU_HEADER);
  268.  
  269.    for (/*unsigned*/ item = 0; item < menu->n_items; item++) {
  270.       unsigned char color = MENU_ITEM;
  271.       if (menu->items[item].flags & MENUITEM::DISABLED) color = MENU_ITEM_DIS;
  272.       else if (item == menu->pos) color = MENU_CURSOR;
  273.       format_item(ln, maxlen, menu->items[item].text, menu->items[item].flags);
  274.       tprint(menu_x, menu_y+item+2, ln, color);
  275.    }
  276. }
  277.  
  278. void menu_move(MENUDEF *menu, int dir)
  279. {
  280.    unsigned start = menu->pos;
  281.    for (;;) {
  282.       menu->pos += dir;
  283.       if ((int)menu->pos == -1) menu->pos = menu->n_items-1;
  284.       if (menu->pos >= menu->n_items) menu->pos = 0;
  285.       if (!(menu->items[menu->pos].flags & MENUITEM::DISABLED)) return;
  286.       if (menu->pos == start) return;
  287.    }
  288. }
  289.  
  290. char handle_menu(MENUDEF *menu)
  291. {
  292.    if (menu->items[menu->pos].flags & MENUITEM::DISABLED)
  293.       menu_move(menu, 1);
  294.    for (;;)
  295.    {
  296.       paint_items(menu);
  297.       debugflip();
  298.  
  299.       unsigned key;
  300.       for (;;Sleep(20))
  301.       {
  302.          key = process_msgs();
  303.          needclr =  0;
  304.          debugflip();
  305.  
  306.          if (mousepos)
  307.              return 0;
  308.          if(key)
  309.              break;
  310.       }
  311.       if (key == VK_ESCAPE)
  312.           return 0;
  313.       if (key == VK_RETURN || key == VK_SPACE)
  314.           return 1;
  315.       if (key == VK_UP || key == VK_LEFT)
  316.           menu_move(menu, -1);
  317.       if (key == VK_DOWN || key == VK_RIGHT)
  318.           menu_move(menu, 1);
  319.       if (key == VK_HOME || key == VK_PRIOR)
  320.       {
  321.           menu->pos = -1;
  322.           menu_move(menu, 1);
  323.       }
  324.       if (key == VK_END || key == VK_NEXT)
  325.       {
  326.           menu->pos = menu->n_items;
  327.           menu_move(menu, -1);
  328.       }
  329.    }
  330. }
  331.