Skip to content

Commit fa1452c

Browse files
authored
Add: Support alternative sprites for RTL languages. (#46)
1 parent 12147ff commit fa1452c

File tree

6 files changed

+17
-8
lines changed

6 files changed

+17
-8
lines changed

docs/grf.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -121,6 +121,7 @@ Normal sprites
121121
1 2 Pixel format contains alpha component.
122122
2 4 Pixel format contains mask/palette component.
123123
3 8 Has transparency (i.e. is a tile), see below.
124+
4 10h Alternative sprite for right-to-left languages.
124125
6 40h The exact size of this sprite is significant. If not set,
125126
grfcodec may attempt to remove extraneous transparent pixels.
126127
others Undefined.

src/info.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -223,6 +223,7 @@ void infowriter::flush()
223223
zoom_levels[s->info.zoom]);
224224
if (HASTRANSPARENCY(s->info.info)) fputs(" chunked", info);
225225
if (DONOTCROP(s->info.info)) fputs(" nocrop", info);
226+
if (ISRTL(s->info.info)) fputs(" rtl", info);
226227
}
227228
} else {
228229
fprintf(info, "%s %d %d %02X %d %d %d %d",

src/nforenum.cpp

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -76,11 +76,14 @@ nfe_map nfo_escapes;
7676
#endif
7777

7878
struct RealSpriteFormat{
79+
bool rtl;
7980
bool bpp32;
8081
int zoom;
8182

8283
bool operator<(const RealSpriteFormat&other)const{
83-
return bpp32==other.bpp32?zoom<other.zoom:other.bpp32;
84+
if (rtl != other.rtl) return other.rtl;
85+
if (bpp32 != other.bpp32) return other.bpp32;
86+
return zoom < other.zoom;
8487
}
8588
};
8689

@@ -670,14 +673,16 @@ bool verify_real(std::string&data,RealSpriteState&formats){
670673
else { IssueMessage(0,REAL_MISSING_DATA,"zoom"); return COMMENTOFF(); }
671674

672675
std::string flag;
673-
bool chunked = false, nocrop=false;
676+
bool chunked = false, nocrop = false, rtl = false;
674677
while (!extract_string(meta,flag,processed,anyprocessing)) {
675678
if (!chunked&&flag=="chunked") chunked = true;
676679
else if (!nocrop&&flag=="nocrop") nocrop = true;
680+
else if (!rtl&&flag=="rtl") rtl = true;
677681
else { IssueMessage(0,REAL_UNKNOWN_FLAG,flag.c_str()); return COMMENTOFF(); }
678682
}
679683

680684
RealSpriteFormat format;
685+
format.rtl = rtl;
681686
format.bpp32 = depth=="32bpp";
682687
format.zoom = zoom;
683688

src/readinfo.cpp

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -200,8 +200,8 @@ void Real::AddSprite(size_t sprite,int infover,const std::string&data){
200200
inf.yrel = S16(ry);
201201
}else{
202202
int sx,sy,rx,ry;
203-
char depth[8],zoom[8],flags[2][8];
204-
int read = sscanf(meta,"%7s %d %d %d %d %d %d %7s %7s %7s",depth,&inf.xpos,&inf.ypos,&sx,&sy,&rx,&ry,zoom,flags[0],flags[1]);
203+
char depth[8],zoom[8],flags[3][8];
204+
int read = sscanf(meta,"%7s %d %d %d %d %d %d %7s %7s %7s %7s",depth,&inf.xpos,&inf.ypos,&sx,&sy,&rx,&ry,zoom,flags[0],flags[1],flags[2]);
205205
if(strcmp(depth,"mask")==0?read!=3:read < 8){
206206
throw Sprite::unparseable("Insufficient meta-data",sprite);
207207
}
@@ -236,6 +236,7 @@ void Real::AddSprite(size_t sprite,int infover,const std::string&data){
236236
/* Comment. */
237237
if (*flag == '#' || *flag == '/' || *flag == ';') break;
238238
if (strcmp(flag,"chunked")==0)inf.info|=8;
239+
else if (strcmp(flag,"rtl")==0)inf.info|=16;
239240
else if (strcmp(flag,"nocrop")==0)inf.info|=64;
240241
else throw Sprite::unparseable("invalid flag",sprite);
241242
}

src/sprites.cpp

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -177,14 +177,14 @@ void SpriteInfo::writetobuffer(U8 *buffer, int grfcontversion)
177177
{
178178
int i = 0;
179179
if (grfcontversion == 2) {
180-
/* Copy bits 3 and 6 of the nfo and make it, for now, an 8bpp normal GRF. */
180+
/* Copy bits 3, 4, 6 of the nfo and make it, for now, an 8bpp normal GRF. */
181181
U8 img=0;
182182
switch(this->depth){
183183
case DEPTH_8BPP: img=0x04; break;
184184
case DEPTH_32BPP: img=0x03; break;
185185
case DEPTH_MASK: img=0x07; break;
186186
}
187-
buffer[i++] = img | (this->info & (1 << 3 | 1 << 6));
187+
buffer[i++] = img | (this->info & (1 << 3 | 1 << 4 | 1 << 6));
188188
buffer[i++] = this->zoom;
189189
buffer[i++] = this->ydim & 0xFF;
190190
buffer[i++] = this->ydim >> 8;
@@ -204,8 +204,8 @@ void SpriteInfo::readfromfile(const char *action, int grfcontversion, FILE *grf,
204204
{
205205
if (grfcontversion == 2) {
206206
U8 data = fgetc(grf);
207-
/* According to the documentation bit 0 must always be set, and bits 3 and 6 are the same as in the nfo. */
208-
this->info = (1 << 0) | (data & (1 << 3 | 1 << 6));
207+
/* According to the documentation bit 0 must always be set, and bits 3, 4, 6 are the same as in the nfo. */
208+
this->info = (1 << 0) | (data & (1 << 3 | 1 << 4 | 1 << 6));
209209
switch(data&0x7){
210210
case 0x03: this->depth=DEPTH_32BPP; break;
211211
case 0x04: this->depth=DEPTH_8BPP; break;

src/sprites.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,7 @@ static const int DEPTH_MASK = 2;
3939

4040
// Define some of the bits in SpriteInfo::info
4141
#define DONOTCROP(info) (info & 64)
42+
#define ISRTL(info) (info & 16)
4243
#define HASTRANSPARENCY(info) (info & 8)
4344
#define SIZEISCOMPRESSED(info) (info & 2)
4445

0 commit comments

Comments
 (0)