author | rubidium |
Sun, 25 May 2008 19:17:03 +0000 | |
changeset 9354 | 845e07db4549 |
parent 9146 | dbe2317185eb |
child 9390 | 88d36f907e96 |
permissions | -rw-r--r-- |
2186 | 1 |
/* $Id$ */ |
2 |
||
9111
48ce04029fe4
(svn r12971) -Documentation: add @file in files that missed them and add something more than whitespace as description of files that don't have a description.
rubidium
parents:
8741
diff
changeset
|
3 |
/** @file spritecache.cpp Caching of sprites. */ |
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
4 |
|
0 | 5 |
#include "stdafx.h" |
1891
862800791170
(svn r2397) - CodeChange: rename all "ttd" files to "openttd" files.
Darkvater
parents:
1844
diff
changeset
|
6 |
#include "openttd.h" |
6896
b96972ff7d4d
(svn r10143) -Add: store the filename of the grfs opened and allow easy access to the name
truelight
parents:
6869
diff
changeset
|
7 |
#include "variables.h" |
1299
39c06aba09aa
(svn r1803) Move debugging stuff into files of it's own
tron
parents:
1250
diff
changeset
|
8 |
#include "debug.h" |
1349
15979a2e9001
(svn r1853) Move spritecache function declarations into a header of their own and use SpriteID as parameter type where appropriate
tron
parents:
1348
diff
changeset
|
9 |
#include "spritecache.h" |
0 | 10 |
#include "fileio.h" |
6852
439563b70fd3
(svn r10092) -Codechange: code-seperated the spriteloader and blitter from the rest of the code
truelight
parents:
6803
diff
changeset
|
11 |
#include "spriteloader/grf.hpp" |
8130
d2eb7d04f6e1
(svn r11691) -Codechange: move+rename helpers.hpp and only include it when it is really needed.
rubidium
parents:
8113
diff
changeset
|
12 |
#include "core/alloc_func.hpp" |
8131
160939e24ed3
(svn r11692) -Codechange: move some functions from 'functions.h' to a more logical place and remove about 50% of the includes of 'functions.h'
rubidium
parents:
8130
diff
changeset
|
13 |
#include "core/math_func.hpp" |
6901
ad8e8b93060d
(svn r10148) -Fix r10143: make --without-png to compile again
truelight
parents:
6896
diff
changeset
|
14 |
#ifdef WITH_PNG |
6896
b96972ff7d4d
(svn r10143) -Add: store the filename of the grfs opened and allow easy access to the name
truelight
parents:
6869
diff
changeset
|
15 |
#include "spriteloader/png.hpp" |
6901
ad8e8b93060d
(svn r10148) -Fix r10143: make --without-png to compile again
truelight
parents:
6896
diff
changeset
|
16 |
#endif /* WITH_PNG */ |
6937
40c760fcf1f6
(svn r10190) -Codechange: merged renderer and blitter to one single class API: blitter
truelight
parents:
6908
diff
changeset
|
17 |
#include "blitter/factory.hpp" |
6803
9803e56a8d9c
(svn r10042) -Codechange: Replace hardcoded spritecache size with a configuration
peter1138
parents:
6799
diff
changeset
|
18 |
|
8264
b1e85998c7d3
(svn r11828) -Codechange: include table/* as the last includes and remove an unneeded include from openttd.h.
rubidium
parents:
8214
diff
changeset
|
19 |
#include "table/sprites.h" |
b1e85998c7d3
(svn r11828) -Codechange: include table/* as the last includes and remove an unneeded include from openttd.h.
rubidium
parents:
8214
diff
changeset
|
20 |
|
6852
439563b70fd3
(svn r10092) -Codechange: code-seperated the spriteloader and blitter from the rest of the code
truelight
parents:
6803
diff
changeset
|
21 |
/* Default of 4MB spritecache */ |
439563b70fd3
(svn r10092) -Codechange: code-seperated the spriteloader and blitter from the rest of the code
truelight
parents:
6803
diff
changeset
|
22 |
uint _sprite_cache_size = 4; |
0 | 23 |
|
24 |
||
6248
e4a2ed7e5613
(svn r9051) -Codechange: typedef [enum|struct] Y {} X; -> [enum|struct] X {};
rubidium
parents:
6247
diff
changeset
|
25 |
struct SpriteCache { |
8741 | 26 |
void *ptr; |
6896
b96972ff7d4d
(svn r10143) -Add: store the filename of the grfs opened and allow easy access to the name
truelight
parents:
6869
diff
changeset
|
27 |
uint32 id; |
8741 | 28 |
uint32 file_pos; |
8373
7431d91527f2
(svn r11939) -Codechange: some type fixes and very initial steps into supporting NDS by default. Based on work by Dominik.
rubidium
parents:
8264
diff
changeset
|
29 |
uint16 file_slot; |
8741 | 30 |
int16 lru; |
6248
e4a2ed7e5613
(svn r9051) -Codechange: typedef [enum|struct] Y {} X; -> [enum|struct] X {};
rubidium
parents:
6247
diff
changeset
|
31 |
}; |
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
32 |
|
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
33 |
|
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
34 |
static uint _spritecache_items = 0; |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
35 |
static SpriteCache *_spritecache = NULL; |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
36 |
|
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
37 |
|
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
38 |
static inline SpriteCache *GetSpriteCache(uint index) |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
39 |
{ |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
40 |
return &_spritecache[index]; |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
41 |
} |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
42 |
|
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
43 |
|
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
44 |
static SpriteCache *AllocateSpriteCache(uint index) |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
45 |
{ |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
46 |
if (index >= _spritecache_items) { |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
47 |
/* Add another 1024 items to the 'pool' */ |
7927
3a3289a049f9
(svn r11480) -Codechange: Rename the function ALIGN fitting to the naming style
skidd13
parents:
7576
diff
changeset
|
48 |
uint items = Align(index + 1, 1024); |
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
49 |
|
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
50 |
DEBUG(sprite, 4, "Increasing sprite cache to %d items (%d bytes)", items, items * sizeof(*_spritecache)); |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
51 |
|
5609
dc6a58930ba4
(svn r8066) - Codechange: MallocT(), CallocT(), ReallocT() now return the pointer to allocated memory instead of modifying the pointer given as parameter
KUDr
parents:
5587
diff
changeset
|
52 |
_spritecache = ReallocT(_spritecache, items); |
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
53 |
|
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
54 |
/* Reset the new items and update the count */ |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
55 |
memset(_spritecache + _spritecache_items, 0, (items - _spritecache_items) * sizeof(*_spritecache)); |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
56 |
_spritecache_items = items; |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
57 |
} |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
58 |
|
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
59 |
return GetSpriteCache(index); |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
60 |
} |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
61 |
|
0 | 62 |
|
6248
e4a2ed7e5613
(svn r9051) -Codechange: typedef [enum|struct] Y {} X; -> [enum|struct] X {};
rubidium
parents:
6247
diff
changeset
|
63 |
struct MemBlock { |
9146
dbe2317185eb
(svn r13008) -Fix [FS#1997]: silence some MSVC x64 warnings
glx
parents:
9111
diff
changeset
|
64 |
size_t size; |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
65 |
byte data[VARARRAY_SIZE]; |
6248
e4a2ed7e5613
(svn r9051) -Codechange: typedef [enum|struct] Y {} X; -> [enum|struct] X {};
rubidium
parents:
6247
diff
changeset
|
66 |
}; |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
67 |
|
0 | 68 |
static uint _sprite_lru_counter; |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
69 |
static MemBlock *_spritecache_ptr; |
0 | 70 |
static int _compact_cache_counter; |
71 |
||
6247 | 72 |
static void CompactSpriteCache(); |
0 | 73 |
|
6247 | 74 |
static bool ReadSpriteHeaderSkipData() |
0 | 75 |
{ |
2329
c4d9fc4006b1
(svn r2855) Make ReadSpriteHeaderSkipData() responsible for detecting the end of a grf file instead of its callers - this simplifies the code a bit
tron
parents:
2321
diff
changeset
|
76 |
uint16 num = FioReadWord(); |
0 | 77 |
byte type; |
78 |
||
2329
c4d9fc4006b1
(svn r2855) Make ReadSpriteHeaderSkipData() responsible for detecting the end of a grf file instead of its callers - this simplifies the code a bit
tron
parents:
2321
diff
changeset
|
79 |
if (num == 0) return false; |
c4d9fc4006b1
(svn r2855) Make ReadSpriteHeaderSkipData() responsible for detecting the end of a grf file instead of its callers - this simplifies the code a bit
tron
parents:
2321
diff
changeset
|
80 |
|
0 | 81 |
type = FioReadByte(); |
82 |
if (type == 0xFF) { |
|
2342
aae24c9661ba
(svn r2868) Change the way NewGRFs are loaded: The loading process i no longer bolted onto the normal graphics loading.
tron
parents:
2340
diff
changeset
|
83 |
FioSkipBytes(num); |
5150
fe410b84b302
(svn r7242) -Fix: Don't load 1-byte pseudo sprites, as used in some NewGRF sets. If the sprite is ever drawn this will result in a "missing sprite" error instead of undefined misbehaviour leading to segmentation faults...
peter1138
parents:
4522
diff
changeset
|
84 |
/* Some NewGRF files have "empty" pseudo-sprites which are 1 |
fe410b84b302
(svn r7242) -Fix: Don't load 1-byte pseudo sprites, as used in some NewGRF sets. If the sprite is ever drawn this will result in a "missing sprite" error instead of undefined misbehaviour leading to segmentation faults...
peter1138
parents:
4522
diff
changeset
|
85 |
* byte long. Catch these so the sprites won't be displayed. */ |
fe410b84b302
(svn r7242) -Fix: Don't load 1-byte pseudo sprites, as used in some NewGRF sets. If the sprite is ever drawn this will result in a "missing sprite" error instead of undefined misbehaviour leading to segmentation faults...
peter1138
parents:
4522
diff
changeset
|
86 |
return num != 1; |
0 | 87 |
} |
184
dbeaaaf8b2bb
(svn r185) -Fix: [1016954] Cached_sprites does now work again
truelight
parents:
182
diff
changeset
|
88 |
|
0 | 89 |
FioSkipBytes(7); |
90 |
num -= 8; |
|
2329
c4d9fc4006b1
(svn r2855) Make ReadSpriteHeaderSkipData() responsible for detecting the end of a grf file instead of its callers - this simplifies the code a bit
tron
parents:
2321
diff
changeset
|
91 |
if (num == 0) return true; |
0 | 92 |
|
93 |
if (type & 2) { |
|
94 |
FioSkipBytes(num); |
|
1355 | 95 |
} else { |
96 |
while (num > 0) { |
|
97 |
int8 i = FioReadByte(); |
|
98 |
if (i >= 0) { |
|
99 |
num -= i; |
|
100 |
FioSkipBytes(i); |
|
101 |
} else { |
|
102 |
i = -(i >> 3); |
|
103 |
num -= i; |
|
104 |
FioReadByte(); |
|
105 |
} |
|
0 | 106 |
} |
107 |
} |
|
2329
c4d9fc4006b1
(svn r2855) Make ReadSpriteHeaderSkipData() responsible for detecting the end of a grf file instead of its callers - this simplifies the code a bit
tron
parents:
2321
diff
changeset
|
108 |
|
c4d9fc4006b1
(svn r2855) Make ReadSpriteHeaderSkipData() responsible for detecting the end of a grf file instead of its callers - this simplifies the code a bit
tron
parents:
2321
diff
changeset
|
109 |
return true; |
0 | 110 |
} |
111 |
||
3565
ef0a9ef56fa0
(svn r4446) - Add function to determine if a Sprite ID exists.
peter1138
parents:
2548
diff
changeset
|
112 |
/* Check if the given Sprite ID exists */ |
ef0a9ef56fa0
(svn r4446) - Add function to determine if a Sprite ID exists.
peter1138
parents:
2548
diff
changeset
|
113 |
bool SpriteExists(SpriteID id) |
ef0a9ef56fa0
(svn r4446) - Add function to determine if a Sprite ID exists.
peter1138
parents:
2548
diff
changeset
|
114 |
{ |
ef0a9ef56fa0
(svn r4446) - Add function to determine if a Sprite ID exists.
peter1138
parents:
2548
diff
changeset
|
115 |
/* Special case for Sprite ID zero -- its position is also 0... */ |
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
116 |
if (id == 0) return true; |
5702
f98beec96c66
(svn r8166) -Fix (r7797): Protect against out of bounds access to the sprite ptr
peter1138
parents:
5609
diff
changeset
|
117 |
if (id >= _spritecache_items) return false; |
7576
702396fd6908
(svn r11101) -Fix r11099: the check: file_pos == 0, no longer works; adjust the check with file_slot. This solves the ? sprites with autorail (nice catch Progman)
truelight
parents:
7570
diff
changeset
|
118 |
return !(GetSpriteCache(id)->file_pos == 0 && GetSpriteCache(id)->file_slot == 0); |
3565
ef0a9ef56fa0
(svn r4446) - Add function to determine if a Sprite ID exists.
peter1138
parents:
2548
diff
changeset
|
119 |
} |
ef0a9ef56fa0
(svn r4446) - Add function to determine if a Sprite ID exists.
peter1138
parents:
2548
diff
changeset
|
120 |
|
6852
439563b70fd3
(svn r10092) -Codechange: code-seperated the spriteloader and blitter from the rest of the code
truelight
parents:
6803
diff
changeset
|
121 |
void* AllocSprite(size_t); |
2014
ccfe4fa81a14
(svn r2522) Reorganize sprite load and decompression in order to remove a special case from the sprite blitter, which decompressed certain sprites every time when blitting them
tron
parents:
1891
diff
changeset
|
122 |
|
6869
cd04f1d7cad7
(svn r10109) -Fix [FS#838]: some NewGRFs use the same (unused in the "current" climate) sprite IDs. Normally this gives some artefacts, but when one NewGRF expects it to be a sprite and another NewGRF overwrites it with a non-sprite nasty things happen (drawing a non-sprite crashes OTTD).
rubidium
parents:
6865
diff
changeset
|
123 |
static void* ReadSprite(SpriteCache *sc, SpriteID id, bool real_sprite) |
0 | 124 |
{ |
7570
5d5d9b6af0ef
(svn r11095) -Codechange: don't abuse 'file_pos' by storing the file_slot in it too, but use a nice seperate variable for it
truelight
parents:
7089
diff
changeset
|
125 |
uint8 file_slot = sc->file_slot; |
6799
169d0b7fe821
(svn r10038) -Fix (r8634): Sprite resulting from '?' substitution was reloaded into the cache entry for SPR_IMG_QUERY instead of the original sprite cache entry. This resulted in unaccounted missing sprite cache memory, and was exacerbated because the original missing sprite was not cached, so it did it again and again and again. Slowdowns and boom. Etc.
peter1138
parents:
6481
diff
changeset
|
126 |
uint32 file_pos = sc->file_pos; |
2014
ccfe4fa81a14
(svn r2522) Reorganize sprite load and decompression in order to remove a special case from the sprite blitter, which decompressed certain sprites every time when blitting them
tron
parents:
1891
diff
changeset
|
127 |
|
5380
8ea58542b6e0
(svn r7565) -Codechange: Rework DEBUG functionality. Look for appropiate debugging levels to
Darkvater
parents:
5150
diff
changeset
|
128 |
DEBUG(sprite, 9, "Load sprite %d", id); |
184
dbeaaaf8b2bb
(svn r185) -Fix: [1016954] Cached_sprites does now work again
truelight
parents:
182
diff
changeset
|
129 |
|
3565
ef0a9ef56fa0
(svn r4446) - Add function to determine if a Sprite ID exists.
peter1138
parents:
2548
diff
changeset
|
130 |
if (!SpriteExists(id)) { |
5962
c861a188a760
(svn r8634) -Codechange: replace missing sprites with a red question mark.
rubidium
parents:
5720
diff
changeset
|
131 |
DEBUG(sprite, 1, "Tried to load non-existing sprite #%d. Probable cause: Wrong/missing NewGRFs", id); |
c861a188a760
(svn r8634) -Codechange: replace missing sprites with a red question mark.
rubidium
parents:
5720
diff
changeset
|
132 |
|
c861a188a760
(svn r8634) -Codechange: replace missing sprites with a red question mark.
rubidium
parents:
5720
diff
changeset
|
133 |
/* SPR_IMG_QUERY is a BIG FAT RED ? */ |
c861a188a760
(svn r8634) -Codechange: replace missing sprites with a red question mark.
rubidium
parents:
5720
diff
changeset
|
134 |
id = SPR_IMG_QUERY; |
7570
5d5d9b6af0ef
(svn r11095) -Codechange: don't abuse 'file_pos' by storing the file_slot in it too, but use a nice seperate variable for it
truelight
parents:
7089
diff
changeset
|
135 |
file_slot = GetSpriteCache(SPR_IMG_QUERY)->file_slot; |
5d5d9b6af0ef
(svn r11095) -Codechange: don't abuse 'file_pos' by storing the file_slot in it too, but use a nice seperate variable for it
truelight
parents:
7089
diff
changeset
|
136 |
file_pos = GetSpriteCache(SPR_IMG_QUERY)->file_pos; |
1378
23d4f642c989
(svn r1882) Add a basic check if a non-existent sprite gets accessed.
tron
parents:
1363
diff
changeset
|
137 |
} |
23d4f642c989
(svn r1882) Add a basic check if a non-existent sprite gets accessed.
tron
parents:
1363
diff
changeset
|
138 |
|
6903
091fb25052ac
(svn r10150) -Fix r10148: show a message to users when using 32bpp blitter and no libpng available
truelight
parents:
6902
diff
changeset
|
139 |
if (BlitterFactoryBase::GetCurrentBlitter()->GetScreenDepth() == 32) { |
6901
ad8e8b93060d
(svn r10148) -Fix r10143: make --without-png to compile again
truelight
parents:
6896
diff
changeset
|
140 |
#ifdef WITH_PNG |
6896
b96972ff7d4d
(svn r10143) -Add: store the filename of the grfs opened and allow easy access to the name
truelight
parents:
6869
diff
changeset
|
141 |
/* Try loading 32bpp graphics in case we are 32bpp output */ |
b96972ff7d4d
(svn r10143) -Add: store the filename of the grfs opened and allow easy access to the name
truelight
parents:
6869
diff
changeset
|
142 |
SpriteLoaderPNG sprite_loader; |
b96972ff7d4d
(svn r10143) -Add: store the filename of the grfs opened and allow easy access to the name
truelight
parents:
6869
diff
changeset
|
143 |
SpriteLoader::Sprite sprite; |
b96972ff7d4d
(svn r10143) -Add: store the filename of the grfs opened and allow easy access to the name
truelight
parents:
6869
diff
changeset
|
144 |
|
8374
7a1b6c89cb89
(svn r11940) -Codechange: Store short filename once per open file instead of once per sprite cache entry. Not all file types need this, but most of the time no sprite cache entry needed it either.
peter1138
parents:
8373
diff
changeset
|
145 |
if (sprite_loader.LoadSprite(&sprite, file_slot, sc->id)) { |
6896
b96972ff7d4d
(svn r10143) -Add: store the filename of the grfs opened and allow easy access to the name
truelight
parents:
6869
diff
changeset
|
146 |
sc->ptr = BlitterFactoryBase::GetCurrentBlitter()->Encode(&sprite, &AllocSprite); |
b96972ff7d4d
(svn r10143) -Add: store the filename of the grfs opened and allow easy access to the name
truelight
parents:
6869
diff
changeset
|
147 |
free(sprite.data); |
b96972ff7d4d
(svn r10143) -Add: store the filename of the grfs opened and allow easy access to the name
truelight
parents:
6869
diff
changeset
|
148 |
|
b96972ff7d4d
(svn r10143) -Add: store the filename of the grfs opened and allow easy access to the name
truelight
parents:
6869
diff
changeset
|
149 |
return sc->ptr; |
b96972ff7d4d
(svn r10143) -Add: store the filename of the grfs opened and allow easy access to the name
truelight
parents:
6869
diff
changeset
|
150 |
} |
b96972ff7d4d
(svn r10143) -Add: store the filename of the grfs opened and allow easy access to the name
truelight
parents:
6869
diff
changeset
|
151 |
/* If the PNG couldn't be loaded, fall back to 8bpp grfs */ |
6903
091fb25052ac
(svn r10150) -Fix r10148: show a message to users when using 32bpp blitter and no libpng available
truelight
parents:
6902
diff
changeset
|
152 |
#else |
091fb25052ac
(svn r10150) -Fix r10148: show a message to users when using 32bpp blitter and no libpng available
truelight
parents:
6902
diff
changeset
|
153 |
static bool show_once = true; |
091fb25052ac
(svn r10150) -Fix r10148: show a message to users when using 32bpp blitter and no libpng available
truelight
parents:
6902
diff
changeset
|
154 |
if (show_once) { |
091fb25052ac
(svn r10150) -Fix r10148: show a message to users when using 32bpp blitter and no libpng available
truelight
parents:
6902
diff
changeset
|
155 |
DEBUG(misc, 0, "You are running a 32bpp blitter, but this build is without libpng support; falling back to 8bpp graphics"); |
091fb25052ac
(svn r10150) -Fix r10148: show a message to users when using 32bpp blitter and no libpng available
truelight
parents:
6902
diff
changeset
|
156 |
show_once = false; |
091fb25052ac
(svn r10150) -Fix r10148: show a message to users when using 32bpp blitter and no libpng available
truelight
parents:
6902
diff
changeset
|
157 |
} |
091fb25052ac
(svn r10150) -Fix r10148: show a message to users when using 32bpp blitter and no libpng available
truelight
parents:
6902
diff
changeset
|
158 |
#endif /* WITH_PNG */ |
6896
b96972ff7d4d
(svn r10143) -Add: store the filename of the grfs opened and allow easy access to the name
truelight
parents:
6869
diff
changeset
|
159 |
} |
b96972ff7d4d
(svn r10143) -Add: store the filename of the grfs opened and allow easy access to the name
truelight
parents:
6869
diff
changeset
|
160 |
|
7570
5d5d9b6af0ef
(svn r11095) -Codechange: don't abuse 'file_pos' by storing the file_slot in it too, but use a nice seperate variable for it
truelight
parents:
7089
diff
changeset
|
161 |
FioSeekToFile(file_slot, file_pos); |
1354
4f9416233d06
(svn r1858) Let ReadSprite() handle the subtleties of loading a sprite, not its caller
tron
parents:
1353
diff
changeset
|
162 |
|
6852
439563b70fd3
(svn r10092) -Codechange: code-seperated the spriteloader and blitter from the rest of the code
truelight
parents:
6803
diff
changeset
|
163 |
/* Read the size and type */ |
439563b70fd3
(svn r10092) -Codechange: code-seperated the spriteloader and blitter from the rest of the code
truelight
parents:
6803
diff
changeset
|
164 |
int num = FioReadWord(); |
439563b70fd3
(svn r10092) -Codechange: code-seperated the spriteloader and blitter from the rest of the code
truelight
parents:
6803
diff
changeset
|
165 |
byte type = FioReadByte(); |
439563b70fd3
(svn r10092) -Codechange: code-seperated the spriteloader and blitter from the rest of the code
truelight
parents:
6803
diff
changeset
|
166 |
/* Type 0xFF indicates either a colormap or some other non-sprite info */ |
2014
ccfe4fa81a14
(svn r2522) Reorganize sprite load and decompression in order to remove a special case from the sprite blitter, which decompressed certain sprites every time when blitting them
tron
parents:
1891
diff
changeset
|
167 |
if (type == 0xFF) { |
6869
cd04f1d7cad7
(svn r10109) -Fix [FS#838]: some NewGRFs use the same (unused in the "current" climate) sprite IDs. Normally this gives some artefacts, but when one NewGRF expects it to be a sprite and another NewGRF overwrites it with a non-sprite nasty things happen (drawing a non-sprite crashes OTTD).
rubidium
parents:
6865
diff
changeset
|
168 |
if (real_sprite) { |
cd04f1d7cad7
(svn r10109) -Fix [FS#838]: some NewGRFs use the same (unused in the "current" climate) sprite IDs. Normally this gives some artefacts, but when one NewGRF expects it to be a sprite and another NewGRF overwrites it with a non-sprite nasty things happen (drawing a non-sprite crashes OTTD).
rubidium
parents:
6865
diff
changeset
|
169 |
static byte warning_level = 0; |
cd04f1d7cad7
(svn r10109) -Fix [FS#838]: some NewGRFs use the same (unused in the "current" climate) sprite IDs. Normally this gives some artefacts, but when one NewGRF expects it to be a sprite and another NewGRF overwrites it with a non-sprite nasty things happen (drawing a non-sprite crashes OTTD).
rubidium
parents:
6865
diff
changeset
|
170 |
DEBUG(sprite, warning_level, "Tried to load non sprite #%d as a real sprite. Probable cause: NewGRF interference", id); |
cd04f1d7cad7
(svn r10109) -Fix [FS#838]: some NewGRFs use the same (unused in the "current" climate) sprite IDs. Normally this gives some artefacts, but when one NewGRF expects it to be a sprite and another NewGRF overwrites it with a non-sprite nasty things happen (drawing a non-sprite crashes OTTD).
rubidium
parents:
6865
diff
changeset
|
171 |
warning_level = 6; |
cd04f1d7cad7
(svn r10109) -Fix [FS#838]: some NewGRFs use the same (unused in the "current" climate) sprite IDs. Normally this gives some artefacts, but when one NewGRF expects it to be a sprite and another NewGRF overwrites it with a non-sprite nasty things happen (drawing a non-sprite crashes OTTD).
rubidium
parents:
6865
diff
changeset
|
172 |
if (id == SPR_IMG_QUERY) error("Uhm, would you be so kind not to load a NewGRF that makes the 'query' sprite a non- sprite?"); |
cd04f1d7cad7
(svn r10109) -Fix [FS#838]: some NewGRFs use the same (unused in the "current" climate) sprite IDs. Normally this gives some artefacts, but when one NewGRF expects it to be a sprite and another NewGRF overwrites it with a non-sprite nasty things happen (drawing a non-sprite crashes OTTD).
rubidium
parents:
6865
diff
changeset
|
173 |
return (void*)GetSprite(SPR_IMG_QUERY); |
cd04f1d7cad7
(svn r10109) -Fix [FS#838]: some NewGRFs use the same (unused in the "current" climate) sprite IDs. Normally this gives some artefacts, but when one NewGRF expects it to be a sprite and another NewGRF overwrites it with a non-sprite nasty things happen (drawing a non-sprite crashes OTTD).
rubidium
parents:
6865
diff
changeset
|
174 |
} |
cd04f1d7cad7
(svn r10109) -Fix [FS#838]: some NewGRFs use the same (unused in the "current" climate) sprite IDs. Normally this gives some artefacts, but when one NewGRF expects it to be a sprite and another NewGRF overwrites it with a non-sprite nasty things happen (drawing a non-sprite crashes OTTD).
rubidium
parents:
6865
diff
changeset
|
175 |
|
6852
439563b70fd3
(svn r10092) -Codechange: code-seperated the spriteloader and blitter from the rest of the code
truelight
parents:
6803
diff
changeset
|
176 |
byte *dest = (byte *)AllocSprite(num); |
2014
ccfe4fa81a14
(svn r2522) Reorganize sprite load and decompression in order to remove a special case from the sprite blitter, which decompressed certain sprites every time when blitting them
tron
parents:
1891
diff
changeset
|
177 |
|
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
178 |
sc->ptr = dest; |
2014
ccfe4fa81a14
(svn r2522) Reorganize sprite load and decompression in order to remove a special case from the sprite blitter, which decompressed certain sprites every time when blitting them
tron
parents:
1891
diff
changeset
|
179 |
FioReadBlock(dest, num); |
ccfe4fa81a14
(svn r2522) Reorganize sprite load and decompression in order to remove a special case from the sprite blitter, which decompressed certain sprites every time when blitting them
tron
parents:
1891
diff
changeset
|
180 |
|
6865
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
181 |
return sc->ptr; |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
182 |
} |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
183 |
/* Ugly hack to work around the problem that the old landscape |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
184 |
* generator assumes that those sprites are stored uncompressed in |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
185 |
* the memory, and they are only read directly by the code, never |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
186 |
* send to the blitter. So do not send it to the blitter (which will |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
187 |
* result in a data array in the format the blitter likes most), but |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
188 |
* read the data directly from disk and store that as sprite. |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
189 |
* Ugly: yes. Other solution: no. Blame the original author or |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
190 |
* something ;) The image should really have been a data-stream |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
191 |
* (so type = 0xFF basicly). */ |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
192 |
if (id >= 4845 && id <= 4881) { |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
193 |
uint height = FioReadByte(); |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
194 |
uint width = FioReadWord(); |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
195 |
Sprite *sprite; |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
196 |
byte *dest; |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
197 |
|
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
198 |
num = width * height; |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
199 |
sprite = (Sprite *)AllocSprite(sizeof(*sprite) + num); |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
200 |
sc->ptr = sprite; |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
201 |
sprite->height = height; |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
202 |
sprite->width = width; |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
203 |
sprite->x_offs = FioReadWord(); |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
204 |
sprite->y_offs = FioReadWord(); |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
205 |
|
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
206 |
dest = sprite->data; |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
207 |
while (num > 0) { |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
208 |
int8 i = FioReadByte(); |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
209 |
if (i >= 0) { |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
210 |
num -= i; |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
211 |
for (; i > 0; --i) *dest++ = FioReadByte(); |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
212 |
} else { |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
213 |
const byte* rel = dest - (((i & 7) << 8) | FioReadByte()); |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
214 |
i = -(i >> 3); |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
215 |
num -= i; |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
216 |
for (; i > 0; --i) *dest++ = *rel++; |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
217 |
} |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
218 |
} |
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
219 |
|
60e668c0ed7c
(svn r10105) -Fix r10092: fix sprite 4845 till 4881 (inclusive), so they store the data as on the disk in the memory, as the old landscape generate assumes this. Talking about ugly hacks...
truelight
parents:
6856
diff
changeset
|
220 |
return sc->ptr; |
6852
439563b70fd3
(svn r10092) -Codechange: code-seperated the spriteloader and blitter from the rest of the code
truelight
parents:
6803
diff
changeset
|
221 |
} |
2014
ccfe4fa81a14
(svn r2522) Reorganize sprite load and decompression in order to remove a special case from the sprite blitter, which decompressed certain sprites every time when blitting them
tron
parents:
1891
diff
changeset
|
222 |
|
6869
cd04f1d7cad7
(svn r10109) -Fix [FS#838]: some NewGRFs use the same (unused in the "current" climate) sprite IDs. Normally this gives some artefacts, but when one NewGRF expects it to be a sprite and another NewGRF overwrites it with a non-sprite nasty things happen (drawing a non-sprite crashes OTTD).
rubidium
parents:
6865
diff
changeset
|
223 |
if (!real_sprite) { |
cd04f1d7cad7
(svn r10109) -Fix [FS#838]: some NewGRFs use the same (unused in the "current" climate) sprite IDs. Normally this gives some artefacts, but when one NewGRF expects it to be a sprite and another NewGRF overwrites it with a non-sprite nasty things happen (drawing a non-sprite crashes OTTD).
rubidium
parents:
6865
diff
changeset
|
224 |
static byte warning_level = 0; |
cd04f1d7cad7
(svn r10109) -Fix [FS#838]: some NewGRFs use the same (unused in the "current" climate) sprite IDs. Normally this gives some artefacts, but when one NewGRF expects it to be a sprite and another NewGRF overwrites it with a non-sprite nasty things happen (drawing a non-sprite crashes OTTD).
rubidium
parents:
6865
diff
changeset
|
225 |
DEBUG(sprite, warning_level, "Tried to load real sprite #%d as a non sprite. Probable cause: NewGRF interference", id); |
cd04f1d7cad7
(svn r10109) -Fix [FS#838]: some NewGRFs use the same (unused in the "current" climate) sprite IDs. Normally this gives some artefacts, but when one NewGRF expects it to be a sprite and another NewGRF overwrites it with a non-sprite nasty things happen (drawing a non-sprite crashes OTTD).
rubidium
parents:
6865
diff
changeset
|
226 |
warning_level = 6; |
cd04f1d7cad7
(svn r10109) -Fix [FS#838]: some NewGRFs use the same (unused in the "current" climate) sprite IDs. Normally this gives some artefacts, but when one NewGRF expects it to be a sprite and another NewGRF overwrites it with a non-sprite nasty things happen (drawing a non-sprite crashes OTTD).
rubidium
parents:
6865
diff
changeset
|
227 |
} |
cd04f1d7cad7
(svn r10109) -Fix [FS#838]: some NewGRFs use the same (unused in the "current" climate) sprite IDs. Normally this gives some artefacts, but when one NewGRF expects it to be a sprite and another NewGRF overwrites it with a non-sprite nasty things happen (drawing a non-sprite crashes OTTD).
rubidium
parents:
6865
diff
changeset
|
228 |
|
6852
439563b70fd3
(svn r10092) -Codechange: code-seperated the spriteloader and blitter from the rest of the code
truelight
parents:
6803
diff
changeset
|
229 |
SpriteLoaderGrf sprite_loader; |
439563b70fd3
(svn r10092) -Codechange: code-seperated the spriteloader and blitter from the rest of the code
truelight
parents:
6803
diff
changeset
|
230 |
SpriteLoader::Sprite sprite; |
0 | 231 |
|
8374
7a1b6c89cb89
(svn r11940) -Codechange: Store short filename once per open file instead of once per sprite cache entry. Not all file types need this, but most of the time no sprite cache entry needed it either.
peter1138
parents:
8373
diff
changeset
|
232 |
if (!sprite_loader.LoadSprite(&sprite, file_slot, file_pos)) return NULL; |
6852
439563b70fd3
(svn r10092) -Codechange: code-seperated the spriteloader and blitter from the rest of the code
truelight
parents:
6803
diff
changeset
|
233 |
if (id == 142) sprite.height = 10; // Compensate for a TTD bug |
6856
aa95d0fd29f1
(svn r10096) -Fix r10092: freetype bypassed the Blitter::Encode, making fonts look weird
truelight
parents:
6852
diff
changeset
|
234 |
sc->ptr = BlitterFactoryBase::GetCurrentBlitter()->Encode(&sprite, &AllocSprite); |
6852
439563b70fd3
(svn r10092) -Codechange: code-seperated the spriteloader and blitter from the rest of the code
truelight
parents:
6803
diff
changeset
|
235 |
free(sprite.data); |
184
dbeaaaf8b2bb
(svn r185) -Fix: [1016954] Cached_sprites does now work again
truelight
parents:
182
diff
changeset
|
236 |
|
6852
439563b70fd3
(svn r10092) -Codechange: code-seperated the spriteloader and blitter from the rest of the code
truelight
parents:
6803
diff
changeset
|
237 |
return sc->ptr; |
0 | 238 |
} |
239 |
||
240 |
||
7570
5d5d9b6af0ef
(svn r11095) -Codechange: don't abuse 'file_pos' by storing the file_slot in it too, but use a nice seperate variable for it
truelight
parents:
7089
diff
changeset
|
241 |
bool LoadNextSprite(int load_index, byte file_slot, uint file_sprite_id) |
0 | 242 |
{ |
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
243 |
SpriteCache *sc; |
7570
5d5d9b6af0ef
(svn r11095) -Codechange: don't abuse 'file_pos' by storing the file_slot in it too, but use a nice seperate variable for it
truelight
parents:
7089
diff
changeset
|
244 |
uint32 file_pos = FioGetPos(); |
0 | 245 |
|
2342
aae24c9661ba
(svn r2868) Change the way NewGRFs are loaded: The loading process i no longer bolted onto the normal graphics loading.
tron
parents:
2340
diff
changeset
|
246 |
if (!ReadSpriteHeaderSkipData()) return false; |
361
95307fb1c3f8
(svn r549) -newgrf: Support for action 0xd (change a parameter (sorta variable for the GRF scripts)). Based on patch by octo, heavy changes by pasky.
darkvater
parents:
184
diff
changeset
|
247 |
|
3591
a5febb93bc11
(svn r4481) - Fix: Validate the given sprite ID when loading a sprite.
peter1138
parents:
3565
diff
changeset
|
248 |
if (load_index >= MAX_SPRITES) { |
a5febb93bc11
(svn r4481) - Fix: Validate the given sprite ID when loading a sprite.
peter1138
parents:
3565
diff
changeset
|
249 |
error("Tried to load too many sprites (#%d; max %d)", load_index, MAX_SPRITES); |
a5febb93bc11
(svn r4481) - Fix: Validate the given sprite ID when loading a sprite.
peter1138
parents:
3565
diff
changeset
|
250 |
} |
a5febb93bc11
(svn r4481) - Fix: Validate the given sprite ID when loading a sprite.
peter1138
parents:
3565
diff
changeset
|
251 |
|
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
252 |
sc = AllocateSpriteCache(load_index); |
7570
5d5d9b6af0ef
(svn r11095) -Codechange: don't abuse 'file_pos' by storing the file_slot in it too, but use a nice seperate variable for it
truelight
parents:
7089
diff
changeset
|
253 |
sc->file_slot = file_slot; |
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
254 |
sc->file_pos = file_pos; |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
255 |
sc->ptr = NULL; |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
256 |
sc->lru = 0; |
6908
6b1324d7a2c9
(svn r10157) -Fix: use as indentified for PNGs, the place of the image as it was in the grf, not the internal SpriteID
truelight
parents:
6903
diff
changeset
|
257 |
sc->id = file_sprite_id; |
6896
b96972ff7d4d
(svn r10143) -Add: store the filename of the grfs opened and allow easy access to the name
truelight
parents:
6869
diff
changeset
|
258 |
|
0 | 259 |
return true; |
260 |
} |
|
261 |
||
2407 | 262 |
|
5587
167d9a91ef02
(svn r8038) -Merge: the cpp branch. Effort of KUDr, Celestar, glx, Smoovius, stillunknown and pv2b.
rubidium
parents:
5584
diff
changeset
|
263 |
void DupSprite(SpriteID old_spr, SpriteID new_spr) |
2407 | 264 |
{ |
8435
6425e2ecd2a6
(svn r12005) -Fix [FS#1717]: possible reading from an invalid pointer. Patch by PhilSophus.
rubidium
parents:
8432
diff
changeset
|
265 |
SpriteCache *scnew = AllocateSpriteCache(new_spr); // may reallocate: so put it first |
5587
167d9a91ef02
(svn r8038) -Merge: the cpp branch. Effort of KUDr, Celestar, glx, Smoovius, stillunknown and pv2b.
rubidium
parents:
5584
diff
changeset
|
266 |
SpriteCache *scold = GetSpriteCache(old_spr); |
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
267 |
|
7570
5d5d9b6af0ef
(svn r11095) -Codechange: don't abuse 'file_pos' by storing the file_slot in it too, but use a nice seperate variable for it
truelight
parents:
7089
diff
changeset
|
268 |
scnew->file_slot = scold->file_slot; |
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
269 |
scnew->file_pos = scold->file_pos; |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
270 |
scnew->ptr = NULL; |
6896
b96972ff7d4d
(svn r10143) -Add: store the filename of the grfs opened and allow easy access to the name
truelight
parents:
6869
diff
changeset
|
271 |
scnew->id = scold->id; |
2407 | 272 |
} |
273 |
||
274 |
||
0 | 275 |
#define S_FREE_MASK 1 |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
276 |
|
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
277 |
static inline MemBlock* NextBlock(MemBlock* block) |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
278 |
{ |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
279 |
return (MemBlock*)((byte*)block + (block->size & ~S_FREE_MASK)); |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
280 |
} |
0 | 281 |
|
6247 | 282 |
static uint32 GetSpriteCacheUsage() |
0 | 283 |
{ |
4321
958a8e9c012b
(svn r5974) -Codechange: added casts all around the place to make Windows 64bit happy (michi_cc)
truelight
parents:
3591
diff
changeset
|
284 |
uint32 tot_size = 0; |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
285 |
MemBlock* s; |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
286 |
|
8562
7419166c16bd
(svn r12140) -Codechange: A bit of code style fixes(Geektoo).
belugas
parents:
8435
diff
changeset
|
287 |
for (s = _spritecache_ptr; s->size != 0; s = NextBlock(s)) { |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
288 |
if (!(s->size & S_FREE_MASK)) tot_size += s->size; |
8562
7419166c16bd
(svn r12140) -Codechange: A bit of code style fixes(Geektoo).
belugas
parents:
8435
diff
changeset
|
289 |
} |
0 | 290 |
|
291 |
return tot_size; |
|
292 |
} |
|
293 |
||
294 |
||
6247 | 295 |
void IncreaseSpriteLRU() |
0 | 296 |
{ |
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
297 |
/* Increase all LRU values */ |
0 | 298 |
if (_sprite_lru_counter > 16384) { |
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
299 |
SpriteID i; |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
300 |
|
5380
8ea58542b6e0
(svn r7565) -Codechange: Rework DEBUG functionality. Look for appropiate debugging levels to
Darkvater
parents:
5150
diff
changeset
|
301 |
DEBUG(sprite, 3, "Fixing lru %d, inuse=%d", _sprite_lru_counter, GetSpriteCacheUsage()); |
0 | 302 |
|
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
303 |
for (i = 0; i != _spritecache_items; i++) { |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
304 |
SpriteCache *sc = GetSpriteCache(i); |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
305 |
if (sc->ptr != NULL) { |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
306 |
if (sc->lru >= 0) { |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
307 |
sc->lru = -1; |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
308 |
} else if (sc->lru != -32768) { |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
309 |
sc->lru--; |
0 | 310 |
} |
311 |
} |
|
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
312 |
} |
0 | 313 |
_sprite_lru_counter = 0; |
314 |
} |
|
315 |
||
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
316 |
/* Compact sprite cache every now and then. */ |
0 | 317 |
if (++_compact_cache_counter >= 740) { |
318 |
CompactSpriteCache(); |
|
319 |
_compact_cache_counter = 0; |
|
320 |
} |
|
321 |
} |
|
322 |
||
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
323 |
/** Called when holes in the sprite cache should be removed. |
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
324 |
* That is accomplished by moving the cached data. */ |
6247 | 325 |
static void CompactSpriteCache() |
0 | 326 |
{ |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
327 |
MemBlock *s; |
184
dbeaaaf8b2bb
(svn r185) -Fix: [1016954] Cached_sprites does now work again
truelight
parents:
182
diff
changeset
|
328 |
|
5380
8ea58542b6e0
(svn r7565) -Codechange: Rework DEBUG functionality. Look for appropiate debugging levels to
Darkvater
parents:
5150
diff
changeset
|
329 |
DEBUG(sprite, 3, "Compacting sprite cache, inuse=%d", GetSpriteCacheUsage()); |
184
dbeaaaf8b2bb
(svn r185) -Fix: [1016954] Cached_sprites does now work again
truelight
parents:
182
diff
changeset
|
330 |
|
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
331 |
for (s = _spritecache_ptr; s->size != 0;) { |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
332 |
if (s->size & S_FREE_MASK) { |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
333 |
MemBlock* next = NextBlock(s); |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
334 |
MemBlock temp; |
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
335 |
SpriteID i; |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
336 |
|
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
337 |
/* Since free blocks are automatically coalesced, this should hold true. */ |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
338 |
assert(!(next->size & S_FREE_MASK)); |
184
dbeaaaf8b2bb
(svn r185) -Fix: [1016954] Cached_sprites does now work again
truelight
parents:
182
diff
changeset
|
339 |
|
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
340 |
/* If the next block is the sentinel block, we can safely return */ |
8741 | 341 |
if (next->size == 0) break; |
0 | 342 |
|
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
343 |
/* Locate the sprite belonging to the next pointer. */ |
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
344 |
for (i = 0; GetSpriteCache(i)->ptr != next->data; i++) { |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
345 |
assert(i != _spritecache_items); |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
346 |
} |
0 | 347 |
|
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
348 |
GetSpriteCache(i)->ptr = s->data; // Adjust sprite array entry |
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
349 |
/* Swap this and the next block */ |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
350 |
temp = *s; |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
351 |
memmove(s, next, next->size); |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
352 |
s = NextBlock(s); |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
353 |
*s = temp; |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
354 |
|
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
355 |
/* Coalesce free blocks */ |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
356 |
while (NextBlock(s)->size & S_FREE_MASK) { |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
357 |
s->size += NextBlock(s)->size & ~S_FREE_MASK; |
0 | 358 |
} |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
359 |
} else { |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
360 |
s = NextBlock(s); |
0 | 361 |
} |
362 |
} |
|
363 |
} |
|
364 |
||
6247 | 365 |
static void DeleteEntryFromSpriteCache() |
0 | 366 |
{ |
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
367 |
SpriteID i; |
5587
167d9a91ef02
(svn r8038) -Merge: the cpp branch. Effort of KUDr, Celestar, glx, Smoovius, stillunknown and pv2b.
rubidium
parents:
5584
diff
changeset
|
368 |
uint best = UINT_MAX; |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
369 |
MemBlock* s; |
0 | 370 |
int cur_lru; |
371 |
||
5380
8ea58542b6e0
(svn r7565) -Codechange: Rework DEBUG functionality. Look for appropiate debugging levels to
Darkvater
parents:
5150
diff
changeset
|
372 |
DEBUG(sprite, 3, "DeleteEntryFromSpriteCache, inuse=%d", GetSpriteCacheUsage()); |
0 | 373 |
|
374 |
cur_lru = 0xffff; |
|
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
375 |
for (i = 0; i != _spritecache_items; i++) { |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
376 |
SpriteCache *sc = GetSpriteCache(i); |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
377 |
if (sc->ptr != NULL && sc->lru < cur_lru) { |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
378 |
cur_lru = sc->lru; |
0 | 379 |
best = i; |
380 |
} |
|
381 |
} |
|
382 |
||
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
383 |
/* Display an error message and die, in case we found no sprite at all. |
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
384 |
* This shouldn't really happen, unless all sprites are locked. */ |
8040
92c69fcd0d61
(svn r11600) -Cleanup: remove extra out-of-memory checks, since it's now done in *allocT functions.
glx
parents:
8037
diff
changeset
|
385 |
if (best == (uint)-1) error("Out of sprite memory"); |
0 | 386 |
|
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
387 |
/* Mark the block as free (the block must be in use) */ |
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
388 |
s = (MemBlock*)GetSpriteCache(best)->ptr - 1; |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
389 |
assert(!(s->size & S_FREE_MASK)); |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
390 |
s->size |= S_FREE_MASK; |
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
391 |
GetSpriteCache(best)->ptr = NULL; |
0 | 392 |
|
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
393 |
/* And coalesce adjacent free blocks */ |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
394 |
for (s = _spritecache_ptr; s->size != 0; s = NextBlock(s)) { |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
395 |
if (s->size & S_FREE_MASK) { |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
396 |
while (NextBlock(s)->size & S_FREE_MASK) { |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
397 |
s->size += NextBlock(s)->size & ~S_FREE_MASK; |
0 | 398 |
} |
399 |
} |
|
400 |
} |
|
401 |
} |
|
402 |
||
6852
439563b70fd3
(svn r10092) -Codechange: code-seperated the spriteloader and blitter from the rest of the code
truelight
parents:
6803
diff
changeset
|
403 |
void* AllocSprite(size_t mem_req) |
0 | 404 |
{ |
2014
ccfe4fa81a14
(svn r2522) Reorganize sprite load and decompression in order to remove a special case from the sprite blitter, which decompressed certain sprites every time when blitting them
tron
parents:
1891
diff
changeset
|
405 |
mem_req += sizeof(MemBlock); |
0 | 406 |
|
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
407 |
/* Align this to an uint32 boundary. This also makes sure that the 2 least |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
408 |
* bits are not used, so we could use those for other things. */ |
7927
3a3289a049f9
(svn r11480) -Codechange: Rename the function ALIGN fitting to the naming style
skidd13
parents:
7576
diff
changeset
|
409 |
mem_req = Align(mem_req, sizeof(uint32)); |
0 | 410 |
|
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
411 |
for (;;) { |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
412 |
MemBlock* s; |
0 | 413 |
|
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
414 |
for (s = _spritecache_ptr; s->size != 0; s = NextBlock(s)) { |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
415 |
if (s->size & S_FREE_MASK) { |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
416 |
size_t cur_size = s->size & ~S_FREE_MASK; |
0 | 417 |
|
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
418 |
/* Is the block exactly the size we need or |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
419 |
* big enough for an additional free block? */ |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
420 |
if (cur_size == mem_req || |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
421 |
cur_size >= mem_req + sizeof(MemBlock)) { |
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
422 |
/* Set size and in use */ |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
423 |
s->size = mem_req; |
184
dbeaaaf8b2bb
(svn r185) -Fix: [1016954] Cached_sprites does now work again
truelight
parents:
182
diff
changeset
|
424 |
|
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
425 |
/* Do we need to inject a free block too? */ |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
426 |
if (cur_size != mem_req) { |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
427 |
NextBlock(s)->size = (cur_size - mem_req) | S_FREE_MASK; |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
428 |
} |
0 | 429 |
|
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
430 |
return s->data; |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
431 |
} |
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
432 |
} |
0 | 433 |
} |
434 |
||
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
435 |
/* Reached sentinel, but no block found yet. Delete some old entry. */ |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
436 |
DeleteEntryFromSpriteCache(); |
0 | 437 |
} |
438 |
} |
|
439 |
||
440 |
||
6869
cd04f1d7cad7
(svn r10109) -Fix [FS#838]: some NewGRFs use the same (unused in the "current" climate) sprite IDs. Normally this gives some artefacts, but when one NewGRF expects it to be a sprite and another NewGRF overwrites it with a non-sprite nasty things happen (drawing a non-sprite crashes OTTD).
rubidium
parents:
6865
diff
changeset
|
441 |
const void *GetRawSprite(SpriteID sprite, bool real_sprite) |
0 | 442 |
{ |
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
443 |
SpriteCache *sc; |
2014
ccfe4fa81a14
(svn r2522) Reorganize sprite load and decompression in order to remove a special case from the sprite blitter, which decompressed certain sprites every time when blitting them
tron
parents:
1891
diff
changeset
|
444 |
void* p; |
0 | 445 |
|
5702
f98beec96c66
(svn r8166) -Fix (r7797): Protect against out of bounds access to the sprite ptr
peter1138
parents:
5609
diff
changeset
|
446 |
assert(sprite < _spritecache_items); |
0 | 447 |
|
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
448 |
sc = GetSpriteCache(sprite); |
0 | 449 |
|
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
450 |
/* Update LRU */ |
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
451 |
sc->lru = ++_sprite_lru_counter; |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
452 |
|
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
453 |
p = sc->ptr; |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
454 |
|
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
455 |
/* Load the sprite, if it is not loaded, yet */ |
6869
cd04f1d7cad7
(svn r10109) -Fix [FS#838]: some NewGRFs use the same (unused in the "current" climate) sprite IDs. Normally this gives some artefacts, but when one NewGRF expects it to be a sprite and another NewGRF overwrites it with a non-sprite nasty things happen (drawing a non-sprite crashes OTTD).
rubidium
parents:
6865
diff
changeset
|
456 |
if (p == NULL) p = ReadSprite(sc, sprite, real_sprite); |
8562
7419166c16bd
(svn r12140) -Codechange: A bit of code style fixes(Geektoo).
belugas
parents:
8435
diff
changeset
|
457 |
|
184
dbeaaaf8b2bb
(svn r185) -Fix: [1016954] Cached_sprites does now work again
truelight
parents:
182
diff
changeset
|
458 |
return p; |
0 | 459 |
} |
460 |
||
961 | 461 |
|
6247 | 462 |
void GfxInitSpriteMem() |
0 | 463 |
{ |
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
464 |
/* initialize sprite cache heap */ |
8037
8aa4ace04383
(svn r11597) -Change: replace all remaining instances of (re|m|c)alloc with (Re|M|C)allocT and add a check for out-of-memory situations to the *allocT functions.
rubidium
parents:
7927
diff
changeset
|
465 |
if (_spritecache_ptr == NULL) _spritecache_ptr = (MemBlock*)MallocT<byte>(_sprite_cache_size * 1024 * 1024); |
0 | 466 |
|
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
467 |
/* A big free block */ |
6803
9803e56a8d9c
(svn r10042) -Codechange: Replace hardcoded spritecache size with a configuration
peter1138
parents:
6799
diff
changeset
|
468 |
_spritecache_ptr->size = ((_sprite_cache_size * 1024 * 1024) - sizeof(MemBlock)) | S_FREE_MASK; |
6420
456c275f3313
(svn r9556) -Documentation: doxygen and comment-style changes. 'R', 'S'.. The end of the preliminary work is near
belugas
parents:
6248
diff
changeset
|
469 |
/* Sentinel block (identified by size == 0) */ |
1353
c5892a0dadad
(svn r1857) Rewrite parts of the sprite heap. It's functionally equivalent but should be easier to read and maintain.
tron
parents:
1352
diff
changeset
|
470 |
NextBlock(_spritecache_ptr)->size = 0; |
0 | 471 |
|
5504
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
472 |
/* Reset the spritecache 'pool' */ |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
473 |
free(_spritecache); |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
474 |
_spritecache_items = 0; |
a6ef917aa095
(svn r7797) -Codechange: Replace static _sprite_ptr and associated arrays with dynamic array to allow variable number of sprites. This does not change the sprite limit.
peter1138
parents:
5501
diff
changeset
|
475 |
_spritecache = NULL; |
0 | 476 |
|
2340
e18ef06bc59a
(svn r2866) Move all functions and tables which aren't directly involved in managing the sprite heap to a new file gfxinit.c.
tron
parents:
2339
diff
changeset
|
477 |
_compact_cache_counter = 0; |
0 | 478 |
} |