1 registered members (AndrewAMD),
946
guests, and 5
spiders. |
Key:
Admin,
Global Mod,
Mod
|
|
|
Re: Blitting multiple Bitmaps with transparent parts?
[Re: Espér]
#376525
07/03/11 23:07
07/03/11 23:07
|
Joined: Oct 2006
Posts: 873
Shadow969
User
|
User
Joined: Oct 2006
Posts: 873
|
i've stripped the code to the bare minimum, to show the basic principle. it's heavily commented and not optimised to make it easier to understand. here it is
#include <acknex.h>
#include <default.c>
//bitmap to be generated
BMAP* map;
//tile bmaps
BMAP* tile1 = "plain001.tga";
BMAP* tile2 = "plain002.tga";
//display for our bitmap
PANEL* viewer =
{
pos_x = 5;
pos_y = 5;
layer = 10;
alpha = 100;
flags = SHOW | TRANSLUCENT;
}
//small utility function to ensure vector components are smaller than a certain value
void vec_trunc(var *vec, var limit)
{
vec[0] = minv(vec[0], limit);
vec[1] = minv(vec[1], limit);
vec[2] = minv(vec[2], limit);
}
//adds feature bitmap to the map at the (X,Y) position. you have to manually lock and unlock bitmaps
void add_bmap(var X, var Y, BMAP *map, var map_format, BMAP *feature, var feature_format)
{
var temp_map_pixel[3];
var temp_feature_pixel[3];
var temp_map_alpha;
var temp_feature_alpha;
var i, j;
for(i = 0; i < bmap_width(feature); i++)
{
for(j = 0; j < bmap_height(feature); j++)
{
//ensure we stay within main bitmap bounds to prevent engine crashing
if(X+i >= bmap_width(map) || Y+j >= bmap_height(map)) continue;
//read map pixel
pixel_to_vec(temp_map_pixel, temp_map_alpha, map_format, pixel_for_bmap(map, X+i, Y+j));
//read feature pixel
pixel_to_vec(temp_feature_pixel, temp_feature_alpha, feature_format, pixel_for_bmap(feature, i, j));
//color mixing in 3 steps
//1.multiply feature pixel's color with normalized alpha
vec_scale(temp_feature_pixel, temp_feature_alpha/100);
//2.add resulting color to the map pixel's color
vec_add(temp_map_pixel, temp_feature_pixel);
//3.check that resulting vector components stay within 0-255 range
vec_trunc(temp_map_pixel, 255);
//write the resulting color to the map
pixel_to_bmap(map, X+i, Y+j, pixel_for_vec(temp_map_pixel, temp_map_alpha, map_format));
}
}
}
void main()
{
level_load(NULL);
wait(3);
//create a blank map
map = bmap_createblack(512, 512, 32);
bmap_fill(map, vector(1,1,1), 100);
viewer.bmap = map;
var i;//our index var
//lock main bitmap
var map_format = bmap_lock(map, 0);
//lock first feature bitmap - called only once instead of locking\unlocking bitmap every time
var feature_format = bmap_lock(tile1, 0);
//add 20 features at random positions
for(i = 0; i < 20; i++)
{
add_bmap(random(bmap_width(map)), random(bmap_height(map)), map, map_format, tile1, feature_format);
}
//we're done with first feature - can unlock it's bitmap
bmap_unlock(tile1);
//do the same routine for the second feature type
var feature_format = bmap_lock(tile2, 0);
for(i = 0; i < 20; i++)
{
add_bmap(random(bmap_width(map)), random(bmap_height(map)), map, map_format, tile2, feature_format);
}
bmap_unlock(tile2);
//unlock main bitmap
bmap_unlock(map);
}
btw your images seem to have a blank alpha channel, so i've made my own dummies. i can upload them somewhere if you want
|
|
|
Re: Blitting multiple Bitmaps with transparent parts?
[Re: Espér]
#376544
07/04/11 10:04
07/04/11 10:04
|
Joined: Mar 2008
Posts: 2,247 Baden Württemberg, Germany
Espér
OP
Expert
|
OP
Expert
Joined: Mar 2008
Posts: 2,247
Baden Württemberg, Germany
|
okay.. tried to implement that to my code..
#include <acknex.h>
#include <d3d9.h>
#include <default.c>
BMAP* map;
BMAP* plain_tile = "plain001.tga";
var plaincount = 0;
var plainmax = 500;
var active = 0;
int pixelcount = 0;
var position[3];
var groundsize = 2048;
STRING* wort = "BILDMENGE ANGEBEN\noder ESC um den Generator\nzu beenden:";
STRING* input = " ";
STRING* bitmapname = "Plain";
STRING* bitmapnumb = "1";
FONT* arial = "Arial#15";
PANEL* viewer =
{
pos_x = 5;
pos_y = 5;
layer = 10;
alpha = 100;
flags = SHOW | TRANSLUCENT;
}
PANEL* infos =
{
pos_x = 730;
pos_y = 50;
layer = 99990;
alpha = 100;
digits(5, 5, "INFOS:", arial, 1, 0);
digits(5, 15, "^^^^^^", arial, 1, 0);
digits(5, 25, "<> Bitmapcount = %.0f", arial, 1, plaincount);
digits(132, 25, "/", arial, 1, 0);
digits(140, 25, 4, arial, 1, plainmax);
digits(5, 115, "PLAIN NAME:", arial, 1, 0);
digits(5, 127, bitmapname, arial, 1,0);
digits(5, 145, "PIXELS SET:", arial, 1, 0);
digits(5, 157, 10, arial, 1,pixelcount);
flags = SHOW | TRANSLUCENT;
}
PANEL* frames =
{
pos_x = 0;
pos_y = 0;
layer = 1;
alpha = 100;
flags = SHOW | TRANSLUCENT;
}
TEXT* txt_input =
{
pos_x = 735;
pos_y = 95;
layer = 99999;
alpha = 100;
font = arial;
string(wort, input);
flags = SHOW | TRANSLUCENT;
}
void vec_trunc(var *vec, var limit)
{
vec[0] = minv(vec[0], limit);
vec[1] = minv(vec[1], limit);
vec[2] = minv(vec[2], limit);
}
void main()
{
video_mode = 8;
d3d_antialias = 9;
wait(1);
video_window(NULL, NULL, (2+16), "Heightmap Generator");
vec_set(sky_color, vector(1,1,1));
vec_set(screen_color, vector(1,1,1));
level_load(NULL);
wait(3);
map = bmap_createblack(groundsize, groundsize, 32);
bmap_fill(map, vector(50,50,50), 100);
viewer.bmap = map;
frames.bmap = bmap_createblack(726, 726, 24);
bmap_fill(frames.bmap, vector(255,255,255), 100);
if(groundsize >= 2048)
{
viewer.scale_x = 0.35;
viewer.scale_y = 0.35;
}
plaincount = 0;
var randompic = 1;
var little_format;
var big_format;
var alphablend;
var alphablend2;
var temp[3];
var temp2[3];
var a = 0;
var b = 0;
while(1)
{
str_cpy(wort, "BILDMENGE ANGEBEN\noder ESC um den generator\nzu beenden:");
str_cpy(input, " ");
inkey(input);
while(inkey_active != 0)
{wait(1);}
if(str_cmpi(input, "esc"))
{break;}
str_cpy(wort, "GEWÄHLTE BILDMENGE:");
plainmax = str_to_num(input);
map = bmap_createblack(groundsize, groundsize, 32);
bmap_fill(map, vector(50,50,50), 100);
viewer.bmap = map;
pixelcount = 0;
plaincount = 0;
big_format = bmap_lock(map, 0);
while(plainmax != 0 && plaincount < plainmax)
{
str_cpy(bitmapname, "Plain");
str_cpy(bitmapnumb, "111");
randompic = integer(random(3)+1);
if(randompic < 10){str_cat(bitmapname, "00");}
else if(randompic < 100){str_cat(bitmapname, "0");}
str_for_num(bitmapnumb, randompic);
str_cat(bitmapname, bitmapnumb);
str_cat(bitmapname, ".tga");
plain_tile = bmap_create(bitmapname);
position[0] = random(bmap_width(map));
position[1] = random(bmap_width(map));
position[2] = 0;
wait(1);
little_format = bmap_lock(plain_tile, 0);
for(a = 0; a<bmap_width(plain_tile); a++)
{
for(b = 0; b<bmap_height(plain_tile); b++)
{
if(position[0]+a >= bmap_width(map) || position[1]+b >= bmap_height(map)) continue;
//read map pixel
pixel_to_vec(temp, alphablend, big_format, pixel_for_bmap(map, position[0]+a, position[1]+b));
//read feature pixel
pixel_to_vec(temp2, alphablend2, little_format, pixel_for_bmap(plain_tile, a, b));
//color mixing in 3 steps
//1.multiply feature pixel's color with normalized alpha
vec_scale(temp2, alphablend2/100);
//2.add resulting color to the map pixel's color
vec_add(temp, temp2);
//3.check that resulting vector components stay within 0-255 range
vec_trunc(temp, 255);
//write the resulting color to the map
pixel_to_bmap(map, position[0]+a, position[1]+b, pixel_for_vec(temp, alphablend, big_format));
pixelcount += 1;
}
}
bmap_unlock(plain_tile);
plaincount += 1;
}
wait(1);
bmap_unlock(map);
}
sys_exit("");
}
But all it does is: - create 1 mini circle - run the complete loop but draw nothing more. so.. it just creates 1 little circle ._. doesn´t matter how many times the while loop runs through..
Last edited by Espér; 07/04/11 16:30.
|
|
|
Re: Blitting multiple Bitmaps with transparent parts?
[Re: Espér]
#376597
07/04/11 20:38
07/04/11 20:38
|
Joined: Oct 2006
Posts: 873
Shadow969
User
|
User
Joined: Oct 2006
Posts: 873
|
you had some logic errors in your code, for example you've recreated map every heightmap recalculation and filled it at wrong time. besides, you load the feature bitmap for every feature, instead of loading all features of type 'a' first, and the features of other types later. i've fixed the errors to make your code work, but you should redesign the structure of your program
#include <acknex.h>
#include <d3d9.h>
#include <default.c>
BMAP* map;
BMAP* plain_tile = "plain001.tga";
var plaincount = 0;
var plainmax = 500;
var active = 0;
int pixelcount = 0;
var position[3];
var groundsize = 2048;
STRING* wort = "BILDMENGE ANGEBEN\noder ESC um den Generator\nzu beenden:";
STRING* input = " ";
STRING* bitmapname = "Plain";
STRING* bitmapnumb = "1";
FONT* arial = "Arial#15";
PANEL* viewer =
{
pos_x = 5;
pos_y = 5;
layer = 10;
alpha = 100;
flags = SHOW | TRANSLUCENT;
}
PANEL* infos =
{
pos_x = 730;
pos_y = 50;
layer = 99990;
alpha = 100;
digits(5, 5, "INFOS:", arial, 1, 0);
digits(5, 15, "^^^^^^", arial, 1, 0);
digits(5, 25, "<> Bitmapcount = %.0f", arial, 1, plaincount);
digits(132, 25, "/", arial, 1, 0);
digits(140, 25, 4, arial, 1, plainmax);
digits(5, 115, "PLAIN NAME:", arial, 1, 0);
digits(5, 127, bitmapname, arial, 1,0);
digits(5, 145, "PIXELS SET:", arial, 1, 0);
digits(5, 157, 10, arial, 1,pixelcount);
flags = SHOW | TRANSLUCENT;
}
PANEL* frames =
{
pos_x = 0;
pos_y = 0;
layer = 1;
alpha = 100;
flags = SHOW | TRANSLUCENT;
}
TEXT* txt_input =
{
pos_x = 735;
pos_y = 95;
layer = 99999;
alpha = 100;
font = arial;
string(wort, input);
flags = SHOW | TRANSLUCENT;
}
void vec_trunc(var *vec, var limit)
{
vec[0] = minv(vec[0], limit);
vec[1] = minv(vec[1], limit);
vec[2] = minv(vec[2], limit);
}
void main()
{
video_mode = 8;
d3d_antialias = 9;
wait(1);
video_window(NULL, NULL, (2+16), "Heightmap Generator");
vec_set(sky_color, vector(1,1,1));
vec_set(screen_color, vector(1,1,1));
level_load(NULL);
wait(3);
map = bmap_createblack(groundsize, groundsize, 32);
bmap_fill(map, vector(50,50,50), 100);
viewer.bmap = map;
frames.bmap = bmap_createblack(726, 726, 24);
bmap_fill(frames.bmap, vector(255,255,255), 100);
if(groundsize >= 2048)
{
viewer.scale_x = 0.35;
viewer.scale_y = 0.35;
}
plaincount = 0;
var randompic = 1;
var little_format;
var big_format;
var alphablend;
var alphablend2;
var temp[3];
var temp2[3];
var a = 0;
var b = 0;
map = bmap_createblack(groundsize, groundsize, 32);
bmap_fill(map, vector(50,50,50), 100);
viewer.bmap = map;
while(1)
{
str_cpy(wort, "BILDMENGE ANGEBEN\noder ESC um den generator\nzu beenden:");
str_cpy(input, " ");
inkey(input);
while(inkey_active != 0)
{wait(1);}
if(str_cmpi(input, "esc"))
{break;}
str_cpy(wort, "GEWÄHLTE BILDMENGE:");
plainmax = str_to_num(input);
pixelcount = 0;
plaincount = 0;
bmap_fill(map, vector(50,50,50), 100);
big_format = bmap_lock(map, 0);
while(plainmax != 0 && plaincount < plainmax)
{
if(random(10) > 5) plain_tile = bmap_create("plain001.tga");//i've changed this part too
else plain_tile = bmap_create("plain002.tga");
position[0] = random(bmap_width(map));
position[1] = random(bmap_width(map));
position[2] = 0;
little_format = bmap_lock(plain_tile, 0);
for(a = 0; a<bmap_width(plain_tile); a++)
{
for(b = 0; b<bmap_height(plain_tile); b++)
{
if(position[0]+a >= bmap_width(map) || position[1]+b >= bmap_height(map)) continue;
//read map pixel
pixel_to_vec(temp, alphablend, big_format, pixel_for_bmap(map, position[0]+a, position[1]+b));
//read feature pixel
pixel_to_vec(temp2, alphablend2, little_format, pixel_for_bmap(plain_tile, a, b));
//color mixing in 3 steps
//1.multiply feature pixel's color with normalized alpha
vec_scale(temp2, alphablend2/100);
//2.add resulting color to the map pixel's color
vec_add(temp, temp2);
//3.check that resulting vector components stay within 0-255 range
vec_trunc(temp, 255);
//write the resulting color to the map
pixel_to_bmap(map, position[0]+a, position[1]+b, pixel_for_vec(temp, alphablend, big_format));
pixelcount += 1;
}
}
bmap_unlock(plain_tile);
plaincount += 1;
}
wait(1);
bmap_unlock(map);
}
sys_exit("");
}
|
|
|
Re: Blitting multiple Bitmaps with transparent parts?
[Re: Shadow969]
#376598
07/04/11 20:47
07/04/11 20:47
|
Joined: Mar 2008
Posts: 2,247 Baden Württemberg, Germany
Espér
OP
Expert
|
OP
Expert
Joined: Mar 2008
Posts: 2,247
Baden Württemberg, Germany
|
That´s cause i will use now 144 different feature bitmaps.. means.. i need them absolutely randomized.. so i need them to be changed for every drawing... means: i need that codepart:
str_cpy(bitmapname, "Plain");
str_cpy(bitmapnumb, "111");
randompic = integer(random(3)+1);
if(randompic < 10){str_cat(bitmapname, "00");}
else if(randompic < 100){str_cat(bitmapname, "0");}
str_for_num(bitmapnumb, randompic);
str_cat(bitmapname, bitmapnumb);
str_cat(bitmapname, ".tga");
plain_tile = bmap_create(bitmapname);
But it works now.. thanks ^^
Last edited by Espér; 07/04/11 20:51.
|
|
|
Re: Blitting multiple Bitmaps with transparent parts?
[Re: Espér]
#376601
07/04/11 21:56
07/04/11 21:56
|
Joined: Apr 2007
Posts: 3,751 Canada
WretchedSid
Expert
|
Expert
Joined: Apr 2007
Posts: 3,751
Canada
|
You can't achive real randomness in software. But if you need a good pseudo algorithm, check out mersenne twister.
Shitlord by trade and passion. Graphics programmer at Laminar Research. I write blog posts at feresignum.com
|
|
|
Re: Blitting multiple Bitmaps with transparent parts?
[Re: Shadow969]
#376626
07/05/11 09:17
07/05/11 09:17
|
Joined: Apr 2007
Posts: 3,751 Canada
WretchedSid
Expert
|
Expert
Joined: Apr 2007
Posts: 3,751
Canada
|
You are probably right, but if he wants good randomness, well he now knows what to implement
Shitlord by trade and passion. Graphics programmer at Laminar Research. I write blog posts at feresignum.com
|
|
|
|