|
|
| version 1.1, 2004/08/07 07:19:56 | version 1.16, 2005/02/04 06:42:12 |
|---|---|
| Line 1 | Line 1 |
| #include "compiler.h" | #include "compiler.h" |
| #include "scrnmng.h" | #include "scrnmng.h" |
| #include "sysmng.h" | |
| #include "pccore.h" | #include "pccore.h" |
| #include "iocore.h" | #include "iocore.h" |
| #include "vram.h" | #include "vram.h" |
| Line 9 | Line 10 |
| #include "makesub.h" | #include "makesub.h" |
| MAKESCRN makescrn; | MAKESCRN makescrn; |
| BYTE updatetmp[0x800+0x101]; | UINT drawtime = 0; |
| BYTE scrnallflash; | |
| BYTE blinktest = 0; | |
| extern BYTE dispmode; | static void fillupdatetmp(void) { |
| static BYTE lastdisp = 0; | UINT i; |
| BYTE dispflg = UPDATE_VRAM0; | |
| BYTE *dispp = &GRP_RAM[GRAM_BANK0]; | |
| BYTE *dispp2 = &GRP_RAM[GRAM_BANK1]; | |
| static BYTE blinktime = 1; | |
| DWORD drawtime = 0; | for (i=0; i<0x800; i++) { |
| TRAMUPDATE(i) |= UPDATE_TVRAM; | |
| } | |
| void init_draw(void) { | |
| makesub_initialize(); | |
| reflesh_palette(); | |
| lastdisp = 0; | |
| dispflg = UPDATE_VRAM0; | |
| dispp = &GRP_RAM[GRAM_BANK0]; | |
| } | } |
| static void flashupdatetmp(void) { | |
| void fillupdatetmp(void) { | UINT posl; |
| UINT y; | |
| UINT x; | |
| UINT r; | |
| UINT posr; | |
| BRESULT y2; | |
| REG16 atr; | |
| REG16 udtbase; | |
| REG16 udt; | |
| __asm { | if (!makescrn.vramsize) { |
| mov ebx, offset updatetmp | return; |
| mov ecx, 0x200 | } |
| filludt_lp: or dword ptr [ebx], (UPDATE_TVRAM * 01010101h) | posl = crtc.e.pos; |
| add ebx, 4 | y = crtc.e.yl; |
| loop filludt_lp | do { |
| for (x=0; x<crtc.s.reg[CRTCREG_HDISP]; x++) { | |
| if (!(TRAM_ATR(LOW11(posl + x)) & TRAMATR_Yx2)) { | |
| break; | |
| } | |
| } | |
| y2 = (x < crtc.s.reg[CRTCREG_HDISP])?FALSE:TRUE; | |
| udtbase = (x < crtc.s.reg[CRTCREG_HDISP])?0x0000:0x0404; | |
| r = (crtc.s.reg[CRTCREG_HDISP] + 1) >> 1; | |
| do { | |
| posr = LOW11(posl + 1); | |
| atr = (TRAM_ATR(posl) << 8) | TRAM_ATR(posr); | |
| udt = udtbase; | |
| if (!y2) { | |
| if (atr & (TRAMATR_Yx2 << 8)) { | |
| udt |= (UPDATE_TRAM | 1) << 8; // 左潰れ縦倍角 | |
| } | |
| else { | |
| y2 = TRUE; | |
| } | |
| } | |
| if (!y2) { | |
| if (atr & (TRAMATR_Yx2 << 0)) { | |
| udt |= (UPDATE_TRAM | 1) << 0; // 右潰れ縦倍角 | |
| } | |
| else { | |
| y2 = TRUE; | |
| } | |
| } | |
| if (atr & (TRAMATR_Xx2 << 8)) { // 左側倍角? | |
| udt |= 0x0812; | |
| } | |
| if (atr & (TRAMATR_Xx2 << 0)) { // 右側倍角? | |
| udt |= 0x0008; | |
| } | |
| if ((TRAMUPDATE(posl) ^ (udt >> 8)) & 0x1f) { | |
| TRAMUPDATE(posl) = (UINT8)((udt >> 8) | UPDATE_TRAM); | |
| } | |
| if ((TRAMUPDATE(posr) ^ (udt >> 0)) & 0x1f) { | |
| TRAMUPDATE(posr) = (UINT8)((udt >> 0) | UPDATE_TRAM); | |
| } | |
| posl = LOW11(posl + 2); | |
| } while(--r); | |
| if (crtc.s.reg[CRTCREG_HDISP] & 1) { | |
| posl = LOW11(posl - 1); | |
| } | } |
| } while(--y); | |
| } | } |
| static LABEL void flashupdatetmp(void) { | static BRESULT updateblink(void) { |
| __asm { | UINT pos; |
| push ebx | REG8 update; |
| push esi | UINT r; |
| push edi | |
| pos = makescrn.vramtop; | |
| movzx esi, crtc.s.TXT_TOP | makescrn.blinktest ^= 0x10; |
| xor dl, dl | update = 0; |
| // まず行すべてが縦倍角か調べる | r = makescrn.vramsize; |
| check_tateflag: mov edi, esi | while(r) { |
| movzx ecx, crtc.s.TXT_XL | r--; |
| tateflaglp_s: and edi, (TRAM_MAX - 1) | if (TRAM_ATR(pos) & 0x10) { |
| test tram[TRAM_ATR + edi], X1ATR_Yx2 | TRAMUPDATE(pos) |= UPDATE_TRAM; |
| je tatex1 | update = UPDATE_TRAM; |
| inc edi | } |
| loop tateflaglp_s | pos = LOW11(pos + 1); |
| // すべて縦倍角 だったら | } |
| if (update) { | |
| movzx ecx, crtc.s.TXT_XL | return(TRUE); |
| shr cl, 1 | } |
| else { | |
| tatex2loop_s: and esi, (TRAM_MAX - 1) | return(FALSE); |
| mov ax, (UPDATE_TVRAM or 04h) * 0101h // 縦倍角 | |
| mov bx, word ptr (tram[TRAM_ATR + esi]) | |
| test bl, X1ATR_Xx2 | |
| je tatex2_norleft | |
| // 倍角フラグが立ってる | |
| or ax, 08h + 12h * 256 // 左4倍角 + 右縦倍角は確定 | |
| test bh, X1ATR_Xx2 | |
| je tatex2_pcg | |
| or ah, 8 // 右側も倍角ビットが立ってた | |
| jmp tatex2_pcg | |
| tatex2_norleft: test bh, X1ATR_Xx2 // 4倍角でない場合 | |
| je tatex2_pcg | |
| or ah, 8 // 右側のみ倍角だった | |
| tatex2_pcg: mov bx, word ptr (updatetmp[esi]) | |
| and bx, UPDATE_TVRAM * 0101h | |
| or ax, bx // UPDATEフラグを加える | |
| cmp word ptr (updatetmp[esi]), ax | |
| je tatex2noupdate | |
| or ax, UPDATE_TVRAM * 0101h | |
| mov word ptr (updatetmp[esi]), ax | |
| tatex2noupdate: add esi, 2 | |
| loop tatex2loop_s | |
| jmp nextlinecheck | |
| tatex1: movzx ecx, crtc.s.TXT_XL | |
| shr cl, 1 | |
| xor dh, dh | |
| tatex1loop_s: and esi, (TRAM_MAX - 1) | |
| xor ax, ax | |
| mov bx, word ptr (tram[TRAM_ATR + esi]) | |
| or dh, dh // 縦ノーマルは既にあったか? | |
| jne tatex1_tate_e | |
| test bl, X1ATR_Yx2 | |
| je tatex1_tate0 | |
| mov al, UPDATE_TVRAM or 1 // 左潰れ縦倍角 | |
| test bh, X1ATR_Yx2 | |
| je tatex1_tate0 | |
| mov ah, UPDATE_TVRAM or 1 // 右潰れ縦倍角 | |
| jmp tatex1_tate_e | |
| tatex1_tate0: inc dh // 縦ノーマルの出現 | |
| tatex1_tate_e: | |
| test bl, X1ATR_Xx2 | |
| je tatex1_norleft | |
| // 倍角フラグが立ってる | |
| or ax, 08h + (12h * 256) // 左横倍角 は確定 | |
| test bh, X1ATR_Xx2 | |
| je tatex1_pcg | |
| or ah, 8 // 右側も倍角ビットが立ってた | |
| jmp tatex1_pcg | |
| tatex1_norleft: test bh, X1ATR_Xx2 // 倍角でない場合 | |
| je tatex1_pcg | |
| or ah, 8 // 右側のみ倍角だった | |
| tatex1_pcg: mov bx, word ptr (updatetmp[esi]) | |
| and bx, UPDATE_TVRAM * 0101h | |
| or ax, bx | |
| cmp word ptr (updatetmp[esi]), ax | |
| je tatex1noupdate | |
| or ax, UPDATE_TVRAM * 0101h | |
| mov word ptr (updatetmp[esi]), ax | |
| tatex1noupdate: add esi, 2 | |
| loop tatex1loop_s | |
| nextlinecheck: inc dl | |
| cmp dl, crtc.s.TXT_YL | |
| jb check_tateflag | |
| pop edi | |
| pop esi | |
| pop ebx | |
| ret | |
| } | } |
| } | } |
| void updateblink(void) { | |
| __asm { | // ---- |
| dec blinktime | |
| jns blinkupflg_ed | typedef void (*MAKEFN)(void); |
| mov blinktime, 30-1 | |
| push edi | static void width_dummy(void) { } |
| movzx edi, crtc.s.TXT_TOP | |
| mov ax, 010h | static const UINT8 screendraw[] = { |
| xor blinktest, al | MAKESCRN_320x200S, MAKESCRN_320x400, |
| mov cx, word ptr (makescrn.vramsize) | MAKESCRN_320x200S, MAKESCRN_320x400, |
| or cx, cx | MAKESCRN_320x200S, MAKESCRN_320x400, |
| je blinkupflg | MAKESCRN_320x200S, MAKESCRN_320x200H, |
| blinkup_lp: test tram[TRAM_ATR + edi], al | MAKESCRN_320x200S, MAKESCRN_320x400, |
| je short blinknup_ed | MAKESCRN_320x200S, MAKESCRN_320x400, |
| mov ah, UPDATE_TVRAM | MAKESCRN_320x200S, MAKESCRN_320x200H, |
| or updatetmp[edi], ah | MAKESCRN_320x200S, MAKESCRN_320x200H, |
| blinknup_ed: inc edi | |
| dec cx | #if defined(SUPPORT_TURBOZ) |
| jne blinkup_lp | MAKESCRN_320x200H, MAKESCRN_320x200H, |
| or makescrn.scrnflash, ah | MAKESCRN_320x200H, MAKESCRN_320x200H, |
| shr ah, 5 | MAKESCRN_320x200H, MAKESCRN_320x200H, |
| blinkupflg: pop edi | MAKESCRN_320x200H, MAKESCRN_320x200H, |
| mov makescrn.existblink, ah | |
| blinkupflg_ed: | MAKESCRN_320x200H, MAKESCRN_320x200H, |
| } | MAKESCRN_320x200H, MAKESCRN_320x200H, |
| } | MAKESCRN_320x200H, MAKESCRN_320x200H, |
| MAKESCRN_320x200H, MAKESCRN_320x200H, | |
| #endif | |
| }; | |
| static const MAKEFN screenmake[] = { | |
| width80x25_200l, width80x25_400h, | |
| width80x25_200l, width80x25_200h, | |
| width80x12_200l, width80x12_400h, | |
| width80x12_200l, width80x12_200h, | |
| width80x20l, width80x20h, | |
| width80x20l, width80x20h, | |
| width80x10l, width80x10h, | |
| width80x10l, width80x10h, | |
| #if defined(SUPPORT_TURBOZ) | |
| width_dummy, width_dummy, | |
| width_dummy, width_dummy, | |
| width_dummy, width_dummy, | |
| width_dummy, width_dummy, | |
| width_dummy, width_dummy, | |
| width_dummy, width_dummy, | |
| width_dummy, width_dummy, | |
| width_dummy, width_dummy, | |
| #endif | |
| }; | |
| static void changemodes(void) { | |
| REG8 dispmode; | |
| dispmode = crtc.e.dispmode; | |
| makescrn.dispmode = dispmode; | |
| makescrn.drawmode = screendraw[dispmode & DISPMODE_MASKMODE]; | |
| if (dispmode & DISPMODE_WIDTH80) { | |
| makescrn.drawmode |= 1; | |
| } | |
| sysmng_scrnwidth((dispmode & DISPMODE_WIDTH80) == 0); | |
| // --------------------------------------------------------------------------- | if (!(dispmode & DISPMODE_BANK1)) { |
| makescrn.disp1 = gram + GRAM_BANK0; | |
| makescrn.disp2 = gram + GRAM_BANK1; | |
| makescrn.dispflag = UPDATE_TRAM + UPDATE_VRAM0; | |
| } | |
| else { | |
| makescrn.disp1 = gram + GRAM_BANK1; | |
| makescrn.disp2 = gram + GRAM_BANK0; | |
| makescrn.dispflag = UPDATE_TRAM + UPDATE_VRAM1; | |
| } | |
| } | |
| static void x1vram_adjust(void) { | static void changecrtc(void) { |
| REG8 widthmode; | UINT scrnxmax; |
| UINT scrnymax; | |
| UINT textxl; | |
| UINT surfcx; | |
| UINT fontcy; | UINT fontcy; |
| UINT underlines; | UINT underlines; |
| REG8 y2; | REG8 y2; |
| UINT charcy; | UINT charcy; |
| UINT surfcy; | UINT surfcy; |
| UINT surfsy; | |
| UINT x; | |
| UINT y; | |
| UINT8 *p; | |
| if (crtc.s.TXT_XL <= 40) { | makescrn.vramtop = crtc.e.pos; |
| if (dispmode & SCRN_DRAW4096) { | |
| widthmode = SCRNWIDTHMODE_4096; | |
| } | |
| else { | |
| widthmode = SCRNWIDTHMODE_WIDTH40; | |
| } | |
| } | |
| else { | |
| widthmode = SCRNWIDTHMODE_WIDTH80; | |
| } | |
| scrndraw_changewidth(widthmode); | |
| makescrn.surfcx = min(80, crtc.s.TXT_XL); | scrnxmax = (makescrn.dispmode & DISPMODE_WIDTH80)?80:40; |
| makescrn.surfrx = crtc.s.TXT_XL - makescrn.surfcx; | scrnymax = 200; |
| fontcy = crtc.s.FNT_YL; | textxl = crtc.s.reg[CRTCREG_HDISP]; |
| if (crtc.s.SCRN_BITS & SCRN_24KHZ) { | surfcx = min(scrnxmax, textxl); |
| fontcy >>= 1; | |
| } | fontcy = crtc.e.fonty; |
| underlines = (crtc.s.SCRN_BITS & SCRN_UNDERLINE)?2:0; | underlines = (makescrn.dispmode & DISPMODE_UNDERLINE)?2:0; |
| if (fontcy > underlines) { | if (fontcy > underlines) { |
| fontcy -= underlines; | fontcy -= underlines; |
| } | } |
| else { | else { |
| fontcy = 0; | fontcy = 0; |
| } | } |
| y2 = (crtc.s.SCRN_BITS & SCRN_TEXTYx2)?1:0; | y2 = (makescrn.dispmode & DISPMODE_TEXTYx2)?1:0; |
| fontcy >>= y2; | fontcy >>= y2; |
| #if 0 | #if 0 |
| if (((dispmode & SCRN64_MASK) != SCRN64_INVALID) && (fontcy > 8)) { | if (((dispmode & SCRN64_MASK) != SCRN64_INVALID) && (fontcy > 8)) { |
| Line 230 static void x1vram_adjust(void) { | Line 243 static void x1vram_adjust(void) { |
| charcy = fontcy + underlines; | charcy = fontcy + underlines; |
| makescrn.fontcy = fontcy; | makescrn.fontcy = fontcy; |
| makescrn.charcy = charcy; | makescrn.charcy = charcy; |
| charcy <<= y2; | charcy <<= y2; |
| surfcy = 200 / charcy; | surfcy = scrnymax / charcy; |
| if (surfcy > crtc.s.TXT_YL) { | if (surfcy > crtc.e.yl) { |
| surfcy = crtc.s.TXT_YL; | surfcy = crtc.e.yl; |
| } | |
| surfsy = charcy * surfcy * 2; | |
| // ハイドライド3で画面が消えないのでロジックを修正すべし | |
| x = min(scrnxmax, makescrn.surfcx); | |
| if (surfcx < x) { // 小さくなった | |
| x = (x - surfcx) * 8; | |
| p = screenmap + (surfcx * 8); | |
| y = surfsy; | |
| while(y) { | |
| y--; | |
| ZeroMemory(p, x); | |
| p += SURFACE_WIDTH; | |
| } | |
| } | |
| if (surfsy < makescrn.surfsy) { | |
| ZeroMemory(screenmap + (SURFACE_WIDTH * surfsy), | |
| SURFACE_WIDTH * (makescrn.surfsy - surfsy)); | |
| } | } |
| makescrn.surfcx = surfcx; | |
| makescrn.surfrx = textxl - surfcx; | |
| makescrn.surfcy = surfcy; | makescrn.surfcy = surfcy; |
| makescrn.surfstep = (SURFACE_WIDTH * charcy * 2) - (makescrn.surfcx * 8); | makescrn.surfsy = surfsy; |
| makescrn.vramsize = min(0x800, charcy * crtc.s.TXT_XL); | makescrn.surfstep = (SURFACE_WIDTH * charcy * 2) - (surfcx * 8); |
| scrnmng_setheight(0, charcy * surfcy * 2); | makescrn.vramsize = min(0x800, surfcy * textxl); |
| // scrnmng_setheight(0, charcy * surfcy * 2); | |
| } | } |
| // ------------------------------------------------------------------------- | |
| typedef void (*DRAWFN)(void); | |
| static const DRAWFN screendraw[8] = { | |
| width80x25_200l, width80x25_400h, | |
| width80x25_200l, width80x25_200h, | |
| width80x12_200l, width80x12_400h, | |
| width80x12_200l, width80x12_200h}; | |
| static const DRAWFN screendraw2[8] = { | |
| width80x20l, width80x20h, | |
| width80x20l, width80x20h, | |
| width80x10l, width80x10h, | |
| width80x10l, width80x10h}; | |
| void scrnupdate(void) { | void scrnupdate(void) { |
| BRESULT ddrawflash; | REG8 flag; |
| REG8 existblink; | |
| if (!corestat.drawframe) { | if (!corestat.drawframe) { |
| return; | return; |
| } | } |
| corestat.drawframe = 0; | corestat.drawframe = 0; |
| ddrawflash = FALSE; | flag = makescrn.nextdraw; |
| if (lastdisp != dispmode) { | if (crtc.e.scrnflash) { |
| lastdisp = dispmode; | crtc.e.scrnflash = 0; |
| scrnallflash = 1; | flag |= SCRNUPD_FLASH; |
| makescrn.palandply = 1; | } |
| if (!(dispmode & SCRN_BANK1)) { | if (crtc.e.scrnallflash) { |
| dispp = GRP_RAM + GRAM_BANK0; | crtc.e.scrnallflash = 0; |
| dispp2 = GRP_RAM + GRAM_BANK1; | flag |= SCRNUPD_ALLFLASH; |
| dispflg = UPDATE_VRAM0; | } |
| } | if (crtc.e.palandply) { |
| else { | crtc.e.palandply = 0; |
| dispp = GRP_RAM + GRAM_BANK1; | flag |= SCRNUPD_PALANDPLY; |
| dispp2 = GRP_RAM + GRAM_BANK0; | } |
| dispflg = UPDATE_VRAM1; | |
| } | if (makescrn.dispmode != crtc.e.dispmode) { |
| } | TRACEOUT(("change mode!")); |
| if (scrnallflash) { | changemodes(); |
| scrnallflash = 0; | flag |= SCRNUPD_ALLFLASH | SCRNUPD_PALANDPLY; |
| } | |
| if (flag & SCRNUPD_ALLFLASH) { | |
| changecrtc(); | |
| TRACEOUT(("flash! %dx%d", makescrn.surfcx, makescrn.surfcy)); | |
| fillupdatetmp(); | fillupdatetmp(); |
| x1vram_adjust(); | flag |= SCRNUPD_FLASH; |
| makescrn.scrnflash = 1; | |
| } | } |
| if (makescrn.remakeattr) { | if (crtc.e.remakeattr) { |
| makescrn.remakeattr = 0; | crtc.e.remakeattr = 0; |
| flashupdatetmp(); | flashupdatetmp(); |
| } | } |
| if (makescrn.palandply) { | if (flag & SCRNUPD_PALANDPLY) { |
| makescrn.palandply = 0; | pal_update(); |
| palettes(); | |
| ddrawflash = 1; | |
| } | |
| if (makescrn.existblink) { | |
| updateblink(); | |
| } | } |
| if (makescrn.scrnflash) { | if (crtc.e.blinktime) { |
| makescrn.scrnflash = 0; | crtc.e.blinktime--; |
| makescrn.fontycnt = 0; | } |
| switch(lastdisp & SCRN64_MASK) { | else { |
| case SCRN64_320x200: | crtc.e.blinktime = 30 - 1; |
| // width40x25_64s(); | if (crtc.e.existblink) { |
| break; | existblink = updateblink(); |
| crtc.e.existblink = existblink; | |
| case SCRN64_L320x200x2: | flag |= existblink; |
| // width40x25_64x2(); | } |
| break; | } |
| case SCRN64_L640x200: | |
| // width80x25_64s(); | |
| break; | |
| case SCRN64_H320x400: | |
| // width40x25_64h(); | |
| break; | |
| case SCRN64_320x200x4096: | |
| // width40x25_4096(); | |
| break; | |
| case SCRN64_320x100: | if (flag & SCRNUPD_FLASH) { |
| // width40x12_64l(); | if (makescrn.vramsize) { |
| break; | makescrn.fontycnt = 0; |
| screenmake[makescrn.dispmode & DISPMODE_MASKMODE](); | |
| #if 0 | |
| switch(lastdisp & SCRN64_MASK) { | |
| case SCRN64_320x200: | |
| // width40x25_64s(); | |
| break; | |
| case SCRN64_L320x200x2: | |
| // width40x25_64x2(); | |
| break; | |
| case SCRN64_L640x200: | |
| // width80x25_64s(); | |
| break; | |
| case SCRN64_H320x400: | |
| // width40x25_64h(); | |
| break; | |
| case SCRN64_320x200x4096: | |
| // width40x25_4096(); | |
| break; | |
| case SCRN64_320x100: | |
| // width40x12_64l(); | |
| break; | |
| case SCRN64_320x100x2: | |
| // width40x12_64x2(); | |
| break; | |
| case SCRN64_L640x100: | |
| // width80x12_64s(); | |
| break; | |
| case SCRN64_H320x200: | |
| // width40x12_64h(); | |
| break; | |
| case SCRN64_320x100x4096: | |
| // width40x12_4096(); | |
| break; | |
| // case SCRN64_INVALID: | |
| default: | |
| if (!(crtc.s.SCRN_BITS & SCRN_UNDERLINE)) { | |
| screenmake[(crtc.s.SCRN_BITS & 7) + 0](); | |
| } | |
| else { | |
| screenmake[(crtc.s.SCRN_BITS & 7) + 8](); | |
| } | |
| break; | |
| } | |
| #endif | |
| } | |
| } | |
| case SCRN64_320x100x2: | if (flag) { |
| // width40x12_64x2(); | makescrn.nextdraw = scrndraw_draw(flag & SCRNUPD_ALLFLASH); |
| break; | drawtime++; |
| } | |
| } | |
| case SCRN64_L640x100: | |
| // width80x12_64s(); | |
| break; | |
| case SCRN64_H320x200: | void makescrn_initialize(void) { |
| // width40x12_64h(); | |
| break; | |
| case SCRN64_320x100x4096: | makesub_initialize(); |
| // width40x12_4096(); | } |
| break; | |
| // case SCRN64_INVALID: | void makescrn_reset(void) { |
| default: | |
| if (!(crtc.s.SCRN_BITS & SCRN_UNDERLINE)) { | |
| screendraw[crtc.s.SCRN_BITS & 7](); | |
| } | |
| else { | |
| screendraw2[crtc.s.SCRN_BITS & 7](); | |
| } | |
| break; | |
| } | |
| ddrawflash = 1; | |
| } | |
| if (ddrawflash) { | changemodes(); |
| ddrawflash = 0; | changecrtc(); |
| scrndraw_draw(FALSE); | flashupdatetmp(); |
| drawtime++; | |
| } | |
| } | } |