1
0
mirror of https://github.com/vcmi/vcmi.git synced 2025-02-15 13:33:36 +02:00

* Implemented rivers animation. Thanks to GrayFace for giving range of colors in palette to be shifted.

* Hopefully fixed all issues with bliwWithRotate functions family. If there are any artefacts on terrain drawing, let me know.
* Fixed drawing of objects shadows.
This commit is contained in:
Michał W. Urbańczyk 2009-12-22 21:53:50 +00:00
parent 9dad83590b
commit 6c4b4f21bc
13 changed files with 295 additions and 336 deletions

View File

@ -1979,12 +1979,20 @@ void CAdvMapInt::select(const CArmedInstance *sel )
if(vstd::contains(paths,h)) //hero has assigned path
{
CGPath &path = paths[h];
assert(h->getPosition(false) == path.startPos());
//update the hero path in case of something has changed on map
if(LOCPLINT->cb->getPath2(path.endPos(), path))
terrain.currentPath = &path;
else
if(!path.nodes.size())
{
tlog3 << "Warning: empty path found...\n";
paths.erase(h);
}
else
{
assert(h->getPosition(false) == path.startPos());
//update the hero path in case of something has changed on map
if(LOCPLINT->cb->getPath2(path.endPos(), path))
terrain.currentPath = &path;
else
paths.erase(h);
}
}
}
townList.draw(screen);

View File

@ -1299,11 +1299,6 @@ void CPlayerInterface::heroArtifactSetChanged(const CGHeroInstance*hero)
}
}
void CPlayerInterface::updateWater()
{
}
void CPlayerInterface::availableCreaturesChanged( const CGDwelling *town )
{
boost::unique_lock<boost::recursive_mutex> un(*pim);

View File

@ -192,7 +192,6 @@ public:
bool shiftPressed() const; //determines if shift key is pressed (left or right or both)
bool ctrlPressed() const; //determines if ctrl key is pressed (left or right or both)
void redrawHeroWin(const CGHeroInstance * hero);
void updateWater();
void showComp(SComponent comp); //TODO: comment me
void openTownWindow(const CGTownInstance * town); //shows townscreen
void openHeroWindow(const CGHeroInstance * hero); //shows hero window with given hero

View File

@ -498,17 +498,61 @@ void CSDL_Ext::alphaTransform(SDL_Surface *src)
}
// <=>
static void prepareOutRect(SDL_Rect &dst, const SDL_Rect *dstRect, const SDL_Rect *clip_rect)
static void prepareOutRect(SDL_Rect *src, SDL_Rect *dst, const SDL_Rect & clip_rect)
{
dst.x = std::max(dstRect->x,clip_rect->x);
dst.y = std::max(dstRect->y,clip_rect->y);
dst.w = std::max(0,std::min(dstRect->w - (dst.x - dstRect->x), clip_rect->x + clip_rect->w - dst.x));
dst.h = std::max(0,std::min(dstRect->h - (dst.y - dstRect->y), clip_rect->y + clip_rect->h - dst.y));
const int xoffset = std::max(clip_rect.x - dst->x, 0),
yoffset = std::max(clip_rect.y - dst->y, 0);
src->x += xoffset;
src->y += yoffset;
dst->x += xoffset;
dst->y += yoffset;
src->w = dst->w = std::max(0,std::min(dst->w - xoffset, clip_rect.x + clip_rect.w - dst->x));
src->h = dst->h = std::max(0,std::min(dst->h - yoffset, clip_rect.y + clip_rect.h - dst->y));
}
void CSDL_Ext::blitWithRotateClip(SDL_Surface *src,SDL_Rect * srcRect, SDL_Surface * dst, SDL_Rect * dstRect, ui8 rotation)//srcRect is not used, works with 8bpp sources and 24bpp dests
{
static void (*blitWithRotate[])(const SDL_Surface *, const SDL_Rect *, SDL_Surface *, const SDL_Rect *) = {blitWithRotate1, blitWithRotate2, blitWithRotate3};
if(!rotation)
{
SDL_BlitSurface(src, srcRect, dst, dstRect);
}
else
{
prepareOutRect(srcRect, dstRect, dst->clip_rect);
blitWithRotate[rotation-1](src, srcRect, dst, dstRect);
}
}
void CSDL_Ext::blitWithRotateClipVal( SDL_Surface *src,SDL_Rect srcRect, SDL_Surface * dst, SDL_Rect dstRect, ui8 rotation )
{
blitWithRotateClip(src, &srcRect, dst, &dstRect, rotation);
}
void CSDL_Ext::blitWithRotateClipWithAlpha(SDL_Surface *src,SDL_Rect * srcRect, SDL_Surface * dst, SDL_Rect * dstRect, ui8 rotation)//srcRect is not used, works with 8bpp sources and 24bpp dests
{
static void (*blitWithRotate[])(const SDL_Surface *, const SDL_Rect *, SDL_Surface *, const SDL_Rect *) = {blitWithRotate1WithAlpha, blitWithRotate2WithAlpha, blitWithRotate3WithAlpha};
if(!rotation)
{
blit8bppAlphaTo24bpp(src, srcRect, dst, dstRect);
}
else
{
prepareOutRect(srcRect, dstRect, dst->clip_rect);
blitWithRotate[rotation-1](src, srcRect, dst, dstRect);
}
}
void CSDL_Ext::blitWithRotateClipValWithAlpha( SDL_Surface *src,SDL_Rect srcRect, SDL_Surface * dst, SDL_Rect dstRect, ui8 rotation )
{
blitWithRotateClipWithAlpha(src, &srcRect, dst, &dstRect, rotation);
}
void CSDL_Ext::blitWithRotate1(const SDL_Surface *src, const SDL_Rect * srcRect, SDL_Surface * dst, const SDL_Rect * dstRect)//srcRect is not used, works with 8bpp sources and 24/32 bpp dests
{
Uint8 *sp = (Uint8 *)src->pixels;
Uint8 *sp = (Uint8 *)src->pixels + srcRect->y*src->pitch + (src->w - srcRect->w - srcRect->x);
const int bpp = dst->format->BytesPerPixel;
Uint8 *dporg = (Uint8 *)dst->pixels + dstRect->y*dst->pitch + (dstRect->x+dstRect->w)*bpp;
const SDL_Color * const colors = src->format->palette->colors;
@ -516,9 +560,6 @@ void CSDL_Ext::blitWithRotate1(const SDL_Surface *src, const SDL_Rect * srcRect,
for(int i=dstRect->h; i>0; i--, dporg += dst->pitch)
{
Uint8 *dp = dporg;
sp += src->w - dstRect->w;
for(int j=dstRect->w; j>0; j--, sp++)
{
if (bpp == 4)
@ -530,19 +571,14 @@ void CSDL_Ext::blitWithRotate1(const SDL_Surface *src, const SDL_Rect * srcRect,
*(--dp) = color.g;
*(--dp) = color.b;
}
}
}
void CSDL_Ext::blitWithRotate1clip(SDL_Surface *src,SDL_Rect * srcRect, SDL_Surface * dst, SDL_Rect * dstRect)//srcRect is not used, works with 8bpp sources and 24bpp dests
{
SDL_Rect realDest;
prepareOutRect(realDest,dstRect,&dst->clip_rect);
blitWithRotate1(src,srcRect,dst,&realDest);
sp += src->w - dstRect->w;
}
}
void CSDL_Ext::blitWithRotate2(const SDL_Surface *src, const SDL_Rect * srcRect, SDL_Surface * dst, const SDL_Rect * dstRect)//srcRect is not used, works with 8bpp sources and 24/32 bpp dests
{
Uint8 *sp = (Uint8 *)src->pixels;
Uint8 *sp = (Uint8 *)src->pixels + (src->h - srcRect->h - srcRect->y)*src->pitch + srcRect->x;
const int bpp = dst->format->BytesPerPixel;
Uint8 *dporg = (Uint8 *)dst->pixels + (dstRect->y + dstRect->h - 1)*dst->pitch + dstRect->x*bpp;
const SDL_Color * const colors = src->format->palette->colors;
@ -567,16 +603,102 @@ void CSDL_Ext::blitWithRotate2(const SDL_Surface *src, const SDL_Rect * srcRect,
}
}
void CSDL_Ext::blitWithRotate2clip(const SDL_Surface *src, const SDL_Rect * srcRect, SDL_Surface * dst, const SDL_Rect * dstRect)//srcRect is not used, works with 8bpp sources and 24bpp dests
{
SDL_Rect realDest;
prepareOutRect(realDest,dstRect,&dst->clip_rect);
blitWithRotate2(src,srcRect,dst,&realDest);
}
void CSDL_Ext::blitWithRotate3(const SDL_Surface *src, const SDL_Rect * srcRect, SDL_Surface * dst, const SDL_Rect * dstRect)//srcRect is not used, works with 8bpp sources and 24/32 bpp dests
{
Uint8 *sp = (Uint8 *)src->pixels;
Uint8 *sp = (Uint8 *)src->pixels + (src->h - srcRect->h - srcRect->y)*src->pitch + (src->w - srcRect->w - srcRect->x);
const int bpp = dst->format->BytesPerPixel;
Uint8 *dporg = (Uint8 *)dst->pixels +(dstRect->y + dstRect->h - 1)*dst->pitch + (dstRect->x+dstRect->w)*bpp;
const SDL_Color * const colors = src->format->palette->colors;
for(int i=dstRect->h; i>0; i--, dporg -= dst->pitch)
{
Uint8 *dp = dporg;
for(int j=dstRect->w; j>0; j--, sp++)
{
const SDL_Color color = colors[*sp];
if (bpp == 4)
*(--dp) = 0;
*(--dp) = color.r;
*(--dp) = color.g;
*(--dp) = color.b;
}
sp += src->w - dstRect->w;
}
}
void CSDL_Ext::blitWithRotate1WithAlpha(const SDL_Surface *src, const SDL_Rect * srcRect, SDL_Surface * dst, const SDL_Rect * dstRect)//srcRect is not used, works with 8bpp sources and 24/32 bpp dests
{
Uint8 *sp = (Uint8 *)src->pixels + srcRect->y*src->pitch + (src->w - srcRect->w - srcRect->x);
const int bpp = dst->format->BytesPerPixel;
Uint8 *dporg = (Uint8 *)dst->pixels + dstRect->y*dst->pitch + (dstRect->x+dstRect->w)*bpp;
const SDL_Color * const colors = src->format->palette->colors;
for(int i=dstRect->h; i>0; i--, dporg += dst->pitch)
{
Uint8 *dp = dporg;
for(int j=dstRect->w; j>0; j--, sp++)
{
if(*sp)
{
if (bpp == 4)
*(--dp) = 0;
const SDL_Color color = colors[*sp];
*(--dp) = color.r;
*(--dp) = color.g;
*(--dp) = color.b;
}
else
{
dp -= bpp;
}
}
sp += src->w - dstRect->w;
}
}
void CSDL_Ext::blitWithRotate2WithAlpha(const SDL_Surface *src, const SDL_Rect * srcRect, SDL_Surface * dst, const SDL_Rect * dstRect)//srcRect is not used, works with 8bpp sources and 24/32 bpp dests
{
Uint8 *sp = (Uint8 *)src->pixels + (src->h - srcRect->h - srcRect->y)*src->pitch + srcRect->x;
const int bpp = dst->format->BytesPerPixel;
Uint8 *dporg = (Uint8 *)dst->pixels + (dstRect->y + dstRect->h - 1)*dst->pitch + dstRect->x*bpp;
const SDL_Color * const colors = src->format->palette->colors;
for(int i=dstRect->h; i>0; i--, dporg -= dst->pitch)
{
Uint8 *dp = dporg;
for(int j=dstRect->w; j>0; j--, sp++)
{
if(*sp)
{
const SDL_Color color = colors[*sp];
*(dp++) = color.b;
*(dp++) = color.g;
*(dp++) = color.r;
if (bpp == 4)
*(dp++) = 0;
}
else
{
dp += bpp;
}
}
sp += src->w - dstRect->w;
}
}
void CSDL_Ext::blitWithRotate3WithAlpha(const SDL_Surface *src, const SDL_Rect * srcRect, SDL_Surface * dst, const SDL_Rect * dstRect)//srcRect is not used, works with 8bpp sources and 24/32 bpp dests
{
Uint8 *sp = (Uint8 *)src->pixels + (src->h - srcRect->h - srcRect->y)*src->pitch + (src->w - srcRect->w - srcRect->x);
const int bpp = dst->format->BytesPerPixel;
Uint8 *dporg = (Uint8 *)dst->pixels +(dstRect->y + dstRect->h - 1)*dst->pitch + (dstRect->x+dstRect->w)*bpp;
const SDL_Color * const colors = src->format->palette->colors;
@ -584,28 +706,27 @@ void CSDL_Ext::blitWithRotate3(const SDL_Surface *src, const SDL_Rect * srcRect,
for(int i=dstRect->h; i>0; i--, dporg -= dst->pitch)
{
Uint8 *dp = dporg;
sp += src->w - dstRect->w;
for(int j=dstRect->w; j>0; j--, sp++)
{
const SDL_Color color = colors[*sp];
if(*sp)
{
const SDL_Color color = colors[*sp];
if (bpp == 4)
*(--dp) = 0;
if (bpp == 4)
*(--dp) = 0;
*(--dp) = color.r;
*(--dp) = color.g;
*(--dp) = color.b;
*(--dp) = color.r;
*(--dp) = color.g;
*(--dp) = color.b;
}
else
{
dp -= bpp;
}
}
}
}
void CSDL_Ext::blitWithRotate3clip(SDL_Surface *src,SDL_Rect * srcRect, SDL_Surface * dst, SDL_Rect * dstRect)//srcRect is not used, works with 8bpp sources and 24bpp dests
{
SDL_Rect realDest;
prepareOutRect(realDest,dstRect,&dst->clip_rect);
blitWithRotate3(src,srcRect,dst,&realDest);
sp += src->w - dstRect->w;
}
}
int CSDL_Ext::blit8bppAlphaTo24bpp(const SDL_Surface * src, const SDL_Rect * srcRect, SDL_Surface * dst, SDL_Rect * dstRect)

View File

@ -101,12 +101,19 @@ namespace CSDL_Ext
Uint32 SDL_GetPixel(SDL_Surface *surface, const int & x, const int & y, bool colorByte = false);
SDL_Color SDL_GetPixelColor(SDL_Surface *surface, int x, int y); //returns color of pixel at given position
void alphaTransform(SDL_Surface * src); //adds transparency and shadows (partial handling only; see examples of using for details)
void blitWithRotate1(const SDL_Surface *src, const SDL_Rect * srcRect, SDL_Surface * dst, const SDL_Rect * dstRect);//srcRect is not used, works with 8bpp sources and 24bpp dests
void blitWithRotate2(const SDL_Surface *src, const SDL_Rect * srcRect, SDL_Surface * dst, const SDL_Rect * dstRect);//srcRect is not used, works with 8bpp sources and 24bpp dests
void blitWithRotate3(const SDL_Surface *src, const SDL_Rect * srcRect, SDL_Surface * dst, const SDL_Rect * dstRect);//srcRect is not used, works with 8bpp sources and 24bpp dests
void blitWithRotate1clip(SDL_Surface *src,SDL_Rect * srcRect, SDL_Surface * dst, SDL_Rect * dstRect);//srcRect is not used, works with 8bpp sources and 24bpp dests preserving clip_rect
void blitWithRotate2clip(const SDL_Surface *src, const SDL_Rect * srcRect, SDL_Surface * dst, const SDL_Rect * dstRect);//srcRect is not used, works with 8bpp sources and 24bpp dests preserving clip_rect
void blitWithRotate3clip(SDL_Surface *src,SDL_Rect * srcRect, SDL_Surface * dst, SDL_Rect * dstRect);//srcRect is not used, works with 8bpp sources and 24bpp dests preserving clip_rect
void blitWithRotateClip(SDL_Surface *src,SDL_Rect * srcRect, SDL_Surface * dst, SDL_Rect * dstRect, ui8 rotation);//srcRect is not used, works with 8bpp sources and 24bpp dests preserving clip_rect
void blitWithRotateClipVal(SDL_Surface *src,SDL_Rect srcRect, SDL_Surface * dst, SDL_Rect dstRect, ui8 rotation);//srcRect is not used, works with 8bpp sources and 24bpp dests preserving clip_rect
void blitWithRotate1WithAlpha(const SDL_Surface *src, const SDL_Rect * srcRect, SDL_Surface * dst, const SDL_Rect * dstRect);//srcRect is not used, works with 8bpp sources and 24bpp dests
void blitWithRotate2WithAlpha(const SDL_Surface *src, const SDL_Rect * srcRect, SDL_Surface * dst, const SDL_Rect * dstRect);//srcRect is not used, works with 8bpp sources and 24bpp dests
void blitWithRotate3WithAlpha(const SDL_Surface *src, const SDL_Rect * srcRect, SDL_Surface * dst, const SDL_Rect * dstRect);//srcRect is not used, works with 8bpp sources and 24bpp dests
void blitWithRotateClipWithAlpha(SDL_Surface *src,SDL_Rect * srcRect, SDL_Surface * dst, SDL_Rect * dstRect, ui8 rotation);//srcRect is not used, works with 8bpp sources and 24bpp dests preserving clip_rect
void blitWithRotateClipValWithAlpha(SDL_Surface *src,SDL_Rect srcRect, SDL_Surface * dst, SDL_Rect dstRect, ui8 rotation);//srcRect is not used, works with 8bpp sources and 24bpp dests preserving clip_rect
int blit8bppAlphaTo24bpp(const SDL_Surface * src, const SDL_Rect * srcRect, SDL_Surface * dst, SDL_Rect * dstRect); //blits 8 bpp surface with alpha channel to 24 bpp surface
Uint32 colorToUint32(const SDL_Color * color); //little endian only

View File

@ -117,6 +117,7 @@
/>
<Tool
Name="VCCLCompilerTool"
AdditionalOptions="/MP4"
Optimization="3"
EnableIntrinsicFunctions="true"
FavorSizeOrSpeed="1"

View File

@ -55,6 +55,7 @@ void CDefObjInfoHandler::load()
nobj->blockMap[o] = 0xff;
nobj->visitMap[o] = 0x00;
nobj->coverageMap[o] = 0x00;
nobj->shadowCoverage[o] = 0x00;
}
inp>>mapStr;
std::reverse(mapStr.begin(), mapStr.end());
@ -107,6 +108,7 @@ void CDefObjInfoHandler::load()
for(int i=0; i<6; ++i)
{
nobj->coverageMap[i] = msk[i+2];
nobj->shadowCoverage[i] = msk[i+8];
}

View File

@ -23,7 +23,7 @@ public:
ui8 visitMap[6];
ui8 blockMap[6];
ui8 coverageMap[6]; //to determine which tiles are covered by picture of this object
ui8 coverageMap[6], shadowCoverage[6]; //to determine which tiles are covered by picture of this object
ui8 visitDir; //directions from which object can be entered, format same as for moveDir in CGHeroInstance(but 0 - 7)
si32 id, subid; //of object described by this defInfo
si32 serial;
@ -44,7 +44,7 @@ public:
template <typename Handler> void serialize(Handler &h, const int version)
{
h & name & serial & visitMap & blockMap & visitDir & id & subid &terrainAllowed
& terrainMenu & width & height & type & printPriority & coverageMap;
& terrainMenu & width & height & type & printPriority & coverageMap & shadowCoverage;
}
CGDefInfo();
};

View File

@ -316,7 +316,8 @@ bool CGObjectInstance::blockingAt(int x, int y) const
bool CGObjectInstance::coveringAt(int x, int y) const
{
if((defInfo->coverageMap[y] >> (7-(x) )) & 1)
if((defInfo->coverageMap[y] >> (7-(x) )) & 1
|| (defInfo->shadowCoverage[y] >> (7-(x) )) & 1)
return true;
return false;
}
@ -786,6 +787,7 @@ void CGHeroInstance::initHeroDefInfo()
defInfo->blockMap[i] = 255;
defInfo->visitMap[i] = 0;
defInfo->coverageMap[i] = 0;
defInfo->shadowCoverage[i] = 0;
}
defInfo->handler=NULL;
defInfo->blockMap[5] = 253;

View File

@ -1396,6 +1396,7 @@ void Mapa::readDefInfo( const unsigned char * bufor, int &i)
for(int i=0; i<6; ++i)
{
vinya->coverageMap[i] = msk[i+2];
vinya->shadowCoverage[i] = msk[i+8];
}
defy.push_back(vinya); // add this def to the vector

View File

@ -72,9 +72,9 @@ struct DLL_EXPORT TerrainTile
EterrainType tertype; // type of terrain
unsigned char terview; // look of terrain
Eriver nuine; // type of Eriver (0 if there is no Eriver)
Eriver nuine; // type of Eriver (0 if there is no river)
unsigned char rivDir; // direction of Eriver
Eroad malle; // type of Eroad (0 if there is no Eriver)
Eroad malle; // type of Eroad (0 if there is no river)
unsigned char roadDir; // direction of Eroad
unsigned char siodmyTajemniczyBajt; //bitfield, info whether this tile is coastal and how to rotate tile graphics

View File

@ -175,7 +175,7 @@ void CMapHandler::roadsRiverTerrainInit()
ttiles[i][j].resize(CGI->mh->map->twoLevel+1, 0, 0);
}
// Draw the map
// prepare the map
for (int i=0; i<map->width; i++) //by width
{
for (int j=0; j<map->height;j++) //by height
@ -185,74 +185,6 @@ void CMapHandler::roadsRiverTerrainInit()
TerrainTile2 &pom(ttiles[i][j][k]);
pom.pos = int3(i, j, k);
pom.tileInfo = &(map->terrain[i][j][k]);
if(pom.tileInfo->malle)
{
bool rotV, rotH;
int roadpom = pom.tileInfo->malle-1,
impom = pom.tileInfo->roadDir;
SDL_Surface *bitmap = roadDefs[roadpom]->ourImages[impom].bitmap;
rotH = (pom.tileInfo->siodmyTajemniczyBajt >> 5) & 1;
rotV = (pom.tileInfo->siodmyTajemniczyBajt >> 4) & 1;
if(rotH || rotV)
{
if(rotH)
bitmap = CSDL_Ext::hFlip(bitmap);
if(rotV)
{
SDL_Surface *bitmap2 = CSDL_Ext::rotate01(bitmap);
if (rotH)
// bitmap is already a duplicated surface
SDL_FreeSurface(bitmap);
bitmap = bitmap2;
}
CSDL_Ext::alphaTransform(bitmap);
}
ttiles[i][j][k].roadbitmap.push_back(bitmap);
}
}
}
}
for (int i=0; i<map->width; i++) //by width
{
for (int j=0; j<map->height;j++) //by height
{
for(int k=0; k<=map->twoLevel; ++k) //by levels
{
if(map->terrain[i][j][k].nuine)
{
bool rotH, rotV;
SDL_Surface *bitmap = staticRiverDefs[map->terrain[i][j][k].nuine-1]->ourImages[map->terrain[i][j][k].rivDir].bitmap;
rotH = (map->terrain[i][j][k].siodmyTajemniczyBajt >> 3) & 1;
rotV = (map->terrain[i][j][k].siodmyTajemniczyBajt >> 2) & 1;
if(rotH || rotV)
{
if(rotH)
bitmap = CSDL_Ext::hFlip(bitmap);
if(rotV)
{
SDL_Surface *bitmap2 = CSDL_Ext::rotate01(bitmap);
if (rotH)
// bitmap is already a duplicated surface
SDL_FreeSurface(bitmap);
bitmap = bitmap2;
}
CSDL_Ext::alphaTransform(bitmap);
}
ttiles[i][j][k].rivbitmap.push_back(bitmap);
}
}
}
}
@ -517,10 +449,12 @@ void CMapHandler::terrainRect(int3 top_tile, unsigned char anim, const std::vect
int srx, sry; // absolute screen coordinates in pixels
// If moving, we need to add an extra column/line
if (moveX != 0) {
if (moveX != 0)
{
dx++;
srx_init += moveX;
if (moveX > 0) {
if (moveX > 0)
{
// Moving right. We still need to draw the old tile on the
// left, so adjust our referential
top_tile.x --;
@ -528,10 +462,12 @@ void CMapHandler::terrainRect(int3 top_tile, unsigned char anim, const std::vect
}
}
if (moveY != 0) {
if (moveY != 0)
{
dy++;
sry_init += moveY;
if (moveY > 0) {
if (moveY > 0)
{
// Moving down. We still need to draw the tile on the top,
// so adjust our referential.
top_tile.y --;
@ -556,12 +492,6 @@ void CMapHandler::terrainRect(int3 top_tile, unsigned char anim, const std::vect
SDL_GetClipRect(extSurf, &prevClip);
SDL_SetClipRect(extSurf, extRect); //preventing blitting outside of that rect
// Temp surface for rotating tile and then properly blit. The
// problem is that blitWithRotate1clip & co do not respect the
// previous SDL_SetClipRect.
// TODO: optimize by pre-rotating those surfaces
SDL_Surface *rSurf = CSDL_Ext::newSurface(32, 32, extSurf);
// printing terrain
srx = srx_init;
@ -575,140 +505,37 @@ void CMapHandler::terrainRect(int3 top_tile, unsigned char anim, const std::vect
for (int by=0; by < dy; by++, sry+=32)
{
int3 pos(top_tile.x+bx, top_tile.y+by, top_tile.z); //blitted tile position
// Skip tile if not in map
if (top_tile.y+by < 0 || top_tile.y+by >= map->height)
if (pos.y < 0 || pos.y >= map->height)
continue;
const TerrainTile2 & tile = ttiles[top_tile.x+bx][top_tile.y+by][top_tile.z];
SDL_Rect sr;
const TerrainTile2 & tile = ttiles[pos.x][pos.y][pos.z];
const TerrainTile &tinfo = *tile.tileInfo;
SDL_Rect sr;
sr.x=srx;
sr.y=sry;
sr.h=sr.w=32;
if(tile.terbitmap)
{
//blit terrain with river/road
if(tile.terbitmap) //if custom terrain graphic - use it
SDL_BlitSurface(tile.terbitmap, &genRect(sr.h, sr.w, 0, 0), extSurf, &sr);
}
else
{
switch(tile.tileInfo->siodmyTajemniczyBajt%4)
{
case 0:
SDL_BlitSurface(terrainGraphics[tile.tileInfo->tertype][tile.tileInfo->terview],
&rtile, extSurf, &sr);
break;
case 1:
CSDL_Ext::blitWithRotate1clip(terrainGraphics[tile.tileInfo->tertype][tile.tileInfo->terview],
&rtile, rSurf, &rtile);
SDL_BlitSurface(rSurf, &rtile, extSurf, &sr);
break;
case 2:
CSDL_Ext::blitWithRotate2clip(terrainGraphics[tile.tileInfo->tertype][tile.tileInfo->terview],
&rtile, rSurf, &rtile);
SDL_BlitSurface(rSurf, &rtile, extSurf, &sr);
break;
default:
CSDL_Ext::blitWithRotate3clip(terrainGraphics[tile.tileInfo->tertype][tile.tileInfo->terview],
&rtile, rSurf, &rtile);
SDL_BlitSurface(rSurf, &rtile, extSurf, &sr);
break;
}
}
}
}
// terrain printed
// printing rivers
srx = srx_init;
for (int bx = 0; bx<dx; bx++, srx+=32)
{
// Skip column if not in map
if (top_tile.x+bx < 0 || top_tile.x+bx >= map->width)
continue;
sry = sry_init;
for (int by= 0; by<dy; by++, sry+=32)
{
// Skip tile if not in map
if (top_tile.y+by < 0 || top_tile.y+by >= map->height)
continue;
SDL_Rect sr;
sr.x=srx;
sr.y=sry;
sr.h=sr.w=32;
const std::vector<SDL_Surface *> &rivbitmap = ttiles[top_tile.x+bx][top_tile.y+by][top_tile.z].rivbitmap;
if(rivbitmap.size())
{
CSDL_Ext::blit8bppAlphaTo24bpp(rivbitmap[anim%rivbitmap.size()],&genRect(sr.h, sr.w, 0, 0),extSurf,&sr);
}
}
}
// rivers printed
// printing roads
srx = srx_init;
for (int bx = 0; bx < dx; bx++, srx+=32)
{
// Skip column if not in map
if (top_tile.x+bx < 0 || top_tile.x+bx >= map->width)
continue;
sry = sry_init + 16;
for (int by = 0; by < dy; by++, sry+=32)
{
// Skip tile if not in map
if (top_tile.y+by < 0 || top_tile.y+by >= map->height)
continue;
SDL_Rect sr;
sr.x = srx;
sr.y = sry;
sr.h=sr.w=32;
const std::vector<SDL_Surface *> &roadbitmap = ttiles[top_tile.x+bx][top_tile.y+by][top_tile.z].roadbitmap;
if(roadbitmap.size())
{
CSDL_Ext::blit8bppAlphaTo24bpp(roadbitmap[anim%roadbitmap.size()], &genRect(sr.h, sr.w, 0, (by==-1 && moveY == 0 ? 16 : 0)),extSurf,&sr);
}
}
}
// roads printed
// printing objects
srx = srx_init;
for (int bx = 0; bx<dx; bx++, srx+=32)
{
// Skip column if not in map
if (top_tile.x+bx < 0 || top_tile.x+bx >= map->width)
continue;
sry = sry_init;
for (int by = 0; by<dy; by++, sry+=32)
{
// Skip tile if not in map
if (top_tile.y+by < 0 || top_tile.y+by >= map->height)
continue;
std::vector < std::pair<const CGObjectInstance*,SDL_Rect> > &objects =
ttiles[top_tile.x+bx][top_tile.y+by][top_tile.z].objects;
else //use default terrain graphic
CSDL_Ext::blitWithRotateClipVal(terrainGraphics[tinfo.tertype][tinfo.terview],rtile, extSurf, sr, tinfo.siodmyTajemniczyBajt%4);
if(tinfo.nuine) //print river if present
CSDL_Ext::blitWithRotateClipValWithAlpha(staticRiverDefs[tinfo.nuine-1]->ourImages[tinfo.rivDir].bitmap,rtile, extSurf, sr, (tinfo.siodmyTajemniczyBajt>>2)%4);
if(tinfo.malle) //print road if present
CSDL_Ext::blitWithRotateClipValWithAlpha(roadDefs[tinfo.malle-1]->ourImages[tinfo.roadDir].bitmap,rtile, extSurf, sr, (tinfo.siodmyTajemniczyBajt>>4)%4);
//blit objects
const std::vector < std::pair<const CGObjectInstance*,SDL_Rect> > &objects = tile.objects;
for(int h=0; h < objects.size(); ++h)
{
const CGObjectInstance *obj = objects[h].first;
ui8 color = obj->tempOwner;
//checking if object has non-empty graphic on this tile
if(obj->ID != HEROI_TYPE && !obj->coveringAt(obj->pos.x - (top_tile.x + bx), top_tile.y + by - obj->pos.y + 5))
continue;
@ -717,10 +544,7 @@ void CMapHandler::terrainRect(int3 top_tile, unsigned char anim, const std::vect
if(puzzleMode && obj->tempOwner != 254)
continue;
SDL_Rect sr;
sr.x = srx;
sr.y = sry;
sr.w = sr.h = 32;
SDL_Rect sr2(sr);
SDL_Rect pp = objects[h].second;
pp.h = sr.h;
@ -738,7 +562,7 @@ void CMapHandler::terrainRect(int3 top_tile, unsigned char anim, const std::vect
std::vector<Cimage> * iv = NULL;
std::vector<CDefEssential *> Graphics::*flg = NULL;
SDL_Surface * tb; //surface to blitted
if(themp) //hero
{
dir = themp->moveDir;
@ -783,12 +607,12 @@ void CMapHandler::terrainRect(int3 top_tile, unsigned char anim, const std::vect
break;
}
}
CSDL_Ext::blit8bppAlphaTo24bpp(tb,&pp,extSurf,&sr);
CSDL_Ext::blit8bppAlphaTo24bpp(tb,&pp,extSurf,&sr2);
//printing flag
pp.y+=IMGVAL*2-32;
sr.y-=16;
SDL_BlitSurface((graphics->*flg)[color]->ourImages[gg+heroAnim%IMGVAL+35].bitmap, &pp, extSurf, &sr);
sr2.y-=16;
SDL_BlitSurface((graphics->*flg)[color]->ourImages[gg+heroAnim%IMGVAL+35].bitmap, &pp, extSurf, &sr2);
}
else //hero / boat stands still
{
@ -801,14 +625,14 @@ void CMapHandler::terrainRect(int3 top_tile, unsigned char anim, const std::vect
break;
}
}
CSDL_Ext::blit8bppAlphaTo24bpp(tb,&pp,extSurf,&sr);
CSDL_Ext::blit8bppAlphaTo24bpp(tb,&pp,extSurf,&sr2);
//printing flag
if(flg
&& obj->pos.x == top_tile.x + bx
&& obj->pos.y == top_tile.y + by)
{
SDL_Rect bufr = sr;
SDL_Rect bufr = sr2;
bufr.x-=2*32;
bufr.y-=1*32;
bufr.h = 64;
@ -826,52 +650,15 @@ void CMapHandler::terrainRect(int3 top_tile, unsigned char anim, const std::vect
//setting appropriate flag color
if(color < 8 || color==255)
CSDL_Ext::setPlayerColor(bitmap, color);
CSDL_Ext::blit8bppAlphaTo24bpp(bitmap,&pp,extSurf,&sr);
CSDL_Ext::blit8bppAlphaTo24bpp(bitmap,&pp,extSurf,&sr2);
}
}
//objects blitted
}
}
// objects printed
// terrain printed
// printing shadow
if(!puzzleMode)
{
srx = srx_init;
for (int bx = 0; bx<dx; bx++, srx+=32)
{
// Skip column if not in map
if (top_tile.x+bx < 0 || top_tile.x+bx >= map->width)
continue;
sry = sry_init;
for (int by = 0; by<dy; by++, sry+=32)
{
// Skip tile if not in map
if (top_tile.y+by < 0 || top_tile.y+by >= map->height)
continue;
SDL_Rect sr;
sr.x = srx;
sr.y = sry;
sr.h = sr.w = 32;
if (top_tile.x+bx >= 0 &&
top_tile.y+by >= 0 &&
top_tile.x+bx < CGI->mh->map->width &&
top_tile.y+by < CGI->mh->map->height &&
!(*visibilityMap)[top_tile.x+bx][top_tile.y+by][top_tile.z])
{
SDL_Surface * hide = getVisBitmap(top_tile.x+bx, top_tile.y+by, *visibilityMap, top_tile.z);
CSDL_Ext::blit8bppAlphaTo24bpp(hide, &rtile, extSurf, &sr);
}
}
}
}
// shadow printed
// printing borders
srx = srx_init;
@ -882,21 +669,38 @@ void CMapHandler::terrainRect(int3 top_tile, unsigned char anim, const std::vect
for (int by = 0; by<dy; by++, sry+=32)
{
if (top_tile.x+bx < 0 || top_tile.x+bx >= map->width ||
top_tile.y+by < 0 || top_tile.y+by >= map->height) {
int3 pos(top_tile.x+bx, top_tile.y+by, top_tile.z); //blitted tile position
SDL_Rect sr;
SDL_Rect sr;
sr.x=srx;
sr.y=sry;
sr.h=sr.w=32;
sr.x=srx;
sr.y=sry;
sr.h=sr.w=32;
if (pos.x < 0 || pos.x >= map->width ||
pos.y < 0 || pos.y >= map->height)
{
SDL_BlitSurface(ttiles[top_tile.x+bx][top_tile.y+by][top_tile.z].terbitmap,
SDL_BlitSurface(ttiles[pos.x][pos.y][top_tile.z].terbitmap,
&genRect(sr.h, sr.w, 0, 0),extSurf,&sr);
} else {
}
else
{
//blitting Fog of War
if (pos.x >= 0 &&
pos.y >= 0 &&
pos.x < CGI->mh->map->width &&
pos.y < CGI->mh->map->height &&
!(*visibilityMap)[pos.x][pos.y][top_tile.z])
{
SDL_Surface * hide = getVisBitmap(pos.x, pos.y, *visibilityMap, top_tile.z);
CSDL_Ext::blit8bppAlphaTo24bpp(hide, &rtile, extSurf, &sr);
}
//FoW blitted
// TODO: these should be activable by the console
#ifdef MARK_BLOCKED_POSITIONS
if(ttiles[top_tile.x+bx][top_tile.y+by][top_tile.z].tileInfo->blocked) //temporary hiding blocked positions
if(ttiles[pos.x][pos.y][top_tile.z].tileInfo->blocked) //temporary hiding blocked positions
{
SDL_Rect sr;
@ -909,7 +713,7 @@ void CMapHandler::terrainRect(int3 top_tile, unsigned char anim, const std::vect
}
#endif
#ifdef MARK_VISITABLE_POSITIONS
if(ttiles[top_tile.x+bx][top_tile.y+by][top_tile.z].tileInfo->visitable) //temporary hiding visitable positions
if(ttiles[pos.x][pos.y][top_tile.z].tileInfo->visitable) //temporary hiding visitable positions
{
SDL_Rect sr;
@ -1026,8 +830,6 @@ void CMapHandler::terrainRect(int3 top_tile, unsigned char anim, const std::vect
//sepia / gray effect applied
SDL_SetClipRect(extSurf, &prevClip); //restoring clip_rect
SDL_FreeSurface(rSurf);
}
SDL_Surface * CMapHandler::getVisBitmap(int x, int y, const std::vector< std::vector< std::vector<unsigned char> > > & visibilityMap, int lvl)
@ -1487,21 +1289,44 @@ unsigned char CMapHandler::getDir(const int3 &a, const int3 &b)
return -2; //shouldn't happen
}
void shiftColors(SDL_Surface *img, int from, int howMany) //shifts colors in palette
{
//works with at most 16 colors, if needed more -> increase values
assert(howMany < 16);
SDL_Color palette[16];
for(int i=0; i<howMany; ++i)
{
palette[(i+1)%howMany] =img->format->palette->colors[from + i];
}
SDL_SetColors(img,palette,from,howMany);
}
void CMapHandler::updateWater() //shift colors in palettes of water tiles
{
SDL_Color palette[14];
for(size_t j=0; j < terrainGraphics[7].size(); ++j)
{
shiftColors(terrainGraphics[7][j],246, 9);
}
for(size_t j=0; j < terrainGraphics[8].size(); ++j)
{
for(int i=0; i<12; ++i)
{
palette[(i+1)%12] = terrainGraphics[8][j]->format->palette->colors[229 + i];
}
SDL_SetColors(terrainGraphics[8][j],palette,229,12);
for(int i=0; i<14; ++i)
{
palette[(i+1)%14] = terrainGraphics[8][j]->format->palette->colors[242 + i];
}
SDL_SetColors(terrainGraphics[8][j],palette,242,14);
shiftColors(terrainGraphics[8][j],229, 12);
shiftColors(terrainGraphics[8][j],242, 14);
}
for(size_t j=0; j < staticRiverDefs[0]->ourImages.size(); ++j)
{
shiftColors(staticRiverDefs[0]->ourImages[j].bitmap,183, 12);
shiftColors(staticRiverDefs[0]->ourImages[j].bitmap,195, 6);
}
for(size_t j=0; j < staticRiverDefs[2]->ourImages.size(); ++j)
{
shiftColors(staticRiverDefs[2]->ourImages[j].bitmap,228, 12);
shiftColors(staticRiverDefs[2]->ourImages[j].bitmap,183, 6);
shiftColors(staticRiverDefs[2]->ourImages[j].bitmap,240, 6);
}
for(size_t j=0; j < staticRiverDefs[3]->ourImages.size(); ++j)
{
shiftColors(staticRiverDefs[3]->ourImages[j].bitmap,240, 9);
}
}

View File

@ -29,9 +29,7 @@ struct TerrainTile2
{
int3 pos;
const TerrainTile *tileInfo;
SDL_Surface * terbitmap; //frames of terrain animation
std::vector<SDL_Surface *> rivbitmap; //frames of river animation
std::vector<SDL_Surface *> roadbitmap; //frames of road animation
SDL_Surface * terbitmap; //bitmap of terrain
std::vector < std::pair<const CGObjectInstance*,SDL_Rect> > objects; //pointers to objects being on this tile with rects to be easier to blit this tile on screen
TerrainTile2();