X-Git-Url: https://git.artsoft.org/?a=blobdiff_plain;f=src%2Ftools.c;h=a2b46c8604fd3b8ac0fed0743e0a96dde455701e;hb=40a487dcc5d3028343ff9123a72b8b3839a42861;hp=f611f5cd7344c54a6b6940f8562ce4d1ea8bfdf3;hpb=4b0c6356359ee52f98cee8fa578179c6c41d4ef1;p=rocksndiamonds.git diff --git a/src/tools.c b/src/tools.c index f611f5cd..a2b46c86 100644 --- a/src/tools.c +++ b/src/tools.c @@ -1,13 +1,12 @@ /*********************************************************** * Rocks'n'Diamonds -- McDuffin Strikes Back! * *----------------------------------------------------------* -* ©1995 Artsoft Development * -* Holger Schemel * -* 33659 Bielefeld-Senne * -* Telefon: (0521) 493245 * -* eMail: aeglos@valinor.owl.de * -* aeglos@uni-paderborn.de * -* q99492@pbhrzx.uni-paderborn.de * +* (c) 1995-98 Artsoft Entertainment * +* Holger Schemel * +* Oststrasse 11a * +* 33604 Bielefeld * +* phone: ++49 +521 290471 * +* email: aeglos@valinor.owl.de * *----------------------------------------------------------* * tools.c * ***********************************************************/ @@ -24,16 +23,17 @@ #include "buttons.h" #include "joystick.h" #include "cartoons.h" +#include "network.h" #include #ifdef MSDOS -extern BOOL wait_for_vsync; +extern boolean wait_for_vsync; #endif void SetDrawtoField(int mode) { - if (mode == DRAW_BUFFERED && soft_scrolling_on) + if (mode == DRAW_BUFFERED && setup.soft_scrolling) { FX = TILEX; FY = TILEY; @@ -64,16 +64,22 @@ void SetDrawtoField(int mode) void BackToFront() { int x,y; - Drawable buffer = (drawto_field != window ? drawto_field : backbuffer); + Drawable buffer = (drawto_field == window ? backbuffer : drawto_field); - if (direct_draw_on && game_status == PLAYING) + if (setup.direct_draw && game_status == PLAYING) redraw_mask &= ~REDRAW_MAIN; if (redraw_mask & REDRAW_TILES && redraw_tiles > REDRAWTILES_THRESHOLD) redraw_mask |= REDRAW_FIELD; - if (redraw_mask & REDRAW_FIELD || ScreenMovPos) + if (redraw_mask & REDRAW_FIELD) + redraw_mask &= ~REDRAW_TILES; + + /* + if (redraw_mask & REDRAW_FIELD || + (ScreenGfxPos && setup.soft_scrolling && game_status == PLAYING)) redraw_mask &= ~REDRAW_TILES; + */ if (!redraw_mask) return; @@ -107,10 +113,10 @@ void BackToFront() { int fx = FX, fy = FY; - if (soft_scrolling_on) + if (setup.soft_scrolling) { - fx += (PlayerMovDir & (MV_LEFT|MV_RIGHT) ? ScreenMovPos : 0); - fy += (PlayerMovDir & (MV_UP|MV_DOWN) ? ScreenMovPos : 0); + fx += (ScreenMovDir & (MV_LEFT|MV_RIGHT) ? ScreenGfxPos : 0); + fy += (ScreenMovDir & (MV_UP|MV_DOWN) ? ScreenGfxPos : 0); } XCopyArea(display,buffer,window,gc, @@ -187,9 +193,9 @@ void BackToFront() void FadeToFront() { /* - long fading_delay = 300000; + long fading_delay = 300; - if (fading_on && (redraw_mask & REDRAW_FIELD)) + if (setup.fading && (redraw_mask & REDRAW_FIELD)) { */ @@ -208,7 +214,7 @@ void FadeToFront() REAL_SX,REAL_SY+i, FULL_SXSIZE,1, REAL_SX,REAL_SY+i); } XFlush(display); - Delay(10000); + Delay(10); } */ @@ -257,7 +263,7 @@ void ClearWindow() XFillRectangle(display,backbuffer,gc, REAL_SX,REAL_SY, FULL_SXSIZE,FULL_SYSIZE); - if (soft_scrolling_on && game_status==PLAYING) + if (setup.soft_scrolling && game_status==PLAYING) { XFillRectangle(display,fieldbuffer,gc, 0,0, FXSIZE,FYSIZE); @@ -266,7 +272,7 @@ void ClearWindow() else SetDrawtoField(DRAW_BACKBUFFER); - if (direct_draw_on && game_status==PLAYING) + if (setup.direct_draw && game_status==PLAYING) { XFillRectangle(display,window,gc, REAL_SX,REAL_SY, FULL_SXSIZE,FULL_SYSIZE); @@ -330,23 +336,41 @@ void DrawTextExt(Drawable d, GC gc, int x, int y, } } -void DrawPlayerField() +void DrawAllPlayers() { - int x = JX, y = JY; - int sx = SCROLLX(x), sy = SCROLLY(y); + int i; - int sxx = 0, syy = 0; + for(i=0; ijx, jy = player->jy; + int last_jx = player->last_jx, last_jy = player->last_jy; + int next_jx = jx + (jx - last_jx), next_jy = jy + (jy - last_jy); + int sx = SCREENX(jx), sy = SCREENY(jy); + int sxx = 0, syy = 0; + int element = Feld[jx][jy]; int graphic, phase; - if (PlayerGone) + if (!player->active || player->gone || + !IN_SCR_FIELD(SCREENX(last_jx),SCREENY(last_jy))) return; #if DEBUG - if (!IN_LEV_FIELD(x,y) || !IN_SCR_FIELD(sx,sy)) + if (!IN_LEV_FIELD(jx,jy)) { - printf("DrawPlayerField(): x = %d, y = %d\n",x,y); + printf("DrawPlayerField(): x = %d, y = %d\n",jx,jy); printf("DrawPlayerField(): sx = %d, sy = %d\n",sx,sy); printf("DrawPlayerField(): This should never happen!\n"); return; @@ -356,92 +380,91 @@ void DrawPlayerField() if (element == EL_EXPLODING) return; - if (direct_draw_on) - SetDrawtoField(DRAW_BUFFERED); - /* draw things in the field the player is leaving, if needed */ - if (lastJX != JX || lastJY != JY) + if (last_jx != jx || last_jy != jy) { - if (Store[lastJX][lastJY]) + if (Store[last_jx][last_jy]) { - DrawLevelElement(lastJX,lastJY, Store[lastJX][lastJY]); - DrawLevelElementThruMask(lastJX,lastJY, Feld[lastJX][lastJY]); + DrawLevelElement(last_jx,last_jy, Store[last_jx][last_jy]); + DrawLevelFieldThruMask(last_jx,last_jy); } - else if (Feld[lastJX][lastJY] == EL_DYNAMIT) - DrawDynamite(lastJX,lastJY); + else if (Feld[last_jx][last_jy] == EL_DYNAMIT) + DrawDynamite(last_jx,last_jy); else - DrawLevelField(lastJX,lastJY); + DrawLevelField(last_jx,last_jy); - if (PlayerPushing) + if (player->Pushing && IN_SCR_FIELD(SCREENX(next_jx),SCREENY(next_jy))) { - int nextJX = JX + (JX - lastJX); - int nextJY = JY + (JY - lastJY); - - if (PlayerGfxPos) + if (player->GfxPos) { - if (Feld[nextJX][nextJY] == EL_SOKOBAN_FELD_VOLL) - DrawLevelElement(nextJX,nextJY, EL_SOKOBAN_FELD_LEER); + if (Feld[next_jx][next_jy] == EL_SOKOBAN_FELD_VOLL) + DrawLevelElement(next_jx,next_jy, EL_SOKOBAN_FELD_LEER); else - DrawLevelElement(nextJX,nextJY, EL_LEERRAUM); + DrawLevelElement(next_jx,next_jy, EL_LEERRAUM); } else - DrawLevelField(nextJX,nextJY); + DrawLevelField(next_jx,next_jy); } } + if (!IN_SCR_FIELD(sx,sy)) + return; + + if (setup.direct_draw) + SetDrawtoField(DRAW_BUFFERED); + /* draw things behind the player, if needed */ - if (Store[x][y]) - DrawLevelElement(x,y, Store[x][y]); + if (Store[jx][jy]) + DrawLevelElement(jx,jy, Store[jx][jy]); else if (element != EL_DYNAMIT && element != EL_DYNABOMB) - DrawLevelField(x,y); + DrawLevelField(jx,jy); /* draw player himself */ - if (PlayerMovDir==MV_LEFT) - graphic = (PlayerPushing ? GFX_SPIELER_PUSH_LEFT : GFX_SPIELER_LEFT); - else if (PlayerMovDir==MV_RIGHT) - graphic = (PlayerPushing ? GFX_SPIELER_PUSH_RIGHT : GFX_SPIELER_RIGHT); - else if (PlayerMovDir==MV_UP) - graphic = GFX_SPIELER_UP; + if (player->MovDir==MV_LEFT) + graphic = (player->Pushing ? GFX_SPIELER1_PUSH_LEFT : GFX_SPIELER1_LEFT); + else if (player->MovDir==MV_RIGHT) + graphic = (player->Pushing ? GFX_SPIELER1_PUSH_RIGHT : GFX_SPIELER1_RIGHT); + else if (player->MovDir==MV_UP) + graphic = GFX_SPIELER1_UP; else /* MV_DOWN || MV_NO_MOVING */ - graphic = GFX_SPIELER_DOWN; + graphic = GFX_SPIELER1_DOWN; - graphic += PlayerFrame; + graphic += player->index_nr * 3*HEROES_PER_LINE; + graphic += player->Frame; - if (PlayerGfxPos) + if (player->GfxPos) { - if (PlayerMovDir == MV_LEFT || PlayerMovDir == MV_RIGHT) - sxx = PlayerGfxPos; + if (player->MovDir == MV_LEFT || player->MovDir == MV_RIGHT) + sxx = player->GfxPos; else - syy = PlayerGfxPos; + syy = player->GfxPos; } - if (!soft_scrolling_on && ScreenMovPos) + if (!setup.soft_scrolling && ScreenMovPos) sxx = syy = 0; DrawGraphicShiftedThruMask(sx,sy, sxx,syy, graphic, NO_CUTTING); - if (PlayerPushing && PlayerGfxPos) + if (player->Pushing && player->GfxPos) { - int nextJX = JX + (JX - lastJX); - int nextJY = JY + (JY - lastJY); - int px = SCROLLX(nextJX), py = SCROLLY(nextJY); + int px = SCREENX(next_jx), py = SCREENY(next_jy); - if (Feld[JX][JY] == EL_SOKOBAN_FELD_LEER || - Feld[nextJX][nextJY] == EL_SOKOBAN_FELD_VOLL) + if (Feld[jx][jy] == EL_SOKOBAN_FELD_LEER || + Feld[next_jx][next_jy] == EL_SOKOBAN_FELD_VOLL) DrawGraphicShiftedThruMask(px,py,sxx,syy, GFX_SOKOBAN_OBJEKT,NO_CUTTING); else { - int element = Feld[nextJX][nextJY]; + int element = Feld[next_jx][next_jy]; int graphic = el2gfx(element); if (element == EL_FELSBROCKEN && sxx) { - int phase = (PlayerGfxPos / (TILEX/4)); + int phase = (player->GfxPos / (TILEX/4)); - if (PlayerMovDir == MV_LEFT) + if (player->MovDir == MV_LEFT) graphic += phase; else graphic += (phase+4)%4; @@ -459,32 +482,34 @@ void DrawPlayerField() if (element == EL_DYNAMIT) { - if ((phase = (96-MovDelay[x][y])/12) > 6) + if ((phase = (96-MovDelay[jx][jy])/12) > 6) phase = 6; } else { - if ((phase = ((96-MovDelay[x][y])/6) % 8) > 3) + if ((phase = ((96-MovDelay[jx][jy])/6) % 8) > 3) phase = 7-phase; } DrawGraphicThruMask(sx,sy, graphic + phase); } - if (direct_draw_on) + if ((last_jx != jx || last_jy != jy) && Feld[last_jx][last_jy]==EL_EXPLODING) { - int dest_x = SX+SCROLLX(x)*TILEX; - int dest_y = SY+SCROLLY(y)*TILEY; - int x_size = TILEX; - int y_size = TILEY; + int phase = Frame[last_jx][last_jy]; + int delay = 2; - if (!ScreenMovPos) - { - dest_x = SX + SCROLLX(MIN(JX,lastJX))*TILEX; - dest_y = SY + SCROLLY(MIN(JY,lastJY))*TILEY; - x_size = TILEX * (1 + ABS(JX - lastJX)); - y_size = TILEY * (1 + ABS(JY - lastJY)); - } + if (phase > 2) + DrawGraphicThruMask(SCREENX(last_jx),SCREENY(last_jy), + GFX_EXPLOSION + ((phase-1)/delay-1)); + } + + if (setup.direct_draw) + { + int dest_x = SX + SCREENX(MIN(jx,last_jx))*TILEX; + int dest_y = SY + SCREENY(MIN(jy,last_jy))*TILEY; + int x_size = TILEX * (1 + ABS(jx - last_jx)); + int y_size = TILEY * (1 + ABS(jy - last_jy)); XCopyArea(display,drawto_field,window,gc, dest_x,dest_y, x_size,y_size, dest_x,dest_y); @@ -513,18 +538,34 @@ static int getGraphicAnimationPhase(int frames, int delay, int mode) return(phase); } +void DrawGraphicAnimationExt(int x, int y, int graphic, + int frames, int delay, int mode, int mask_mode) +{ + int phase = getGraphicAnimationPhase(frames, delay, mode); + + if (!(FrameCounter % delay) && IN_SCR_FIELD(SCREENX(x),SCREENY(y))) + { + if (mask_mode == USE_MASKING) + DrawGraphicThruMask(SCREENX(x),SCREENY(y), graphic + phase); + else + DrawGraphic(SCREENX(x),SCREENY(y), graphic + phase); + } +} + void DrawGraphicAnimation(int x, int y, int graphic, int frames, int delay, int mode) { - int phase = getGraphicAnimationPhase(frames, delay, mode); + DrawGraphicAnimationExt(x,y, graphic, frames,delay,mode, NO_MASKING); +} - if (!(FrameCounter % delay) && IN_SCR_FIELD(SCROLLX(x),SCROLLY(y))) - DrawGraphic(SCROLLX(x),SCROLLY(y), graphic + phase); +void DrawGraphicAnimationThruMask(int x, int y, int graphic, + int frames, int delay, int mode) +{ + DrawGraphicAnimationExt(x,y, graphic, frames,delay,mode, USE_MASKING); } void DrawGraphic(int x, int y, int graphic) { - #if DEBUG if (!IN_SCR_FIELD(x,y)) { @@ -534,40 +575,35 @@ void DrawGraphic(int x, int y, int graphic) } #endif - DrawGraphicExt(drawto_field, gc, x, y, graphic); + DrawGraphicExt(drawto_field, gc, FX+x*TILEX, FY+y*TILEY, graphic); MarkTileDirty(x,y); } void DrawGraphicExt(Drawable d, GC gc, int x, int y, int graphic) -{ - DrawGraphicExtHiRes(d, gc, FX+x*TILEX, FY+y*TILEY, graphic); -} - -void DrawGraphicExtHiRes(Drawable d, GC gc, int x, int y, int graphic) { if (graphic >= GFX_START_ROCKSSCREEN && graphic <= GFX_END_ROCKSSCREEN) { graphic -= GFX_START_ROCKSSCREEN; XCopyArea(display,pix[PIX_BACK],d,gc, - SX+(graphic % GFX_PER_LINE)*TILEX, - SY+(graphic / GFX_PER_LINE)*TILEY, + SX + (graphic % GFX_PER_LINE) * TILEX, + SY + (graphic / GFX_PER_LINE) * TILEY, TILEX,TILEY, x,y); } else if (graphic >= GFX_START_ROCKSHEROES && graphic <= GFX_END_ROCKSHEROES) { graphic -= GFX_START_ROCKSHEROES; XCopyArea(display,pix[PIX_HEROES],d,gc, - (graphic % HEROES_PER_LINE)*TILEX, - (graphic / HEROES_PER_LINE)*TILEY, + (graphic % HEROES_PER_LINE) * TILEX, + (graphic / HEROES_PER_LINE) * TILEY, TILEX,TILEY, x,y); } else if (graphic >= GFX_START_ROCKSFONT && graphic <= GFX_END_ROCKSFONT) { graphic -= GFX_START_ROCKSFONT; XCopyArea(display,pix[PIX_BIGFONT],d,gc, - (graphic % FONT_CHARS_PER_LINE)*TILEX, - (graphic / FONT_CHARS_PER_LINE)*TILEY + - FC_SPECIAL1*TILEY*FONT_LINES_PER_FONT, + (graphic % FONT_CHARS_PER_LINE) * TILEX, + (graphic / FONT_CHARS_PER_LINE) * TILEY + + FC_SPECIAL1 * FONT_LINES_PER_FONT * TILEY, TILEX,TILEY, x,y); } else @@ -576,73 +612,74 @@ void DrawGraphicExtHiRes(Drawable d, GC gc, int x, int y, int graphic) void DrawGraphicThruMask(int x, int y, int graphic) { - int src_x,src_y, dest_x,dest_y; - #if DEBUG if (!IN_SCR_FIELD(x,y)) { - printf("DrawGraphicThruMask(): x = %d, y = %d\n",x,y); + printf("DrawGraphicThruMask(): x = %d,y = %d, graphic = %d\n",x,y,graphic); printf("DrawGraphicThruMask(): This should never happen!\n"); return; } #endif + DrawGraphicThruMaskExt(drawto_field, FX+x*TILEX, FY+y*TILEY, graphic); + MarkTileDirty(x,y); +} + +void DrawGraphicThruMaskExt(Drawable d, int dest_x, int dest_y, int graphic) +{ + int src_x, src_y; + int tile = graphic; + Pixmap src_pixmap; + GC drawing_gc; + if (graphic >= GFX_START_ROCKSSCREEN && graphic <= GFX_END_ROCKSSCREEN) { + src_pixmap = pix[PIX_BACK]; + drawing_gc = clip_gc[PIX_BACK]; graphic -= GFX_START_ROCKSSCREEN; src_x = SX+(graphic % GFX_PER_LINE)*TILEX; src_y = SY+(graphic / GFX_PER_LINE)*TILEY; - dest_x = FX+x*TILEX; - dest_y = FY+y*TILEY; - - XSetClipOrigin(display,clip_gc[PIX_BACK],dest_x-src_x,dest_y-src_y); - XCopyArea(display,pix[PIX_BACK],drawto_field,clip_gc[PIX_BACK], - src_x,src_y, TILEX,TILEY, dest_x,dest_y); } else if (graphic >= GFX_START_ROCKSHEROES && graphic <= GFX_END_ROCKSHEROES) { + src_pixmap = pix[PIX_HEROES]; + drawing_gc = clip_gc[PIX_HEROES]; graphic -= GFX_START_ROCKSHEROES; src_x = (graphic % HEROES_PER_LINE)*TILEX; src_y = (graphic / HEROES_PER_LINE)*TILEY; - dest_x = FX+x*TILEX; - dest_y = FY+y*TILEY; - - XSetClipOrigin(display,clip_gc[PIX_HEROES],dest_x-src_x,dest_y-src_y); - XCopyArea(display,pix[PIX_HEROES],drawto_field,clip_gc[PIX_HEROES], - src_x,src_y, TILEX,TILEY, dest_x,dest_y); } else { - DrawGraphic(x,y,graphic); + DrawGraphicExt(d, gc, dest_x,dest_y, graphic); return; } - MarkTileDirty(x,y); -} - -void DrawScreenElementThruMask(int x, int y, int element) -{ - DrawGraphicThruMask(x,y,el2gfx(element)); -} + if (tile_clipmask[tile] != None) + { + XSetClipMask(display, tile_clip_gc, tile_clipmask[tile]); + XSetClipOrigin(display, tile_clip_gc, dest_x,dest_y); + XCopyArea(display, src_pixmap, drawto_field, tile_clip_gc, + src_x,src_y, TILEX,TILEY, dest_x,dest_y); + } + else + { +#if DEBUG + printf("DrawGraphicThruMask(): tile '%d' needs clipping!\n", tile); +#endif -void DrawLevelElementThruMask(int x, int y, int element) -{ - if (IN_LEV_FIELD(x,y) && IN_SCR_FIELD(SCROLLX(x),SCROLLY(y))) - DrawScreenElementThruMask(SCROLLX(x),SCROLLY(y),element); + XSetClipOrigin(display, drawing_gc, dest_x-src_x, dest_y-src_y); + XCopyArea(display, src_pixmap, drawto_field, drawing_gc, + src_x,src_y, TILEX,TILEY, dest_x,dest_y); + } } void DrawMiniGraphic(int x, int y, int graphic) { - DrawMiniGraphicExt(drawto, gc, x, y, graphic); + DrawMiniGraphicExt(drawto,gc, SX+x*MINI_TILEX,SY+y*MINI_TILEY, graphic); MarkTileDirty(x/2, y/2); } void DrawMiniGraphicExt(Drawable d, GC gc, int x, int y, int graphic) -{ - DrawMiniGraphicExtHiRes(d,gc, SX+x*MINI_TILEX,SY+y*MINI_TILEY, graphic); -} - -void DrawMiniGraphicExtHiRes(Drawable d, GC gc, int x, int y, int graphic) { if (graphic >= GFX_START_ROCKSSCREEN && graphic <= GFX_END_ROCKSSCREEN) { @@ -671,6 +708,9 @@ void DrawGraphicShifted(int x,int y, int dx,int dy, int graphic, int width = TILEX, height = TILEY; int cx = 0, cy = 0; int src_x,src_y, dest_x,dest_y; + int tile = graphic; + Pixmap src_pixmap; + GC drawing_gc; if (graphic < 0) { @@ -744,41 +784,24 @@ void DrawGraphicShifted(int x,int y, int dx,int dy, int graphic, if (graphic >= GFX_START_ROCKSSCREEN && graphic <= GFX_END_ROCKSSCREEN) { + src_pixmap = pix[PIX_BACK]; + drawing_gc = clip_gc[PIX_BACK]; graphic -= GFX_START_ROCKSSCREEN; src_x = SX+(graphic % GFX_PER_LINE)*TILEX+cx; src_y = SY+(graphic / GFX_PER_LINE)*TILEY+cy; - dest_x = FX+x*TILEX+dx; - dest_y = FY+y*TILEY+dy; - - if (mask_mode == USE_MASKING) - { - XSetClipOrigin(display,clip_gc[PIX_BACK],dest_x-src_x,dest_y-src_y); - XCopyArea(display,pix[PIX_BACK],drawto_field,clip_gc[PIX_BACK], - src_x,src_y, width,height, dest_x,dest_y); - } - else - XCopyArea(display,pix[PIX_BACK],drawto_field,gc, - src_x,src_y, width,height, dest_x,dest_y); } else if (graphic >= GFX_START_ROCKSHEROES && graphic <= GFX_END_ROCKSHEROES) { + src_pixmap = pix[PIX_HEROES]; + drawing_gc = clip_gc[PIX_HEROES]; graphic -= GFX_START_ROCKSHEROES; src_x = (graphic % HEROES_PER_LINE)*TILEX+cx; src_y = (graphic / HEROES_PER_LINE)*TILEY+cy; - dest_x = FX+x*TILEX+dx; - dest_y = FY+y*TILEY+dy; - - if (mask_mode == USE_MASKING) - { - XSetClipOrigin(display,clip_gc[PIX_HEROES],dest_x-src_x,dest_y-src_y); - XCopyArea(display,pix[PIX_HEROES],drawto_field,clip_gc[PIX_HEROES], - src_x,src_y, width,height, dest_x,dest_y); - } - else - XCopyArea(display,pix[PIX_HEROES],drawto_field,gc, - src_x,src_y, width,height, dest_x,dest_y); } + dest_x = FX + x*TILEX + dx; + dest_y = FY + y*TILEY + dy; + #if DEBUG if (!IN_SCR_FIELD(x,y)) { @@ -788,6 +811,30 @@ void DrawGraphicShifted(int x,int y, int dx,int dy, int graphic, } #endif + if (mask_mode == USE_MASKING) + { + if (tile_clipmask[tile] != None) + { + XSetClipMask(display, tile_clip_gc, tile_clipmask[tile]); + XSetClipOrigin(display, tile_clip_gc, dest_x,dest_y); + XCopyArea(display, src_pixmap, drawto_field, tile_clip_gc, + src_x,src_y, TILEX,TILEY, dest_x,dest_y); + } + else + { +#if DEBUG + printf("DrawGraphicShifted(): tile '%d' needs clipping!\n", tile); +#endif + + XSetClipOrigin(display, drawing_gc, dest_x-src_x, dest_y-src_y); + XCopyArea(display, src_pixmap, drawto_field, drawing_gc, + src_x,src_y, width,height, dest_x,dest_y); + } + } + else + XCopyArea(display, src_pixmap, drawto_field, gc, + src_x,src_y, width,height, dest_x,dest_y); + MarkTileDirty(x,y); } @@ -797,10 +844,10 @@ void DrawGraphicShiftedThruMask(int x,int y, int dx,int dy, int graphic, DrawGraphicShifted(x,y, dx,dy, graphic, cut_mode, USE_MASKING); } -void DrawScreenElementShifted(int x, int y, int dx, int dy, int element, - int cut_mode) +void DrawScreenElementExt(int x, int y, int dx, int dy, int element, + int cut_mode, int mask_mode) { - int ux = UNSCROLLX(x), uy = UNSCROLLY(y); + int ux = LEVELX(x), uy = LEVELY(y); int graphic = el2gfx(element); int phase4 = ABS(MovPos[ux][uy])/(TILEX/4); int phase = phase4 / 2; @@ -843,6 +890,10 @@ void DrawScreenElementShifted(int x, int y, int dx, int dy, int element, { graphic = GFX_SONDE_START + getGraphicAnimationPhase(8, 2, ANIM_NORMAL); } + else if (element==EL_SALZSAEURE) + { + graphic = GFX_GEBLUBBER + getGraphicAnimationPhase(4, 10, ANIM_NORMAL); + } else if (element==EL_BUTTERFLY || element==EL_FIREFLY) { graphic += !phase; @@ -863,7 +914,7 @@ void DrawScreenElementShifted(int x, int y, int dx, int dy, int element, } else if (element==EL_MAUER_LEBT) { - BOOL links_massiv = FALSE, rechts_massiv = FALSE; + boolean links_massiv = FALSE, rechts_massiv = FALSE; if (!IN_LEV_FIELD(ux-1,uy) || IS_MAUER(Feld[ux-1][uy])) links_massiv = TRUE; @@ -879,22 +930,52 @@ void DrawScreenElementShifted(int x, int y, int dx, int dy, int element, } if (dx || dy) - DrawGraphicShifted(x,y, dx,dy, graphic, cut_mode, NO_MASKING); + DrawGraphicShifted(x,y, dx,dy, graphic, cut_mode, mask_mode); + else if (mask_mode == USE_MASKING) + DrawGraphicThruMask(x,y, graphic); else DrawGraphic(x,y, graphic); } +void DrawLevelElementExt(int x, int y, int dx, int dy, int element, + int cut_mode, int mask_mode) +{ + if (IN_LEV_FIELD(x,y) && IN_SCR_FIELD(SCREENX(x),SCREENY(y))) + DrawScreenElementExt(SCREENX(x),SCREENY(y), dx,dy, element, + cut_mode, mask_mode); +} + +void DrawScreenElementShifted(int x, int y, int dx, int dy, int element, + int cut_mode) +{ + DrawScreenElementExt(x,y, dx,dy, element, cut_mode, NO_MASKING); +} + void DrawLevelElementShifted(int x, int y, int dx, int dy, int element, int cut_mode) { - if (IN_LEV_FIELD(x,y) && IN_SCR_FIELD(SCROLLX(x),SCROLLY(y))) - DrawScreenElementShifted(SCROLLX(x),SCROLLY(y), dx,dy, element, cut_mode); + DrawLevelElementExt(x,y, dx,dy, element, cut_mode, NO_MASKING); +} + +void DrawScreenElementThruMask(int x, int y, int element) +{ + DrawScreenElementExt(x,y, 0,0, element, NO_CUTTING, USE_MASKING); +} + +void DrawLevelElementThruMask(int x, int y, int element) +{ + DrawLevelElementExt(x,y, 0,0, element, NO_CUTTING, USE_MASKING); +} + +void DrawLevelFieldThruMask(int x, int y) +{ + DrawLevelElementExt(x,y, 0,0, Feld[x][y], NO_CUTTING, USE_MASKING); } void ErdreichAnbroeckeln(int x, int y) { int i, width, height, cx,cy; - int ux = UNSCROLLX(x), uy = UNSCROLLY(y); + int ux = LEVELX(x), uy = LEVELY(y); int element, graphic; int snip = 4; static int xy[4][2] = @@ -998,19 +1079,19 @@ void ErdreichAnbroeckeln(int x, int y) void DrawScreenElement(int x, int y, int element) { - DrawScreenElementShifted(x,y, 0,0, element, NO_CUTTING); + DrawScreenElementExt(x,y, 0,0, element, NO_CUTTING, NO_MASKING); ErdreichAnbroeckeln(x,y); } void DrawLevelElement(int x, int y, int element) { - if (IN_LEV_FIELD(x,y) && IN_SCR_FIELD(SCROLLX(x),SCROLLY(y))) - DrawScreenElement(SCROLLX(x),SCROLLY(y),element); + if (IN_LEV_FIELD(x,y) && IN_SCR_FIELD(SCREENX(x),SCREENY(y))) + DrawScreenElement(SCREENX(x),SCREENY(y),element); } void DrawScreenField(int x, int y) { - int ux = UNSCROLLX(x), uy = UNSCROLLY(y); + int ux = LEVELX(x), uy = LEVELY(y); int element; if (!IN_LEV_FIELD(ux,uy)) @@ -1024,7 +1105,7 @@ void DrawScreenField(int x, int y) if (IS_MOVING(ux,uy)) { int horiz_move = (MovDir[ux][uy]==MV_LEFT || MovDir[ux][uy]==MV_RIGHT); - BOOL cut_mode = NO_CUTTING; + boolean cut_mode = NO_CUTTING; if (Store[ux][uy]==EL_MORAST_LEER || Store[ux][uy]==EL_SIEB_LEER || @@ -1032,9 +1113,8 @@ void DrawScreenField(int x, int y) Store[ux][uy]==EL_AMOEBE_NASS) cut_mode = CUT_ABOVE; else if (Store[ux][uy]==EL_MORAST_VOLL || - Store[ux][uy]==EL_SIEB_VOLL || - Store[ux][uy]==EL_SIEB2_VOLL || - Store[ux][uy]==EL_SALZSAEURE) + Store[ux][uy]==EL_SIEB_VOLL || + Store[ux][uy]==EL_SIEB2_VOLL) cut_mode = CUT_BELOW; if (cut_mode==CUT_ABOVE) @@ -1046,17 +1126,20 @@ void DrawScreenField(int x, int y) DrawScreenElementShifted(x,y, MovPos[ux][uy],0, element, NO_CUTTING); else DrawScreenElementShifted(x,y, 0,MovPos[ux][uy], element, cut_mode); + + if (Store[ux][uy] == EL_SALZSAEURE) + DrawLevelElementThruMask(ux,uy+1, EL_SALZSAEURE); } else if (IS_BLOCKED(ux,uy)) { int oldx,oldy; int sx, sy; int horiz_move; - BOOL cut_mode = NO_CUTTING; + boolean cut_mode = NO_CUTTING; Blocked2Moving(ux,uy,&oldx,&oldy); - sx = SCROLLX(oldx); - sy = SCROLLY(oldy); + sx = SCREENX(oldx); + sy = SCREENY(oldy); horiz_move = (MovDir[oldx][oldy]==MV_LEFT || MovDir[oldx][oldy]==MV_RIGHT); if (Store[oldx][oldy]==EL_MORAST_LEER || @@ -1081,23 +1164,23 @@ void DrawScreenField(int x, int y) void DrawLevelField(int x, int y) { - if (IN_SCR_FIELD(SCROLLX(x),SCROLLY(y))) - DrawScreenField(SCROLLX(x),SCROLLY(y)); + if (IN_SCR_FIELD(SCREENX(x),SCREENY(y))) + DrawScreenField(SCREENX(x),SCREENY(y)); else if (IS_MOVING(x,y)) { int newx,newy; Moving2Blocked(x,y,&newx,&newy); - if (IN_SCR_FIELD(SCROLLX(newx),SCROLLY(newy))) - DrawScreenField(SCROLLX(newx),SCROLLY(newy)); + if (IN_SCR_FIELD(SCREENX(newx),SCREENY(newy))) + DrawScreenField(SCREENX(newx),SCREENY(newy)); } else if (IS_BLOCKED(x,y)) { int oldx,oldy; Blocked2Moving(x,y,&oldx,&oldy); - if (IN_SCR_FIELD(SCROLLX(oldx),SCROLLY(oldy))) - DrawScreenField(SCROLLX(oldx),SCROLLY(oldy)); + if (IN_SCR_FIELD(SCREENX(oldx),SCREENY(oldy))) + DrawScreenField(SCREENX(oldx),SCREENY(oldy)); } } @@ -1115,16 +1198,16 @@ void DrawMiniElement(int x, int y, int element) DrawMiniGraphic(x,y,graphic); } -void DrawMiniElementOrWall(int x, int y, int scroll_x, int scroll_y) +void DrawMiniElementOrWall(int sx, int sy, int scroll_x, int scroll_y) { - if (x+scroll_x<-1 || x+scroll_x>lev_fieldx || - y+scroll_y<-1 || y+scroll_y>lev_fieldy) - DrawMiniElement(x,y,EL_LEERRAUM); - else if (x+scroll_x==-1 || x+scroll_x==lev_fieldx || - y+scroll_y==-1 || y+scroll_y==lev_fieldy) - DrawMiniElement(x,y,EL_BETON); + int x = sx + scroll_x, y = sy + scroll_y; + + if (x<-1 || x>lev_fieldx || y<-1 || y>lev_fieldy) + DrawMiniElement(sx,sy,EL_LEERRAUM); + else if (x==-1 || x==lev_fieldx || y==-1 || y==lev_fieldy) + DrawMiniElement(sx,sy,EL_BETON); else - DrawMiniElement(x,y,Feld[x+scroll_x][y+scroll_y]); + DrawMiniElement(sx,sy,Feld[x][y]); } void DrawMicroElement(int xpos, int ypos, int element) @@ -1152,7 +1235,7 @@ void DrawLevel() for(y=BY1; y<=BY2; y++) DrawScreenField(x,y); - if (soft_scrolling_on) + if (setup.soft_scrolling) XCopyArea(display,fieldbuffer,backbuffer,gc, FX,FY, SXSIZE,SYSIZE, SX,SY); @@ -1209,7 +1292,7 @@ void DrawMicroLevel(int xpos, int ypos) redraw_mask |= REDRAW_MICROLEV; } -int AYS_in_range(int x, int y) +int REQ_in_range(int x, int y) { if (y>DY+249 && ystate)) @@ -1356,44 +1460,51 @@ BOOL AreYouSure(char *text, unsigned int ays_state) case XK_Return: result = 1; break; + case XK_Escape: result = 0; break; + + default: + break; } + if (req_state & REQ_PLAYER) + result = 0; break; + case KeyRelease: key_joystick_mapping = 0; break; - case FocusIn: - case FocusOut: - HandleFocusEvent((XFocusChangeEvent *) &event); - break; - case ClientMessage: - HandleClientMessageEvent((XClientMessageEvent *) &event); - break; + default: + HandleOtherEvents(&event); break; } } - else if (JoystickButton() == JOY_BUTTON_NEW_PRESSED) + else if (AnyJoystickButton() == JOY_BUTTON_NEW_PRESSED) { - int joy=Joystick(); + int joy = AnyJoystick(); if (joy & JOY_BUTTON_1) result = 1; else if (joy & JOY_BUTTON_2) result = 0; } + + DoAnimation(); + + /* don't eat all CPU time */ + Delay(10); } if (game_status != MAINMENU) StopAnimation(); - if (!(ays_state & AYS_STAY_OPEN)) + if (!(req_state & REQ_STAY_OPEN)) { CloseDoor(DOOR_CLOSE_1); - if (!(ays_state & AYS_STAY_CLOSED) && (old_door_state & DOOR_OPEN_1)) + if (!(req_state & REQ_STAY_CLOSED) && (old_door_state & DOOR_OPEN_1)) { XCopyArea(display,pix[PIX_DB_DOOR],pix[PIX_DB_DOOR],gc, DOOR_GFX_PAGEX2,DOOR_GFX_PAGEY1, DXSIZE,DYSIZE, @@ -1402,6 +1513,12 @@ BOOL AreYouSure(char *text, unsigned int ays_state) } } + /* continue network game after request */ + if (options.network && + game_status == PLAYING && + req_state & REQUEST_WAIT_FOR) + SendToServer_ContinuePlaying(); + return(result); } @@ -1447,7 +1564,7 @@ unsigned int MoveDoor(unsigned int door_state) static unsigned int door2 = DOOR_CLOSE_2; static long door_delay = 0; int x, start, stepsize = 2; - long door_delay_value = stepsize * 5000; + long door_delay_value = stepsize * 5; if (door_state == DOOR_GET_STATE) return(door1 | door2); @@ -1461,7 +1578,7 @@ unsigned int MoveDoor(unsigned int door_state) else if (door2==DOOR_CLOSE_2 && door_state & DOOR_CLOSE_2) door_state &= ~DOOR_CLOSE_2; - if (quick_doors) + if (setup.quick_doors) { stepsize = 20; door_delay_value = 0; @@ -1477,8 +1594,7 @@ unsigned int MoveDoor(unsigned int door_state) for(x=start; x<=DXSIZE; x+=stepsize) { - while(!DelayReached(&door_delay, door_delay_value/10000)) - Delay(1000); + WaitUntilDelayReached(&door_delay, door_delay_value); if (door_state & DOOR_ACTION_1) { @@ -1561,6 +1677,9 @@ unsigned int MoveDoor(unsigned int door_state) } } + if (setup.quick_doors) + StopSound(SND_OEFFNEN); + if (door_state & DOOR_ACTION_1) door1 = door_state & DOOR_ACTION_1; if (door_state & DOOR_ACTION_2) @@ -1672,6 +1791,9 @@ int el2gfx(int element) case EL_ZEIT_VOLL: return(GFX_ZEIT_VOLL); case EL_ZEIT_LEER: return(GFX_ZEIT_LEER); case EL_MAUER_LEBT: return(GFX_MAUER_LEBT); + case EL_MAUER_X: return(GFX_MAUER_X); + case EL_MAUER_Y: return(GFX_MAUER_Y); + case EL_MAUER_XY: return(GFX_MAUER_XY); case EL_EDELSTEIN_BD: return(GFX_EDELSTEIN_BD); case EL_EDELSTEIN_GELB: return(GFX_EDELSTEIN_GELB); case EL_EDELSTEIN_ROT: return(GFX_EDELSTEIN_ROT);