made specification of 'time of day' type according to location possible

This commit is contained in:
Dave White 2004-04-14 21:33:51 +00:00
parent 7c4f86e11d
commit 956ebfdb3c
13 changed files with 204 additions and 73 deletions

View file

@ -3,8 +3,6 @@
id=dawn
name=Dawn
image=Dawn.png
red=-20
green=-20
[/time]
[illuminated_time]
id=morning
@ -49,8 +47,6 @@ lawful_bonus=25
id=dusk
name=Dusk
image=Dusk.png
green=-30
blue=-30
[/time]
[illuminated_time]
id=afternoon
@ -66,16 +62,11 @@ id=first_watch
name=First Watch
image=FirstWatch.png
lawful_bonus=-25
red=-40
green=-40
blue=10
[/time]
[illuminated_time]
id=dusk
name=Dusk
image=Dusk.png
green=-15
blue=-15
[/illuminated_time]
#enddef
@ -85,16 +76,11 @@ id=second_watch
name=Second Watch
image=SecondWatch.png
lawful_bonus=-25
red=-40
green=-40
blue=10
[/time]
[illuminated_time]
id=dusk
name=Dusk
image=Dusk.png
green=-15
blue=-15
[/illuminated_time]
#enddef
@ -109,8 +95,5 @@ lawful_bonus=-25
id=underground
name=Underground
image=UndergroundIllum.png
red=10
green=10
blue=10
[/illuminated_time]
#enddef

View file

@ -1269,7 +1269,7 @@ const time_of_day& timeofday_at(const gamestatus& status,
}
}
return status.get_time_of_day(lighten);
return status.get_time_of_day(lighten,loc);
}
int combat_modifier(const gamestatus& status,

View file

@ -1022,6 +1022,7 @@ std::vector<std::string> config::split(const std::string& val, char c, bool remo
return res;
}
//identical to split(), except it does not split when it otherwise
//would if the previous character was identical to the parameter 'quote'.
//i.e. it does not split quoted commas.
@ -1063,6 +1064,18 @@ std::vector<std::string> config::quoted_split(const std::string& val, char c, bo
return res;
}
std::pair<int,int> config::parse_range(const std::string& str)
{
const std::string::const_iterator dash = std::find(str.begin(),str.end(),'-');
const std::string a(str.begin(),dash);
const std::string b = dash != str.end() ? std::string(dash+1,str.end()) : a;
std::pair<int,int> res(atoi(a.c_str()),atoi(b.c_str()));
if(res.second < res.first)
res.second = res.first;
return res;
}
namespace {
//make sure we regard '\r' and '\n' as a space, since Mac, Unix, and DOS
//all consider these differently.

View file

@ -153,6 +153,7 @@ struct config
static std::vector<std::string> split(const std::string& val, char c=',', bool remove_empty=true);
static std::vector<std::string> quoted_split(const std::string& val, char c=',',
bool remove_empty=true, char quote='\\');
static std::pair<int,int> parse_range(const std::string& str);
static std::string& escape(std::string& str);
static std::string& unescape(std::string& str);
static std::string& strip(std::string& str);

View file

@ -116,7 +116,7 @@ Uint32 display::rgb(Uint8 red, Uint8 green, Uint8 blue)
void display::new_turn()
{
int r,g,b;
/* int r,g,b;
image::get_colour_adjustment(&r,&g,&b);
const time_of_day& tod = status_.get_time_of_day();
@ -140,8 +140,10 @@ void display::new_turn()
SDL_Delay(wanted_ticks - cur_ticks);
}
}
adjust_colours(0,0,0);
*/
const time_of_day& tod = status_.get_time_of_day();
image::set_colour_adjustment(tod.red,tod.green,tod.blue);
image::set_image_mask(tod.image_mask);
}
void display::adjust_colours(int r, int g, int b)
@ -1290,6 +1292,15 @@ void display::draw_tile(int x, int y, SDL_Surface* unit_image, double alpha, Uin
image::TYPE image_type = image::SCALED;
const time_of_day& tod = status_.get_time_of_day();
const time_of_day& tod_at = timeofday_at(status_,units_,loc);
std::string mask;
if(tod.image_mask != tod_at.image_mask) {
std::cerr << "drawing unmasked image at " << (x+1) << "," << (y+1) << "\n";
image_type = image::UNMASKED;
mask = tod_at.image_mask;
}
//find if this tile should be greyed
if(pathsList_ != NULL && pathsList_->routes.find(gamemap::location(x,y)) ==
pathsList_->routes.end()) {
@ -1341,6 +1352,12 @@ void display::draw_tile(int x, int y, SDL_Surface* unit_image, double alpha, Uin
}
}
if(mask != "") {
scoped_sdl_surface img(image::get_image(mask,image::UNMASKED,image::NO_ADJUST_COLOUR));
SDL_Rect dstrect = { xpos, ypos, 0, 0 };
SDL_BlitSurface(img,NULL,dst,&dstrect);
}
if(!is_shrouded) {
draw_footstep(loc,xpos,ypos);
}

View file

@ -205,38 +205,9 @@ private:
const config* cfg_;
};
std::pair<int,int> parse_range(const std::string& str)
{
const std::string::const_iterator dash = std::find(str.begin(),str.end(),'-');
const std::string a(str.begin(),dash);
const std::string b = dash != str.end() ? std::string(dash+1,str.end()) : a;
std::pair<int,int> res(atoi(a.c_str()),atoi(b.c_str()));
if(res.second < res.first)
res.second = res.first;
return res;
}
std::vector<gamemap::location> multiple_locs(const config& cfg)
{
std::vector<gamemap::location> res;
const std::vector<std::string> xvals = config::split(cfg["x"]);
const std::vector<std::string> yvals = config::split(cfg["y"]);
for(unsigned int i = 0; i != minimum(xvals.size(),yvals.size()); ++i) {
const std::pair<int,int> xrange = parse_range(xvals[i]);
const std::pair<int,int> yrange = parse_range(yvals[i]);
std::cerr << "range: " << xrange.first << "-" << xrange.second << "\n";
std::cerr << "range: " << yrange.first << "-" << yrange.second << "\n";
for(int x = xrange.first; x <= xrange.second; ++x) {
for(int y = yrange.first; y <= yrange.second; ++y) {
res.push_back(gamemap::location(x-1,y-1));
}
}
}
return res;
return parse_location_range(cfg["x"],cfg["y"]);
}
std::multimap<std::string,event_handler> events_map;

View file

@ -25,6 +25,7 @@
time_of_day::time_of_day(const config& cfg)
: lawful_bonus(atoi(cfg["lawful_bonus"].c_str())),
image(cfg["image"]), name(cfg["name"]), id(cfg["id"]),
image_mask(cfg["mask"]),
red(atoi(cfg["red"].c_str())),
green(atoi(cfg["green"].c_str())),
blue(atoi(cfg["blue"].c_str()))
@ -52,6 +53,27 @@ void time_of_day::write(config& cfg) const
cfg["image"] = image;
cfg["name"] = name;
cfg["id"] = id;
cfg["mask"] = image_mask;
}
namespace {
void parse_times(const config& cfg, std::vector<time_of_day>& normal_times, std::vector<time_of_day>& illuminated_times)
{
const config::child_list& times = cfg.get_children("time");
config::child_list::const_iterator t;
for(t = times.begin(); t != times.end(); ++t) {
normal_times.push_back(time_of_day(**t));
}
const config::child_list& times_illum = cfg.get_children("illuminated_time");
const config::child_list& illum = times_illum.empty() ? times : times_illum;
for(t = illum.begin(); t != illum.end(); ++t) {
illuminated_times.push_back(time_of_day(**t));
}
}
}
gamestatus::gamestatus(config& time_cfg, int num_turns) :
@ -62,17 +84,18 @@ gamestatus::gamestatus(config& time_cfg, int num_turns) :
turn_ = atoi(turn_at.c_str());
}
const config::child_list& times = time_cfg.get_children("time");
config::child_list::const_iterator t;
for(t = times.begin(); t != times.end(); ++t) {
times_.push_back(time_of_day(**t));
}
parse_times(time_cfg,times_,illuminatedTimes_);
const config::child_list& times_illum = time_cfg.get_children("illuminated_time");
const config::child_list& illum = times_illum.empty() ? times : times_illum;
const config::child_list& times_range = time_cfg.get_children("time_area");
for(config::child_list::const_iterator t = times_range.begin(); t != times_range.end(); ++t) {
const std::vector<gamemap::location> locs = parse_location_range((**t)["x"],(**t)["y"]);
area_time_of_day area;
area.xsrc = (**t)["x"];
area.ysrc = (**t)["y"];
std::copy(locs.begin(),locs.end(),std::inserter(area.hexes,area.hexes.end()));
parse_times(**t,area.times,area.illuminated_times);
for(t = illum.begin(); t != illum.end(); ++t) {
illuminatedTimes_.push_back(time_of_day(**t));
areas_.push_back(area);
}
}
@ -93,10 +116,44 @@ void gamestatus::write(config& cfg) const
for(t = illuminatedTimes_.begin(); t != illuminatedTimes_.end(); ++t) {
t->write(cfg.add_child("illuminated_time"));
}
for(std::vector<area_time_of_day>::const_iterator i = areas_.begin(); i != areas_.end(); ++i) {
config& area = cfg.add_child("time_area");
area["x"] = i->xsrc;
area["y"] = i->ysrc;
for(t = i->times.begin(); t != i->times.end(); ++t) {
t->write(area.add_child("time"));
}
for(t = i->illuminated_times.begin(); t != i->illuminated_times.end(); ++t) {
t->write(area.add_child("illuminated_time"));
}
}
}
const time_of_day& gamestatus::get_time_of_day(bool illuminated) const
const time_of_day& gamestatus::get_time_of_day() const
{
if(times_.empty() == false) {
return times_[(turn()-1)%times_.size()];
} else {
config dummy_cfg;
const static time_of_day default_time(dummy_cfg);
return default_time;
}
}
const time_of_day& gamestatus::get_time_of_day(bool illuminated, const gamemap::location& loc) const
{
for(std::vector<area_time_of_day>::const_iterator i = areas_.begin(); i != areas_.end(); ++i) {
if(i->hexes.count(loc) == 1) {
if(illuminated && i->illuminated_times.empty() == false) {
return i->illuminated_times[(turn()-1)%i->illuminated_times.size()];
} else if(i->times.empty() == false) {
return i->times[(turn()-1)%i->times.size()];
}
}
}
if(illuminated && illuminatedTimes_.empty() == false) {
return illuminatedTimes_[(turn()-1)%illuminatedTimes_.size()];
} else if(times_.empty() == false) {

View file

@ -36,6 +36,10 @@ struct time_of_day
std::string name;
std::string id;
//the image that is to be laid over all images while it's this
//time of day
std::string image_mask;
//the colour modifications that should
//be made to the game board to reflect the time of day.
int red, green, blue;
@ -49,7 +53,8 @@ public:
gamestatus(config& time_cfg, int num_turns);
void write(config& cfg) const;
const time_of_day& get_time_of_day(bool illuminated=false) const;
const time_of_day& get_time_of_day() const;
const time_of_day& get_time_of_day(bool illuminated, const gamemap::location& loc) const;
size_t turn() const;
size_t number_of_turns() const;
@ -83,6 +88,14 @@ public:
private:
std::vector<time_of_day> times_, illuminatedTimes_;
struct area_time_of_day {
std::string xsrc, ysrc;
std::vector<time_of_day> times, illuminated_times;
std::set<gamemap::location> hexes;
};
std::vector<area_time_of_day> areas_;
size_t turn_;
size_t numTurns_;
};

View file

@ -18,10 +18,12 @@ typedef std::map<gamemap::TERRAIN,SDL_Surface*> mini_terrain_cache_map;
mini_terrain_cache_map mini_terrain_cache;
typedef std::map<std::string,SDL_Surface*> image_map;
image_map images_,scaledImages_,greyedImages_,brightenedImages_;
image_map images_,scaledImages_,unmaskedImages_,greyedImages_,brightenedImages_;
int red_adjust = 0, green_adjust = 0, blue_adjust = 0;
std::string image_mask;
SDL_PixelFormat* pixel_format = NULL;
double zoom = 70.0;
@ -68,6 +70,7 @@ void flush_cache()
{
clear_surfaces(images_);
clear_surfaces(scaledImages_);
clear_surfaces(unmaskedImages_);
clear_surfaces(greyedImages_);
clear_surfaces(brightenedImages_);
clear_surfaces(mini_terrain_cache);
@ -126,6 +129,17 @@ void get_colour_adjustment(int *r, int *g, int *b)
}
}
void set_image_mask(const std::string& image)
{
if(image_mask != image) {
image_mask = image;
clear_surfaces(scaledImages_);
clear_surfaces(greyedImages_);
clear_surfaces(brightenedImages_);
}
}
void set_zoom(double amount)
{
if(amount != zoom) {
@ -156,6 +170,15 @@ SDL_Surface* get_image(const std::string& filename, TYPE type, COLOUR_ADJUSTMENT
}
}
if(type == UNMASKED) {
i = unmaskedImages_.find(filename);
if(i != unmaskedImages_.end()) {
result = i->second;
sdl_add_ref(result);
return result;
}
}
i = images_.find(filename);
if(i == images_.end()) {
@ -195,17 +218,41 @@ SDL_Surface* get_image(const std::string& filename, TYPE type, COLOUR_ADJUSTMENT
} else {
const int z = static_cast<int>(zoom);
result = scale_surface(i->second,z,z);
const scoped_sdl_surface scaled_surf(scale_surface(i->second,z,z));
if(result == NULL)
if(scaled_surf == NULL) {
return NULL;
if(adjust_colour == ADJUST_COLOUR) {
const scoped_sdl_surface scoped_surface(result);
result = adjust_surface_colour(result,red_adjust,green_adjust,blue_adjust);
}
scaledImages_.insert(std::pair<std::string,SDL_Surface*>(filename,result));
if(adjust_colour == ADJUST_COLOUR && (red_adjust != 0 || green_adjust != 0 || blue_adjust != 0)) {
const scoped_sdl_surface scoped_surface(result);
result = adjust_surface_colour(scaled_surf,red_adjust,green_adjust,blue_adjust);
} else {
result = clone_surface(scaled_surf);
}
if(result == NULL) {
return NULL;
}
if(type == SCALED && adjust_colour == ADJUST_COLOUR && image_mask != "") {
const scoped_sdl_surface mask(get_image(image_mask,UNMASKED,NO_ADJUST_COLOUR));
if(mask != NULL) {
SDL_SetAlpha(mask,SDL_SRCALPHA|SDL_RLEACCEL,SDL_ALPHA_OPAQUE);
SDL_SetAlpha(result,SDL_SRCALPHA|SDL_RLEACCEL,SDL_ALPHA_OPAQUE);
//commented out pending reply from SDL team about bug report
//SDL_BlitSurface(mask,NULL,result,NULL);
}
} else {
std::cerr << "getting unmasked image...\n";
}
if(type == UNMASKED) {
unmaskedImages_.insert(std::pair<std::string,SDL_Surface*>(filename,result));
} else {
scaledImages_.insert(std::pair<std::string,SDL_Surface*>(filename,result));
}
}
}

View file

@ -44,6 +44,10 @@ namespace image {
//function to get back the current colour adjustment values
void get_colour_adjustment(int *r, int *g, int *b);
//function which sets a certain image as a 'mask' for all scaled images.
//the 'mask' is blitted onto all scaled images.
void set_image_mask(const std::string& image_name);
//sets the pixel format used by the images. Is called every time the
//video mode changes. Invalidates all images.
void set_pixel_format(SDL_PixelFormat* format);
@ -52,7 +56,7 @@ namespace image {
//scaled images.
void set_zoom(double zoom);
enum TYPE { UNSCALED, SCALED, GREYED, BRIGHTENED };
enum TYPE { UNSCALED, SCALED, UNMASKED, GREYED, BRIGHTENED };
enum COLOUR_ADJUSTMENT { ADJUST_COLOUR, NO_ADJUST_COLOUR };

View file

@ -351,3 +351,23 @@ void gamemap::set_terrain(const gamemap::location& loc, gamemap::TERRAIN ter)
tiles_[loc.x][loc.y] = ter;
}
std::vector<gamemap::location> parse_location_range(const std::string& x, const std::string& y)
{
std::vector<gamemap::location> res;
const std::vector<std::string> xvals = config::split(x);
const std::vector<std::string> yvals = config::split(y);
for(unsigned int i = 0; i != minimum(xvals.size(),yvals.size()); ++i) {
const std::pair<int,int> xrange = config::parse_range(xvals[i]);
const std::pair<int,int> yrange = config::parse_range(yvals[i]);
for(int x = xrange.first; x <= xrange.second; ++x) {
for(int y = yrange.first; y <= yrange.second; ++y) {
res.push_back(gamemap::location(x-1,y-1));
}
}
}
return res;
}

View file

@ -153,4 +153,9 @@ private:
mutable std::map<location,TERRAIN> borderCache_;
};
//a utility function which parses ranges of locations
//into a vector of locations
std::vector<gamemap::location> parse_location_range(const std::string& xvals, const std::string& yvals);
#endif

View file

@ -127,8 +127,8 @@ height_map generate_height_map(size_t width, size_t height,
//we have to check whether this is actually a valley
if(island_size != 0) {
const size_t diffx = abs(x1 - center_x);
const size_t diffy = abs(y1 - center_y);
const size_t diffx = abs(x1 - int(center_x));
const size_t diffy = abs(y1 - int(center_y));
const size_t dist = size_t(sqrt(double(diffx*diffx + diffy*diffy)));
is_valley = dist > island_size;
}