示例#1
0
void mouse_action::set_terrain_mouse_overlay(editor_display& disp, const t_translation::t_terrain & fg,
		const t_translation::t_terrain & bg)
{
	surface image_fg(image::get_image(disp.get_map().get_terrain_info(fg).editor_image()));
	surface image_bg(image::get_image(disp.get_map().get_terrain_info(bg).editor_image()));

	if (image_fg == nullptr || image_bg == nullptr) {
		ERR_ED << "Missing terrain icon" << std::endl;
		disp.set_mouseover_hex_overlay(nullptr);
		return;
	}

	// Create a transparent surface of the right size.
	surface image = create_neutral_surface(image_fg->w, image_fg->h);

	// For efficiency the size of the tile is cached.
	// We assume all tiles are of the same size.
	// The zoom factor can change, so it's not cached.
	// NOTE: when zooming and not moving the mouse, there are glitches.
	// Since the optimal alpha factor is unknown, it has to be calculated
	// on the fly, and caching the surfaces makes no sense yet.
	static const fixed_t alpha = 196;
	static const int size = image_fg->w;
	static const int half_size = size / 2;
	static const int quarter_size = size / 4;
	static const int offset = 2;
	static const int new_size = half_size - 2;

	// Blit left side
	image_fg = scale_surface(image_fg, new_size, new_size);
	SDL_Rect rcDestLeft = sdl::create_rect(offset, quarter_size, 0, 0);
	blit_surface ( image_fg, nullptr, image, &rcDestLeft );

	// Blit right side
	image_bg = scale_surface(image_bg, new_size, new_size);
	SDL_Rect rcDestRight = sdl::create_rect(half_size, quarter_size, 0, 0);
	blit_surface ( image_bg, nullptr, image, &rcDestRight );

	//apply mask so the overlay is contained within the mouseover hex
	image = mask_surface(image, image::get_hexmask());

	// Add the alpha factor
	image = adjust_surface_alpha(image, alpha);

	// scale the image
	const int zoom = disp.hex_size();
	if (zoom != game_config::tile_size) {
		image = scale_surface(image, zoom, zoom);
	}

	// Set as mouseover
	disp.set_mouseover_hex_overlay(image);
}
示例#2
0
void dialog_frame::draw_background()
{
	if(auto_restore_) {
		clear_background();
//		restorer_ = new surface_restorer(&video_, dim_.exterior);
	}

	if (dialog_style_.blur_radius) 
	{
		//surface surf = ::get_surface_portion(video_.getSurface(), dim_.exterior);
		//surf = blur_surface(surf, dialog_style_.blur_radius, false);
		//SDL_BlitSurface(surf, NULL, video_.getSurface(), &dim_.exterior);
		// KP: fade instead of blur...
		SDL_SetRenderDrawColor(0, 0, 0, 0x80);
		SDL_RenderFill(&dim_.exterior);
	}

	if(bg_ == NULL) {
		ERR_DP << "could not find dialog background '" << dialog_style_.panel << "'\n";
		return;
	}
	for(int i = 0; i < dim_.interior.w; i += bg_->w) {
		for(int j = 0; j < dim_.interior.h; j += bg_->h) {
			SDL_Rect src = {0,0,0,0};
			src.w = std::min(dim_.interior.w - i, bg_->w);
			src.h = std::min(dim_.interior.h - j, bg_->h);
			SDL_Rect dst = src;
			dst.x = dim_.interior.x + i;
			dst.y = dim_.interior.y + j;
			//SDL_BlitSurface(bg_, &src, video_.getSurface(), &dst);
			blit_surface(dst.x, dst.y, bg_, &src);
		}
	}
}
示例#3
0
void dialog_frame::draw_border()
{
	if(have_border_ == false) {
		return;
	}

//	surface top_image(scale_surface(top_, dim_.interior.w, top_->h));

//	if(top_image != NULL) 
	{
		//video_.blit_surface(dim_.interior.x, dim_.exterior.y, top_image);
		blit_surface_scaled(dim_.interior.x, dim_.exterior.y, dim_.interior.w, top_->h, top_);
	}

//	surface bot_image(scale_surface(bot_, dim_.interior.w, bot_->h));

//	if(bot_image != NULL) 
	{
		blit_surface_scaled(dim_.interior.x, dim_.interior.y + dim_.interior.h, dim_.interior.w, bot_->h, bot_);
	}

//	surface left_image(scale_surface(left_, left_->w, dim_.interior.h));

//	if(left_image != NULL) 
	{
		blit_surface_scaled(dim_.exterior.x, dim_.interior.y, left_->w, dim_.interior.h, left_);
	}

//	surface right_image(scale_surface(right_, right_->w, dim_.interior.h));

//	if(right_image != NULL) 
	{
		blit_surface_scaled(dim_.interior.x + dim_.interior.w, dim_.interior.y, right_->w, dim_.interior.h, right_);
	}

//	update_rect(dim_.exterior);

	if(top_left_ == NULL || bot_left_ == NULL || top_right_ == NULL || bot_right_ == NULL) {
		return;
	}

	blit_surface(dim_.interior.x - left_->w, dim_.interior.y - top_->h, top_left_);
	blit_surface(dim_.interior.x - left_->w, dim_.interior.y + dim_.interior.h + bot_->h - bot_left_->h, bot_left_);
	blit_surface(dim_.interior.x + dim_.interior.w + right_->w - top_right_->w, dim_.interior.y - top_->h, top_right_);
	blit_surface(dim_.interior.x + dim_.interior.w + right_->w - bot_right_->w, dim_.interior.y + dim_.interior.h + bot_->h - bot_right_->h, bot_right_);
}
surface darken_modification::operator()(const surface &src) const
{
	surface ret = make_neutral_surface(src);
	surface tod_dark(image::get_image(game_config::images::tod_dark));
	if (tod_dark)
		blit_surface(tod_dark, NULL, ret, NULL);
	return ret;
}
surface mask_modification::operator()(const surface& src) const
{
	if(src->w == mask_->w &&  src->h == mask_->h && x_ == 0 && y_ == 0)
		return mask_surface(src, mask_);
	SDL_Rect r = create_rect(x_, y_, 0, 0);
	surface new_mask = create_neutral_surface(src->w, src->h);
	blit_surface(mask_, NULL, new_mask, &r);
	return mask_surface(src, new_mask);
}
示例#6
0
void
WorldObjRenderer::render_sprite(const ResDescriptor& desc,
                                const Vector3f& pos)
{
  Surface surface = Resource::load_surface(desc);

  // FIXME: hack, should take that info from the resource file
  blit_surface(surface, 
               static_cast<int>(pos.x) - surface.get_width()/2,
               static_cast<int>(pos.y) - surface.get_height());
}
示例#7
0
	void multimenu::draw_row(const size_t row_index, const SDL_Rect &rect, menu::ROW_TYPE type) {
		surface img = image::get_image(active_items_[row_index]
									   ? "buttons/checkbox-pressed.png"
									   : "buttons/checkbox.png");
		blit_surface(img, NULL, video().getSurface(), &rect);
		SDL_Rect newrect = {
				Sint16 (rect.x + img->w + 2),
				rect.y,
				Uint16 (rect.w - img->w - 2),
				rect.h
		};
		menu::draw_row(row_index, newrect, type);
	}
示例#8
0
void
WorldObjRenderer::render_surface(const ResDescriptor& desc,
                                 const Vector3f& pos,
                                 int repeat)
{
  Surface surface = Resource::load_surface(desc);
  for(int i = 0; i < repeat; ++i)
  {
    blit_surface(surface, 
                 static_cast<int>(pos.x) + surface.get_width()*i,
                 static_cast<int>(pos.y));
  }
}
示例#9
0
surface background_modification::operator()(const surface &src) const
{
	surface ret = make_neutral_surface(src);
#if SDL_VERSION_ATLEAST(2,0,0)
	SDL_FillRect(ret, NULL, SDL_MapRGBA(ret->format, color_.r, color_.g,
					    color_.b, color_.a));
#else
	SDL_FillRect(ret, NULL, SDL_MapRGBA(ret->format, color_.r, color_.g,
					    color_.b, color_.unused));
#endif
	SDL_SetAlpha(src, SDL_SRCALPHA, SDL_ALPHA_OPAQUE);
	blit_surface(src, NULL, ret, NULL);
	return ret;
}
示例#10
0
surface blit_modification::operator()(const surface& src) const
{
	if(x_ >= src->w) {
		std::stringstream sstr;
		sstr << "~BLIT(): x-coordinate '"
			<< x_ << "' larger than destination image's width '"
			<< src->w << "' no blitting performed.\n";

		throw texception(sstr);
	}

	if(y_ >= src->h) {
		std::stringstream sstr;
		sstr << "~BLIT(): y-coordinate '"
			<< y_ << "' larger than destination image's height '"
			<< src->h << "' no blitting performed.\n";

		throw texception(sstr);
	}

	if(surf_->w + x_ > src->w) {
		std::stringstream sstr;
		sstr << "~BLIT(): offset and width '"
			<< x_ + surf_->w << "' larger than destination image's width '"
			<< src->w << "' no blitting performed.\n";

		throw texception(sstr);
	}

	if(surf_->h + y_ > src->h) {
		std::stringstream sstr;
		sstr << "~BLIT(): offset and height '"
			<< y_ + surf_->h << "' larger than destination image's height '"
			<< src->h << "' no blitting performed.\n";

		throw texception(sstr);
	}

	//blit_surface want neutral surfaces
	surface nsrc = make_neutral_surface(src);
	surface nsurf = make_neutral_surface(surf_);
	SDL_Rect r = create_rect(x_, y_, 0, 0);
	blit_surface(nsurf, NULL, nsrc, &r);
	return nsrc;
}
void mouse_action_village::set_mouse_overlay(editor_display& disp)
{
	surface image60 = image::get_image("icons/action/editor-tool-village_60.png");

	//TODO avoid hardcoded hex field size
	surface image = create_neutral_surface(72,72);

	SDL_Rect r = sdl::create_rect(6, 6, 0, 0);
	blit_surface(image60, NULL, image, &r);

	Uint8 alpha = 196;
	int size = image->w;
	int zoom = static_cast<int>(size * disp.get_zoom_factor());

	// Add the alpha factor and scale the image
	image = scale_surface(adjust_surface_alpha(image, alpha), zoom, zoom);
	disp.set_mouseover_hex_overlay(image);
}
示例#12
0
void menu::imgsel_style::draw_row_bg(menu& menu_ref, const size_t row_index, const SDL_Rect& rect, ROW_TYPE type)
{
	if(type == SELECTED_ROW && has_background_ && !load_failed_) {
		if(bg_cache_.width != rect.w || bg_cache_.height != rect.h)
		{
			//draw scaled background image
			//scale image each time (to prevent loss of quality)
			bg_cache_.surf = scale_surface(img_map_["background"], rect.w, rect.h);
			bg_cache_.width = rect.w;
			bg_cache_.height = rect.h;
		}
		SDL_Rect clip = rect;
		blit_surface(rect.x,rect.y,bg_cache_.surf,NULL,&clip);
	}
	else {
		style::draw_row_bg(menu_ref, row_index, rect, type);
	}
}
示例#13
0
void part_ui::prepare_background()
{
#ifdef SDL_GPU
	base_rect_.w = video_.getx();
	base_rect_.h = video_.gety();
	has_background_ = false;
	bool no_base_yet = true;

	BOOST_FOREACH(const background_layer& bl, p_.get_background_layers()) {
		sdl::timage layer;

		if (!bl.file().empty()) {
			layer = image::get_texture(bl.file());
		}
		has_background_ = has_background_ || !layer.null();
		if(layer.null() || layer.width() * layer.height() == 0) {
			continue;
		}

		const double xscale = 1.0 * video_.getx() / layer.base_width();
		const double yscale = 1.0 * video_.gety() / layer.base_height();
		const bool scalev = bl.scale_vertically();
		const bool scaleh = bl.scale_horizontally();
		const bool keep_ratio = bl.keep_aspect_ratio();
		const bool tileh = bl.tile_horizontally();
		const bool tilev = bl.tile_vertically();

		double x_scale_factor = scaleh ? xscale : 1.0;
		double y_scale_factor = scalev ? yscale : 1.0;

		if (scalev && scaleh && keep_ratio) {
			x_scale_factor = y_scale_factor = std::min<double>(xscale, yscale);
		} else if (keep_ratio && scaleh) {
			x_scale_factor = y_scale_factor = xscale;
		} else if (keep_ratio && scalev) {
			x_scale_factor = y_scale_factor = yscale;
		}

		layer.set_smooth_scaling(true);
		SDL_Rect clip = sdl::create_rect(0, 0, layer.base_width(), layer.base_height());
		if (tileh) {
			clip.x = (layer.base_width() - video_.getx())/2;
			clip.w = video_.getx();
			layer.set_hwrap(GPU_WRAP_REPEAT);
		}
		if (tilev) {
			clip.y = (layer.base_height() - video_.gety())/2;
			clip.h = video_.gety();
			layer.set_vwrap(GPU_WRAP_REPEAT);
		}
		layer.set_clip(clip);
		layer.set_scale(x_scale_factor, y_scale_factor);

		SDL_Rect base_rect = sdl::create_rect(
				  (video_.getx() - layer.width()) / 2
				, (video_.gety() - layer.height()) / 2
				, layer.width()
				, layer.height());

		background_images_.push_back(layer);
		background_positions_.push_back(std::pair<int, int>(base_rect.x, base_rect.y));

		if (bl.is_base_layer() || no_base_yet) {
			x_scale_factor_ = x_scale_factor;
			y_scale_factor_ = y_scale_factor;
			base_rect_ = base_rect;
			no_base_yet = false;
		}
	}
#else
	background_.assign( create_neutral_surface(video_.getx(), video_.gety()) );
	base_rect_.w = video_.getx();
	base_rect_.h = video_.gety();
	has_background_ = false;
	bool no_base_yet = true;

	// Build background surface
	BOOST_FOREACH(const background_layer& bl, p_.get_background_layers()) {
		surface layer;

		if(bl.file().empty() != true) {
			layer.assign( image::get_image(bl.file()) );
		}
		has_background_ = has_background_ || !layer.null();
		if(layer.null() || layer->w * layer->h == 0) {
			continue;
		}

		layer = make_neutral_surface(layer);

		const double xscale = 1.0 * video_.getx() / layer->w;
		const double yscale = 1.0 * video_.gety() / layer->h;
		const bool scalev = bl.scale_vertically();
		const bool scaleh = bl.scale_horizontally();
		const bool keep_ratio = bl.keep_aspect_ratio();

		double x_scale_factor = scaleh ? xscale : 1.0;
		double y_scale_factor = scalev ? yscale : 1.0;

		if (scalev && scaleh && keep_ratio) {
			x_scale_factor = y_scale_factor = std::min<double>(xscale, yscale);
		} else if (keep_ratio && scaleh) {
			x_scale_factor = y_scale_factor = xscale;
		} else if (keep_ratio && scalev) {
			x_scale_factor = y_scale_factor = yscale;
		}

		layer = scale_surface(layer, static_cast<int>(layer->w*x_scale_factor), static_cast<int>(layer->h*y_scale_factor), false);

		const int tilew = bl.tile_horizontally() ? video_.getx() : layer->w;
		const int tileh = bl.tile_vertically() ? video_.gety() : layer->h;

		layer = tile_surface(layer, tilew, tileh, false);

		SDL_Rect drect = sdl::create_rect(
				  (background_->w - layer->w) / 2
				, (background_->h - layer->h) / 2
				, layer->w
				, layer->h);
		SDL_Rect srect = sdl::create_rect(
				  0
				, 0
				, layer->w
				, layer->h);
		SDL_Rect base_rect = drect;

		// If we can't see the whole image anyways, we'll want to display the
		// top-middle area.
		if (drect.y < 0) {
			drect.y = 0;
			base_rect.y = 0;
		}

		if (drect.x < 0) {
			srect.x -= drect.x;
			drect.x = 0;
		}

		blit_surface(layer, &srect, background_, &drect);
		ASSERT_LOG(layer.null() == false, "Oops: a storyscreen part background layer got NULL");

		if (bl.is_base_layer() || no_base_yet) {
			x_scale_factor_ = x_scale_factor;
			y_scale_factor_ = y_scale_factor;
			base_rect_ = base_rect;
			no_base_yet = false;
		}
	}
#endif
}
surface getMinimap(int w, int h, const gamemap &map, const team *vw)
{
	const int scale = 8;

	DBG_DP << "creating minimap " << int(map.w()*scale*0.75) << "," << int(map.h()*scale) << "\n";

	const size_t map_width = map.w()*scale*3/4;
	const size_t map_height = map.h()*scale;
	if(map_width == 0 || map_height == 0) {
		return surface(NULL);
	}

	surface minimap(create_neutral_surface(map_width, map_height));
	if(minimap == NULL)
		return surface(NULL);

	typedef mini_terrain_cache_map cache_map;
	cache_map *normal_cache = &mini_terrain_cache;
	cache_map *fog_cache = &mini_fogged_terrain_cache;

	for(int y = 0; y != map.total_height(); ++y) {
		for(int x = 0; x != map.total_width(); ++x) {

			surface surf(NULL);

			const map_location loc(x,y);
			if(map.on_board(loc)) {
				const bool shrouded = vw != NULL && vw->shrouded(loc);
				// shrouded hex are not considered fogged (no need to fog a black image)
				const bool fogged = vw != NULL && !shrouded && vw->fogged(loc);
				const t_translation::t_terrain terrain = shrouded ?
					t_translation::VOID_TERRAIN : map[loc];

				bool need_fogging = false;

				cache_map* cache = fogged ? fog_cache : normal_cache;
				cache_map::iterator i = cache->find(terrain);

				if (fogged && i == cache->end()) {
					// we don't have the fogged version in cache
					// try the normal cache and ask fogging the image
					cache = normal_cache;
					i = cache->find(terrain);
					need_fogging = true;
				}

				if(i == cache->end()) {
					surface tile(get_image("terrain/" + map.get_terrain_info(terrain).minimap_image() + ".png",image::HEXED));

					if(tile == 0) {
						utils::string_map symbols;
						symbols["terrain"] = t_translation::write_terrain_code(terrain);
						const std::string msg =
							vgettext("Could not get image for terrain: $terrain.", symbols);
						VALIDATE(false, msg);
					}

					//Compose images of base and overlay if neccessary
					if(map.get_terrain_info(terrain).is_combined()) {
						surface overlay(get_image("terrain/" + map.get_terrain_info(terrain).minimap_image_overlay() + ".png", image::HEXED));
						if(overlay != 0 && overlay != tile) {
							surface combined = create_compatible_surface(tile, tile->w, tile->h);
							SDL_Rect r;
							r.x = 0;
							r.y = 0;
							SDL_BlitSurface(tile, NULL, combined, &r);
							r.x = std::max(0, (tile->w - overlay->w)/2);
							r.y = std::max(0, (tile->h - overlay->h)/2);
                            if ((overlay->flags & SDL_RLEACCEL) == 0) {
                                blit_surface(overlay, NULL, combined, &r);
                            } else {
                                WRN_DP << map.get_terrain_info(terrain).minimap_image_overlay() << ".png overlay is RLE-encoded, creating a neutral surface\n";
                                surface overlay_neutral = make_neutral_surface(overlay);
							    blit_surface(overlay_neutral, NULL, combined, &r);
                            }
							tile = combined;
						}

					}

					surf = surface(scale_surface_blended(tile,scale,scale));

					VALIDATE(surf != NULL, _("Error creating or aquiring an image."));

					i = normal_cache->insert(cache_map::value_type(terrain,surf)).first;
				}

				surf = i->second;

				if (need_fogging) {
					surf = surface(adjust_surface_colour(surf,-50,-50,-50));
					fog_cache->insert(cache_map::value_type(terrain,surf));
				}

				VALIDATE(surf != NULL, _("Error creating or aquiring an image."));

				// we need a balanced shift up and down of the hexes.
				// if not, only the bottom half-hexes are clipped
				// and it looks asymmetrical.

				// also do 1-pixel shift because the scaling
				// function seems to do it with its rounding
				SDL_Rect maprect = {x * scale*3/4 - 1,
					y*scale + scale/4 * (is_odd(x) ? 1 : -1) - 1,
					0, 0};
				SDL_BlitSurface(surf, NULL, minimap, &maprect);
			}
		}
	}

	double wratio = w*1.0 / minimap->w;
	double hratio = h*1.0 / minimap->h;
	double ratio = std::min<double>(wratio, hratio);

	minimap = scale_surface(minimap,
		static_cast<int>(minimap->w * ratio), static_cast<int>(minimap->h * ratio));

	DBG_DP << "done generating minimap\n";

	return minimap;
}
示例#15
0
void ttext::draw(surface& canvas
		, const game_logic::map_formula_callable& variables)
{
	assert(variables.has_key("text"));

	// We first need to determine the size of the text which need the rendered
	// text. So resolve and render the text first and then start to resolve
	// the other formulas.
	const t_string text = text_(variables);

	if(text.empty()) {
		DBG_GUI_D << "Text: no text to render, leave.\n";
		return;
	}

	static font::ttext text_renderer;
	text_renderer.set_text(text, text_markup_(variables));

	text_renderer.set_font_size(font_size_)
			.set_font_style(font_style_)
			.set_alignment(text_alignment_(variables))
			.set_foreground_color(color_)
			.set_maximum_width(maximum_width_(variables))
			.set_maximum_height(maximum_height_(variables))
			.set_ellipse_mode(variables.has_key("text_wrap_mode")
				? static_cast<PangoEllipsizeMode>
					(variables.query_value("text_wrap_mode").as_int())
				: PANGO_ELLIPSIZE_END);

	surface surf = text_renderer.render();
	if(surf->w == 0) {
		DBG_GUI_D  << "Text: Rendering '"
				<< text << "' resulted in an empty canvas, leave.\n";
		return;
	}

	game_logic::map_formula_callable local_variables(variables);
	local_variables.add("text_width", variant(surf->w));
	local_variables.add("text_height", variant(surf->h));
/*
	std::cerr << "Text: drawing text '" << text
		<< " maximum width " << maximum_width_(variables)
		<< " maximum height " << maximum_height_(variables)
		<< " text width " << surf->w
		<< " text height " << surf->h;
*/
	///@todo formulas are now recalculated every draw cycle which is a
	// bit silly unless there has been a resize. So to optimize we should
	// use an extra flag or do the calculation in a separate routine.

	const unsigned x = x_(local_variables);
	const unsigned y = y_(local_variables);
	const unsigned w = w_(local_variables);
	const unsigned h = h_(local_variables);

	DBG_GUI_D << "Text: drawing text '" << text
			<< "' drawn from " << x << ',' << y
			<< " width " << w << " height " << h
			<< " canvas size " << canvas->w << ',' << canvas->h << ".\n";

	VALIDATE(static_cast<int>(x) < canvas->w && static_cast<int>(y) < canvas->h
			, _("Text doesn't start on canvas."));

	// A text might be to long and will be clipped.
	if(surf->w > static_cast<int>(w)) {
		WRN_GUI_D << "Text: text is too wide for the "
				"canvas and will be clipped.\n";
	}

	if(surf->h > static_cast<int>(h)) {
		WRN_GUI_D << "Text: text is too high for the "
				"canvas and will be clipped.\n";
	}

	SDL_Rect dst = ::create_rect(x, y, canvas->w, canvas->h);
	blit_surface(surf, 0, canvas, &dst);
}
示例#16
0
void timage::draw(surface& canvas
		, const game_logic::map_formula_callable& variables)
{
	DBG_GUI_D << "Image: draw.\n";

	/**
	 * @todo formulas are now recalculated every draw cycle which is a  bit
	 * silly unless there has been a resize. So to optimize we should use an
	 * extra flag or do the calculation in a separate routine.
	 */
	const std::string& name = image_name_(variables);

	if(name.empty()) {
		DBG_GUI_D << "Image: formula returned no value, will not be drawn.\n";
		return;
	}

	/*
	 * The locator might return a different surface for every call so we can't
	 * cache the output, also not if no formula is used.
	 */
	surface tmp(image::get_image(image::locator(name)));

	if(!tmp) {
		ERR_GUI_D << "Image: '" << name << "' not found and won't be drawn.\n";
		return;
	}

	image_.assign(make_neutral_surface(tmp));
	assert(image_);
	src_clip_ = ::create_rect(0, 0, image_->w, image_->h);

	game_logic::map_formula_callable local_variables(variables);
	local_variables.add("image_original_width", variant(image_->w));
	local_variables.add("image_original_height", variant(image_->h));

	unsigned w = w_(local_variables);
	VALIDATE_WITH_DEV_MESSAGE(
			  static_cast<int>(w) >= 0
			, _("Image doesn't fit on canvas.")
			, (formatter() << "Image '" << name
				<< "', w = " << static_cast<int>(w) << ".").str());

	unsigned h = h_(local_variables);
	VALIDATE_WITH_DEV_MESSAGE(
			  static_cast<int>(h) >= 0
			, _("Image doesn't fit on canvas.")
			, (formatter() << "Image '" << name
				<< "', h = " << static_cast<int>(h) << ".").str());

	local_variables.add("image_width", variant(w ? w : image_->w));
	local_variables.add("image_height", variant(h ? h : image_->h));

	const unsigned x = x_(local_variables);
	VALIDATE_WITH_DEV_MESSAGE(
			  static_cast<int>(x) >= 0
			, _("Image doesn't fit on canvas.")
			, (formatter() << "Image '" << name
				<< "', x = " << static_cast<int>(x) << ".").str());

	const unsigned y = y_(local_variables);
	VALIDATE_WITH_DEV_MESSAGE(
			  static_cast<int>(y) >= 0
			, _("Image doesn't fit on canvas.")
			, (formatter() << "Image '" << name
				<< "', y = " << static_cast<int>(y) << ".").str());

	// Copy the data to local variables to avoid overwriting the originals.
	SDL_Rect src_clip = src_clip_;
	SDL_Rect dst_clip = ::create_rect(x, y, 0, 0);
	surface surf;

	// Test whether we need to scale and do the scaling if needed.
	if(w || h) {
		bool done = false;
		bool stretch_image = (resize_mode_ == stretch) && (!!w ^ !!h);
		if(!w) {
			if(stretch_image) {
				DBG_GUI_D << "Image: vertical stretch from " << image_->w
						<< ',' << image_->h << " to a height of " << h << ".\n";

				surf = stretch_surface_vertical(image_, h, false);
				done = true;
			}
			w = image_->w;
		}

		if(!h) {
			if(stretch_image) {
				DBG_GUI_D << "Image: horizontal stretch from " << image_->w
						<< ',' << image_->h << " to a width of " << w << ".\n";

				surf = stretch_surface_horizontal(image_, w, false);
				done = true;
			}
			h = image_->h;
		}

		if(!done) {

			if(resize_mode_ == tile) {
				DBG_GUI_D << "Image: tiling from " << image_->w
						<< ',' << image_->h << " to " << w << ',' << h << ".\n";

				const int columns = (w + image_->w - 1) / image_->w;
				const int rows = (h + image_->h - 1) / image_->h;
				surf = create_neutral_surface(w, h);

				for(int x = 0; x < columns; ++x) {
					for(int y = 0; y < rows; ++y) {
						const SDL_Rect dest = ::create_rect(
								  x * image_->w
								, y * image_->h
								, 0
								, 0);
						blit_surface(image_, NULL, surf, &dest);
					}
				}

			} else {
				if(resize_mode_ == stretch) {
					ERR_GUI_D << "Image: failed to stretch image, "
							"fall back to scaling.\n";
				}

				DBG_GUI_D << "Image: scaling from " << image_->w
						<< ',' << image_->h << " to " << w << ',' << h << ".\n";

				surf = scale_surface(image_, w, h, false);
			}
		}
		src_clip.w = w;
		src_clip.h = h;
	} else {
		surf = image_;
	}

	if(vertical_mirror_(local_variables)) {
		surf = flip_surface(surf, false);
	}

	blit_surface(surf, &src_clip, canvas, &dst_clip);
}
示例#17
0
文件: menu.cpp 项目: dodikk/iWesnoth
void menu::draw_row(const size_t row_index, const SDL_Rect& rect, ROW_TYPE type)
{
	//called from style, draws one row's contents in a generic and adaptable way
	const std::vector<std::string>& row = (type == HEADING_ROW) ? heading_ : items_[row_index].fields;
	SDL_Rect const &area = screen_area();
	SDL_Rect const &loc = inner_location();
	const std::vector<int>& widths = column_widths();
	bool lang_rtl = current_language_rtl();
	int dir = (lang_rtl) ? -1 : 1;
	SDL_Rect column = loc;

	int xpos = rect.x;
	if(lang_rtl)
		xpos += rect.w;
	for(size_t i = 0; i != row.size(); ++i) {

		if(lang_rtl)
			xpos -= widths[i];
		if(type == HEADING_ROW && highlight_heading_ == int(i)) {
			//draw_solid_tinted_rectangle(xpos,rect.y,widths[i],rect.h,255,255,255,0.3); //,video().getSurface());
		}

		const int last_x = xpos;
		column.w = widths[i];
		std::string str = row[i];
		std::vector<std::string> img_text_items = utils::split(str, IMG_TEXT_SEPARATOR);
		for (std::vector<std::string>::const_iterator it = img_text_items.begin();
			 it != img_text_items.end(); it++) {
			str = *it;
			if (!str.empty() && str[0] == IMAGE_PREFIX) {
				const std::string image_name(str.begin()+1,str.end());
				const surface img = style_->get_item_image(image_name);
				const int remaining_width = max_width_ < 0 ? area.w :
				std::min<int>(max_width_, ((lang_rtl)? xpos - rect.x : rect.x + rect.w - xpos));
				if(img != NULL && img->w <= remaining_width
				&& rect.y + img->h < area.h) {
					const size_t y = rect.y + (rect.h - img->h)/2;
					const size_t w = img->w + 5;
					const size_t x = xpos + ((lang_rtl) ? widths[i] - w : 0);
					blit_surface(x,y,img);
					if(!lang_rtl)
						xpos += w;
					column.w -= w;
				}
			} else {
				column.x = xpos;
				const bool has_wrap = (str.find_first_of("\r\n") != std::string::npos);
				//prevent ellipsis calculation if there is any line wrapping
				const std::string to_show =
					(use_ellipsis_ && !has_wrap) ?
						font::make_text_ellipsis(str, style_->get_font_size(),
							loc.w - (xpos - rect.x) - 2*style_->get_thickness(), false, true).get()
						: str;
				const SDL_Rect& text_size = font::text_area(str,style_->get_font_size());
				const size_t y = rect.y + (rect.h - text_size.h)/2;
				font::draw_text(&video(),column,style_->get_font_size(),font::NORMAL_COLOUR,to_show,xpos,y);

				if(type == HEADING_ROW && sortby_ == int(i)) {
					const surface sort_img = image::get_image(sortreversed_ ? "misc/sort-arrow.png" :
					                                   "misc/sort-arrow-reverse.png");
					if(sort_img != NULL && sort_img->w <= widths[i] && sort_img->h <= rect.h) {
						const size_t sort_x = xpos + widths[i] - sort_img->w;
						const size_t sort_y = rect.y + rect.h/2 - sort_img->h/2;
						blit_surface(sort_x,sort_y,sort_img);
					}
				}

				xpos += dir * (text_size.w + 5);
			}
		}
		if(lang_rtl)
			xpos = last_x;
		else
			xpos = last_x + widths[i];
	}
}
示例#18
0
文件: about.cpp 项目: dodikk/iWesnoth
/**
 * Show credits with list of contributors.
 *
 * Names of people are shown scrolling up like in movie-credits.\n
 * Uses map from wesnoth or campaign as background.
 */
void show_about(display &disp, std::string campaign)
{
	cursor::set(cursor::WAIT);
	CVideo &video = disp.video();
//	surface screen = video.getSurface();
//	if (screen == NULL) return;

	std::vector<std::string> text = about::get_text(campaign);
//	SDL_Rect screen_rect = {0, 0, video.getx(), video.gety()};

//	const surface_restorer restorer(&video, screen_rect);

	cursor::set(cursor::NORMAL);

	std::vector<shared_string> image_list;
	if(campaign.size() && !images[campaign].empty()){
		image_list=utils::split_shared(images[campaign]);
	}else{
		image_list=utils::split_shared(images_default,',',utils::STRIP_SPACES);
	}
	surface map_image(scale_surface(image::get_image(image_list[0]), video.getx(), video.gety()));
	if(! map_image){
		image_list[0]=game_config::game_title;
		map_image=surface(scale_surface(image::get_image(image_list[0]), video.getx(), video.gety()));
	}

	gui::button close(video,_("Close"));
	close.set_location((video.getx()/2)-(close.width()/2), video.gety() - 30);
	close.set_volatile(true);

	const int def_size = font::SIZE_XLARGE;
	const SDL_Color def_color = font::NORMAL_COLOUR;

	//substitute in the correct control characters for '+' and '-'
	std::string before_header(2, ' ');
	before_header[0] = font::LARGE_TEXT;
	for(unsigned i = 0; i < text.size(); ++i) {
		std::string &s = text[i];
		if (s.empty()) continue;
		char &first = s[0];
		if (first == '-')
			first = font::SMALL_TEXT;
		else if (first == '+') {
			first = font::LARGE_TEXT;
			text.insert(text.begin() + i, before_header);
			++i;
		}
	}
	text.insert(text.begin(), 10, before_header);

	int startline = 0;

	//TODO: use values proportionnal to screen ?
	// distance from top of map image to top of scrolling text
	const int top_margin = 60;
	// distance from bottom of scrolling text to bottom of map image
	const int bottom_margin = 40;
	// distance from left of scrolling text to the frame border
	const int text_left_padding = video.getx()/32;

	int offset = 0;
	bool is_new_line = true;

	int first_line_height = 0;

	SDL_Rect frame_area = {
		video.getx() * 3/32,
		top_margin,
		video.getx() * 13 / 16,
		video.gety() - top_margin - bottom_margin
	};

	// we use a dialog to contains the text. Strange idea but at least the style
	// will be consistent with the titlescreen
	gui::dialog_frame f(video, "", gui::dialog_frame::titlescreen_style, false);

	// set the layout and get the interior rectangle
	SDL_Rect text_rect = f.layout(frame_area).interior;
	text_rect.x += text_left_padding;
	text_rect.w -= text_left_padding;
	// make a copy to prevent SDL_blit to change its w and h
	SDL_Rect text_rect_blit = text_rect;

	CKey key;
	bool last_escape;

	surface text_surf = create_neutral_surface(text_rect.w, text_rect.h); //create_compatible_surface(screen, text_rect.w, text_rect.h);
	SDL_SetAlpha(text_surf, SDL_RLEACCEL, SDL_ALPHA_OPAQUE);

	int image_count = 0;
	int scroll_speed = 4;	// scroll_speed*50 = speed of scroll in pixel per second

	// initialy redraw all
	bool redraw_mapimage = true;
	int max_text_width = text_rect.w;

	do {
		last_escape = key[SDLK_ESCAPE] != 0;

		// check to see if background image has changed
		if(text.size() && (image_count <
				((startline * static_cast<int>(image_list.size())) /
				static_cast<int>(text.size())))){

			image_count++;
			surface temp=surface(scale_surface(image::get_image(image_list[image_count]), video.getx(), video.gety()));
			map_image=temp?temp:map_image;
			redraw_mapimage = true;
		}

//		if (redraw_mapimage) 
		{
			// draw map to screen, thus erasing all text
			//SDL_BlitSurface(map_image, NULL, screen, NULL);
			blit_surface(0, 0, map_image);
//			update_rect(screen_rect);

			// redraw the dialog
			f.draw_background();
			f.draw_border();
			// cache the dialog background (alpha blending + blurred map)
			//SDL_BlitSurface(screen, &text_rect, text_surf, NULL);
			redraw_mapimage = false;
		} 
/*		else {
			// redraw the saved part of the dialog where text scrolled
			// thus erasing all text
			SDL_Rect modified = {0,0, max_text_width, text_rect.h};
			SDL_BlitSurface(text_surf, &modified, screen, &text_rect_blit);
			//update_rect(text_rect);
		}
*/
		const int line_spacing = 5;

		int y = text_rect.y - offset;
		int line = startline;
		int cur_line = 0;
		max_text_width = 0;

		{
		// clip to keep text into the frame (thus the new code block)
		clip_rect_setter set_clip_rect(/*screen,*/ text_rect);
			do {
				// draw the text (with ellipsis if needed)
				// update the max_text_width for future cleaning
				int w = font::draw_text(&video, text_rect, def_size, def_color,
										text[line], text_rect.x, y).w;
				max_text_width = std::max<int>(max_text_width, w);
				// since the real drawing on screen is clipped,
				// we do a dummy one to get the height of the not clipped line.
				// (each time because special format characters may change it)
				const int line_height = font::draw_text(NULL, text_rect, def_size, def_color,
										text[line], 0,0).h;

				if(is_new_line) {
					is_new_line = false;
					first_line_height = line_height + line_spacing;
				}
				line++;
				if(size_t(line) > text.size()-1)
					line = 0;
				y += line_height + line_spacing;
				cur_line++;
			} while(y < text_rect.y + text_rect.h);
		}

		// performs the actual scrolling
		offset += scroll_speed;
		if (offset>=first_line_height) {
			offset -= first_line_height;
			is_new_line = true;
			startline++;
			if(size_t(startline) == text.size()){
				startline = 0;
				image_count = -1;
			}
		}

		// handle events
		if (key[SDLK_UP] && scroll_speed < 20) {
			++scroll_speed;
		}
		if (key[SDLK_DOWN] && scroll_speed > 0) {
			--scroll_speed;
		}

		events::pump();
		events::raise_process_event();
		events::raise_draw_event();

		// flip screen and wait, so the text does not scroll too fast
		disp.flip();
		disp.delay(20);

	} while(!close.pressed() && (last_escape || !key[SDLK_ESCAPE]));
}
示例#19
0
/* renders a window struct to the screen */
void gui_show_window(gui_window *window) {
	SDL_Rect src, rect;
	int i, j, hor_pixels_needed, hor_iterations_needed, ver_pixels_needed, ver_iterations_needed;

	assert(window);

	if (!window->visible)
		return;

	/* render background */
	src.x = 0;
	src.y = 0;
	src.w = background->w;
	src.h = background->h;

	hor_pixels_needed = window->w - b1->w - b3->w;
	hor_iterations_needed = hor_pixels_needed / background->w;
	hor_pixels_needed -= (hor_iterations_needed * background->w);

	ver_pixels_needed = window->h - b1->h - b6->h;
	ver_iterations_needed = ver_pixels_needed / background->h;
	ver_pixels_needed -= (ver_iterations_needed * background->h);

	for (j = 0; j < ver_iterations_needed; j++) {
		for (i = 0; i < hor_iterations_needed; i++) {
			rect.x = window->x + b1->w;
			rect.y = window->y + b1->h;
			rect.w = window->w - b1->w - b3->w;
			rect.h = window->h - b6->h - b1->h;

			rect.x += (i * background->w);
			rect.y += (j * background->h);

			blit_surface(background, &src, &rect, 0);
		}
	}

	/* draw any left over background (the extra pixels_needed) */
	for (j = 0; j < ver_iterations_needed; j++) {
		src.w = hor_pixels_needed;
		rect.x = window->x + b1->w;
		rect.y = window->y + b1->h;
		rect.w = hor_pixels_needed;
		rect.h = background->h;

		rect.x += (hor_iterations_needed * background->w);
		rect.y += (j * background->h);

		blit_surface(background, &src, &rect, 0);
	}
	for (i = 0; i < hor_iterations_needed; i++) {
		src.w = background->w;
		src.h = ver_pixels_needed;
		rect.x = window->x + b1->w;
		rect.y = window->y + b1->h;
		rect.w = background->w;
		rect.h = ver_pixels_needed;

		rect.x += (i * background->w);
		rect.y += (ver_iterations_needed * background->h);

		blit_surface(background, &src, &rect, 0);
	}

	/* finish that last square */
	src.w = hor_pixels_needed;
	src.h = ver_pixels_needed;
	rect.x = window->x + b1->w;
	rect.y = window->y + b1->h;
	rect.w = hor_pixels_needed;
	rect.h = ver_pixels_needed;
	rect.x += (hor_iterations_needed * background->w);
	rect.y += (ver_iterations_needed * background->h);
	blit_surface(background, &src, &rect, 0);

	/* render upper left corner */
	rect.x = window->x;
	rect.y = window->y;
	rect.w = b1->w;
	rect.h = b1->h;

	blit_surface(b1, NULL, &rect, 0);

	/* render upper border, repeating if necessary */
	{
		int pixels_needed, iterations_needed;
		int i;

		pixels_needed = window->w - b1->w - b3->w;

		iterations_needed = pixels_needed / b2->w;

		pixels_needed -= (iterations_needed * b2->w);

		src.x = 0;
		src.y = 0;
		src.w = b2->w;
		src.h = b2->h;

		for (i = 0; i < iterations_needed; i++) {
			rect.x = window->x + b1->w;
			rect.y = window->y;
			rect.w = b2->w;
			rect.h = b2->h;

			rect.x += (i * b2->w);

			blit_surface(b2, &src, &rect, 0);
		}

		/* do left over pixels here */
		if (pixels_needed) {
			src.w = pixels_needed;
			rect.x = window->x + b1->w;
			rect.y = window->y;
			rect.w = pixels_needed;
			rect.h = b2->h;

			rect.x += (i * b2->w);

			blit_surface(b2, &src, &rect, 0);
		}
	}

	/* render upper right corner */
	rect.x = window->x + window->w - b3->w;
	rect.y = window->y;
	rect.w = b3->w;
	rect.h = b3->h;

	blit_surface(b3, NULL, &rect, 0);

	/* render left border, repeating if necessary */
	{
		int pixels_needed, iterations_needed;
		int i;

		pixels_needed = window->h - b1->h - b6->h;

		iterations_needed = pixels_needed / b4->h;

		pixels_needed -= (iterations_needed * b4->h);

		src.x = 0;
		src.y = 0;
		src.w = b4->w;
		src.h = b4->h;

		for (i = 0; i < iterations_needed; i++) {
			rect.x = window->x;
			rect.y = window->y + b1->h;
			rect.w = b4->w;
			rect.h = b4->h;

			rect.y += (i * b4->h);

			blit_surface(b4, &src, &rect, 0);
		}

		/* do left over pixels here */
		if (pixels_needed) {
			src.h = pixels_needed;
			rect.x = window->x;
			rect.y = window->y + b1->h;
			rect.w = b4->w;
			rect.h = pixels_needed;

			rect.y += (i * b4->h);

			blit_surface(b4, &src, &rect, 0);
		}
	}

	/* render right border, repeating if necessary */
	{
		int pixels_needed, iterations_needed;
		int i;

		pixels_needed = window->h - b3->h - b8->h;

		iterations_needed = pixels_needed / b5->h;

		pixels_needed -= (iterations_needed * b5->h);

		src.x = 0;
		src.y = 0;
		src.w = b5->w;
		src.h = b5->h;

		for (i = 0; i < iterations_needed; i++) {
			rect.x = window->x + window->w - b5->w;
			rect.y = window->y + b3->h;
			rect.w = b5->w;
			rect.h = b5->h;

			rect.y += (i * b5->h);

			blit_surface(b5, &src, &rect, 0);
		}

		/* do left over pixels here */
		if (pixels_needed) {
			src.h = pixels_needed;
			rect.x = window->x + window->w - b5->w;
			rect.y = window->y + b1->h;
			rect.w = b5->w;
			rect.h = pixels_needed;

			rect.y += (i * b5->h);

			blit_surface(b5, &src, &rect, 0);
		}
	}

	/* render lower left corner */
	rect.x = window->x;
	rect.y = window->y + window->h - b6->h;
	rect.w = b6->w;
	rect.h = b6->h;

	blit_surface(b6, NULL, &rect, 0);

	/* render lower border, repeating if necessary */
	{
		int pixels_needed, iterations_needed;
		int i;

		pixels_needed = window->w - b6->w - b8->w;

		iterations_needed = pixels_needed / b7->w;

		pixels_needed -= (iterations_needed * b7->w);

		src.x = 0;
		src.y = 0;
		src.w = b7->w;
		src.h = b7->h;

		for (i = 0; i < iterations_needed; i++) {
			rect.x = window->x + b6->w;
			rect.y = window->y + window->h - b7->h;
			rect.w = b7->w;
			rect.h = b7->h;

			rect.x += (i * b7->w);

			blit_surface(b7, &src, &rect, 0);
		}

		/* do left over pixels here */
		if (pixels_needed) {
			src.w = pixels_needed;
			rect.x = window->x + b1->w;
			rect.y = window->y + window->h - b7->h;
			rect.w = pixels_needed;
			rect.h = b7->h;

			rect.x += (i * b7->w);

			blit_surface(b7, &src, &rect, 0);
		}
	}

	/* render lower right corner */
	rect.x = window->x + window->w - b8->w;
	rect.y = window->y + window->h - b8->h - 1; /* -1 ? it was off .... ? */
	rect.w = b8->w;
	rect.h = b8->h;

	blit_surface(b8, NULL, &rect, 0);
}
示例#20
0
void loadscreen::set_progress(const int percentage, const std::string &text, const bool commit)
{
	
	if (gRedraw)
	{
		gRedraw = false;
		logo_drawn_ = false;
	}
	
	// Saturate percentage.
	prcnt_ = percentage < MIN_PERCENTAGE ? MIN_PERCENTAGE: percentage > MAX_PERCENTAGE ? MAX_PERCENTAGE: percentage;
	// Set progress bar parameters:
	int fcr =  21, fcg =  53, fcb =  80;		// RGB-values for finished piece.
	int lcr =  21, lcg =  22, lcb =  24;		// Leftover piece.
	//int bcr = 188, bcg = 176, bcb = 136;		// Border color.
	int bcr = 104, bcg = 74, bcb = 28;			// Border color.
	int bw = 1;								//< Border width.
	int bispw = 1;								//< Border inner spacing width.
	bw = 2*(bw+bispw) > screen_.getx() ? 0: 2*(bw+bispw) > screen_.gety() ? 0: bw;
	int scrx = screen_.getx() - 2*(bw+bispw);	//< Available width.
	int scry = screen_.gety() - 2*(bw+bispw);	//< Available height.
	int pbw = scrx/2;							//< Used width.
	int pbh = scry/16;							//< Used heigth.
	int	lightning_thickness = 2;

//	surface const gdis = screen_.getSurface();
	SDL_Rect area;
	
	// Clear the last text and draw new if text is provided.
//	if(text.length() > 0 && commit)
//	{
//		logo_drawn_ = false;
//	}
	
	bool updateFull = false;
	
	
	// Draw logo if it was succesfully loaded.
//	if (logo_surface_ && !logo_drawn_) 
	if (!logo_drawn_)
	{
/*		
		area.x = (screen_.getx () - logo_surface_->w) / 2;
		area.y = ((scry - logo_surface_->h) / 2) - pbh;
		area.w = logo_surface_->w;
		area.h = logo_surface_->h;
		// Check if we have enough pixels to display it.
		if (area.x > 0 && area.y > 0) {
			pby_offset_ = (pbh + area.h)/2;
			SDL_BlitSurface (logo_surface_, 0, gdis, &area);
		} else {
			ERR_DISP << "loadscreen: Logo image is too big." << std::endl;
		}
*/
		area.x = 0;
		area.y = 0;
		//area.w = logo_surface_->w;
		//area.h = logo_surface_->h;
		//SDL_BlitSurface (logo_surface_, 0, gdis, &area);		
		//screen_.blit_surface(0, 0, logo_surface_);
		GLshort vertices[12];
		GLfloat texCoords[8];
		
#ifdef __IPAD__
		int size = 1024;
#else
		int size = 512;
#endif
		
		vertices[0] = 0;
		vertices[1] = 0;
		vertices[2] = 0;
		vertices[3] = size;
		vertices[4] = 0;
		vertices[5] = 0;
		vertices[6] = 0;
		vertices[7] = size;
		vertices[8] = 0;
		vertices[9] = size;
		vertices[10] = size;
		vertices[11] = 0;

		texCoords[0] = 0;
		texCoords[1] = 0;
		texCoords[2] = 1;
		texCoords[3] = 0;
		texCoords[4] = 0;
		texCoords[5] = 1;
		texCoords[6] = 1;
		texCoords[7] = 1;
		renderQueueAddTexture(vertices, texCoords, logo_texture_, 0xFFFFFFFF, 1.0);
		
		//	glVertexPointer(3, GL_SHORT, 0, vertices);
		//	glTexCoordPointer(2, GL_FLOAT, 0, texCoords);
		//	glDrawArrays(GL_TRIANGLE_STRIP, 0, 4);
		
		//SDL_RenderCopy(logo_texture_, NULL, NULL,DRAW);
		//SDL_RenderPresent();
		//SDL_UpdateRect(gdis, area.x, area.y, area.w, area.h);
		
		// draw logo over everything
#ifdef __IPAD__
		std::string path = game_config::path + "/data/core/images/misc/logo.png";
		surface logo_surface = IMG_Load(path.c_str());
		blit_surface((1024-logo_surface.get()->w)/2, -10, logo_surface);
		
		
		SDL_Rect tip_area = {690, 306, 225, 140};
		draw_tip_of_day(screen_, tips_of_day, gui::dialog_frame::titlescreen_style,&tip_area);		
#else
		std::string path = game_config::path + "/data/core/images/misc/logo_small.png";
		surface logo_surface = IMG_Load(path.c_str());
		blit_surface((480-logo_surface.get()->w)/2, -10, logo_surface);
		

		SDL_Rect tip_area = {242, 100, 225, 140};
		draw_tip_of_day(screen_, tips_of_day, gui::dialog_frame::titlescreen_style,&tip_area);
#endif

		logo_drawn_ = true;

		updateFull = true;
	}
	
	int pbx = (scrx - pbw)/2;					// Horizontal location.
#ifdef __IPAD__	
	int pby = 693;
#else
	int pby = 276; //(scry - pbh)/2 + pby_offset_;		// Vertical location.
#endif

	// Draw top border.
	area.x = pbx; area.y = pby;
	area.w = pbw + 2*(bw+bispw); area.h = bw;
//	SDL_FillRect(gdis,&area,SDL_MapRGB(gdis->format,bcr,bcg,bcb));
	SDL_SetRenderDrawColor(bcr, bcg, bcb, 0xff);
	SDL_RenderFill(&area);
	// Draw bottom border.
	area.x = pbx; area.y = pby + pbh + bw + 2*bispw;
	area.w = pbw + 2*(bw+bispw); area.h = bw;
	//SDL_FillRect(gdis,&area,SDL_MapRGB(gdis->format,bcr,bcg,bcb));
	SDL_RenderFill(&area);
	// Draw left border.
	area.x = pbx; area.y = pby + bw;
	area.w = bw; area.h = pbh + 2*bispw;
	//SDL_FillRect(gdis,&area,SDL_MapRGB(gdis->format,bcr,bcg,bcb));
	SDL_RenderFill(&area);
	// Draw right border.
	area.x = pbx + pbw + bw + 2*bispw; area.y = pby + bw;
	area.w = bw; area.h = pbh + 2*bispw;
	//SDL_FillRect(gdis,&area,SDL_MapRGB(gdis->format,bcr,bcg,bcb));
	SDL_RenderFill(&area);
	// Draw the finished bar area.
	area.x = pbx + bw + bispw; area.y = pby + bw + bispw;
	area.w = (prcnt_ * pbw) / (MAX_PERCENTAGE - MIN_PERCENTAGE); area.h = pbh;
	//SDL_FillRect(gdis,&area,SDL_MapRGB(gdis->format,fcr,fcg,fcb));
	SDL_SetRenderDrawColor(fcr, fcg, fcb, 0xff);
	SDL_RenderFill(&area);

	SDL_Rect lightning = area;
	lightning.h = lightning_thickness;
	//we add 25% of white to the color of the bar to simulate a light effect
	//SDL_FillRect(gdis,&lightning,SDL_MapRGB(gdis->format,(fcr*3+255)/4,(fcg*3+255)/4,(fcb*3+255)/4));
	SDL_SetRenderDrawColor((fcr*3+255)/4,(fcg*3+255)/4,(fcb*3+255)/4, 0xff);
	SDL_RenderFill(&lightning);
	lightning.y = area.y+area.h-lightning.h;
	//remove 50% of color to simulate a shadow effect
	//SDL_FillRect(gdis,&lightning,SDL_MapRGB(gdis->format,fcr/2,fcg/2,fcb/2));
	SDL_SetRenderDrawColor(fcr/2,fcg/2,fcb/2, 0xff);
	SDL_RenderFill(&lightning);

	// Draw the leftover bar area.
	area.x = pbx + bw + bispw + (prcnt_ * pbw) / (MAX_PERCENTAGE - MIN_PERCENTAGE); area.y = pby + bw + bispw;
	area.w = ((MAX_PERCENTAGE - prcnt_) * pbw) / (MAX_PERCENTAGE - MIN_PERCENTAGE); area.h = pbh;
	//SDL_FillRect(gdis,&area,SDL_MapRGB(gdis->format,lcr,lcg,lcb));
	SDL_SetRenderDrawColor(lcr, lcg, lcb, 0xff);
	SDL_RenderFill(&area);

	// Clear the last text and draw new if text is provided.
/*	if(text.length() > 0 && commit)
	{
		SDL_Rect oldarea = textarea_;
//		SDL_FillRect(gdis,&textarea_,SDL_MapRGB(gdis->format,0,0,0));
		textarea_ = font::line_size(text, font::SIZE_NORMAL);
		textarea_.x = scrx/2 + bw + bispw - textarea_.w / 2;
		textarea_.y = pby + pbh + 4*(bw + bispw);
		//draw_solid_tinted_rectangle(textarea_.x-4, textarea_.y-2, textarea_.w + 8, textarea_.h + 4,0,0,0,0.50,gdis);
		SDL_Rect tintRect = {textarea_.x-4, textarea_.y-2, textarea_.w + 8, textarea_.h + 4};
		SDL_SetRenderDrawColor(0, 0, 0, 0x80);
		SDL_RenderFill(&tintRect);
		textarea_ = font::draw_text(&screen_,textarea_,font::SIZE_NORMAL,font::NORMAL_COLOUR,text,textarea_.x,textarea_.y);
		oldarea.x = std::min<int>(textarea_.x, oldarea.x);
		oldarea.y = std::min<int>(textarea_.y, oldarea.y);
		oldarea.w = std::max<int>(textarea_.w, oldarea.w);
		oldarea.h = std::max<int>(textarea_.h, oldarea.h);
//		SDL_UpdateRect(gdis, oldarea.x, oldarea.y, oldarea.w, oldarea.h);
	}
*/ 
	// Update the rectangle if needed
	if(commit)
	{
//		SDL_UpdateRect(gdis, pbx, pby, pbw + 2*(bw + bispw), pbh + 2*(bw + bispw));
	}
	
//	if (updateFull)
//	{
//		SDL_UpdateRect(gdis, 0, 0, 480, 320);
//	}
//	else if (commit)
//	{
//		SDL_UpdateRect(gdis, 116, 274, 251, 47);
//	}
	
	SDL_RenderPresent();
}
示例#21
0
//helper blit functions specifically for the Image class wrapping a surface
//
//blit this (tile) image into another image (or screen)
void Image::blitTo(Surface* dest, int destX, int destY, int tileNum /*= -1*/)
{
	//Image class objects default to clip = 0 unless explicitly set
	blit_surface(this->_surface, (tileNum<0)?NULL:&this->tile(tileNum),			//source
				dest->surface(), destX, destY);									//dest
}
示例#22
0
TITLE_RESULT show_title(game_display& screen, config& tips_of_day)
{
	disableTerrainCache();
	
	free_all_caches();
	
	cursor::set(cursor::NORMAL);

	const preferences::display_manager disp_manager(&screen);
	const hotkey::basic_handler key_handler(&screen);

	const font::floating_label_context label_manager;

	screen.video().modeChanged(); // resets modeChanged value

//	if (background_is_dirty_) 
	{
		draw_background(screen);
	}

	//- Texts for the menu-buttons.
	//- Members of this array must correspond to the enumeration TITLE_RESULT
	static const char* button_labels[] = {
					       //N_("TitleScreen button^Tutorial"),
					       N_("TitleScreen button^Campaign"),
#ifndef FREE_VERSION		
							N_("TitleScreen button^Skirmish"),
					       N_("TitleScreen button^Multiplayer"),
#endif
					       N_("TitleScreen button^Load"),
//					       N_("TitleScreen button^Add-ons"),
//#ifndef DISABLE_EDITOR2
					       //N_("TitleScreen button^Map Editor"),
//#endif
					       //N_("TitleScreen button^Language"),
					       N_("TitleScreen button^Preferences"),
							N_("Sync Saves"),
#ifndef DISABLE_OPENFEINT
							N_("TitleScreen button^OpenFeint"),
#endif
					       N_("TitleScreen button^Help"),
					       //N_("TitleScreen button^Quit"),
								// Only the above buttons go into the menu-frame
								// Next 2 buttons go into frame for the tip-of-the-day:
					       N_("TitleScreen button^Previous"),
					       N_("TitleScreen button^Next"),
					       //N_("TitleScreen button^Help"),
								// Next entry is no button, but shown as a mail-icon instead:
					       //N_("TitleScreen button^Help Wesnoth") 
							};
	//- Texts for the tooltips of the menu-buttons
	static const char* help_button_labels[] = { 
							//N_("Start a tutorial to familiarize yourself with the game"),
						    N_("Start a new single player campaign"),
#ifndef FREE_VERSION
							N_("Play a single scenario against the AI"),
						    N_("Play multiplayer (hotseat or Internet)"),
#endif
						    N_("Load a saved game"),
//						    N_("Download usermade campaigns, eras, or map packs"),
//#ifndef DISABLE_EDITOR2
						    //N_("Start the map editor"),
//#endif
						    //N_("Change the language"),
						    N_("Configure the game's settings"),
							N_("Sync saved games"),
#ifndef DISABLE_OPENFEINT
							N_("Launch the OpenFeint dashboard"),
#endif

							N_("Show Battle for Wesnoth help"),
							//N_("Quit the game"),
						    N_("Show next tip of the day"),
						    //N_("Upload statistics") 
							};

	//static const size_t nbuttons = sizeof(button_labels)/sizeof(*button_labels);
#ifdef FREE_VERSION	
	int nbuttons = 10;
#else
	int nbuttons = 8;
#endif
	
#ifdef DISABLE_OPENFEINT
	nbuttons--;
#endif
	
#ifndef __IPAD__
	nbuttons--;	// because help is off to the left now
#endif
	
	int menu_xbase = CVideo::getx()-108-10; //380; //(game_config::title_buttons_x*screen.w())/1024;
	const int menu_xincr = 0;

#ifdef USE_TINY_GUI
	//const int menu_ybase = 15; //(330*screen.h())/768 - 50; //15;
	const int menu_yincr = 36+5; //(35*3)/4;//15;
	const int menu_ybase = (screen.h() - (36+5)*nbuttons - 5) / 2 + 4;
#else
	const int menu_ybase = (screen.h() - (36+5)*nbuttons - 5) / 2 + 4;
	const int menu_yincr = 36+5;
#endif
	
#ifdef __IPAD__
	menu_xbase -= 10;
#endif

	const int padding = 4; //game_config::title_buttons_padding;

	std::vector<button> buttons;
	size_t b, max_width = 0;
	size_t n_menubuttons = 0;
	for(b = 0; b != nbuttons; ++b) 
	{
//#ifdef __IPHONEOS__		
//		if (b + TUTORIAL == TUTORIAL || b + TUTORIAL == START_MAP_EDITOR || b+TUTORIAL == CHANGE_LANGUAGE)
//			continue;
//#endif		
		buttons.push_back(button(screen.video(),sgettext(button_labels[b])));
		buttons.back().set_help_string(sgettext(help_button_labels[b]));
		max_width = std::max<size_t>(max_width,buttons.back().width());

		n_menubuttons = b;
#ifdef __IPAD__
		if(b + NEW_CAMPAIGN == SHOW_HELP) break;
#else
		if(b + NEW_CAMPAIGN == SHOW_OPENFEINT) break;		
#endif
	}

	SDL_Rect main_dialog_area = {menu_xbase-padding, menu_ybase-padding, max_width+padding*2,
								 menu_yincr*(n_menubuttons)+buttons.back().height()+padding*2};

	gui::dialog_frame main_frame(screen.video(), "", gui::dialog_frame::titlescreen_style, false);
	main_frame.layout(main_dialog_area);

	// we only redraw transparent parts when asked,
	// to prevent alpha growing
	if (background_is_dirty_) {
		main_frame.draw_background();
		main_frame.draw_border();
	}

	int i=0;
	for(b = 0; b != nbuttons; ++b) 
	{
//#ifdef __IPHONEOS__		
//		if (b + TUTORIAL == TUTORIAL || b + TUTORIAL == START_MAP_EDITOR || b+TUTORIAL == CHANGE_LANGUAGE)
//			continue;
//#endif		
		buttons[i].set_width(max_width);
		buttons[i].set_location(menu_xbase + i*menu_xincr, menu_ybase + i*menu_yincr);
#ifdef __IPAD__
		if(b + NEW_CAMPAIGN == SHOW_HELP) break;
#else
		if(b + NEW_CAMPAIGN == SHOW_OPENFEINT) break;		
#endif
		i++;
	}
	
#ifndef __IPAD__
	buttons.push_back(button(screen.video(),sgettext(button_labels[i+1])));
	buttons.back().set_help_string(sgettext(help_button_labels[i+1]));
	buttons[i+1].set_width(max_width);
	buttons[i+1].set_location(5, 320-menu_yincr);	
#endif

//	b = TIP_PREVIOUS - NEW_CAMPAIGN;
//	gui::button previous_tip_button(screen.video(),sgettext(button_labels[b]),button::TYPE_PRESS,"lite_small");
//	previous_tip_button.set_help_string( sgettext(button_labels[b] ));

//	b = TIP_NEXT - NEW_CAMPAIGN;
//	gui::button next_tip_button(screen.video(),sgettext(button_labels[b]),button::TYPE_PRESS,"lite_small");
//	next_tip_button.set_help_string( sgettext(button_labels[b] ));

//	b = SHOW_HELP - NEW_CAMPAIGN;
//	gui::button help_tip_button(screen.video(),sgettext(button_labels[b]),button::TYPE_PRESS,"lite_small");
//	help_tip_button.set_help_string( sgettext(button_labels[b] ));

//	gui::button beg_button(screen.video(),_("Help Wesnoth"),button::TYPE_IMAGE,"menu-button",button::MINIMUM_SPACE);
//	beg_button.set_help_string(_("Help Wesnoth by sending us information"));

//	next_tip_of_day(tips_of_day);

//	surface_restorer tip_of_day_restorer;

//	draw_tip_of_day(screen, tips_of_day, gui::dialog_frame::titlescreen_style,
//					&previous_tip_button, &next_tip_button, NULL/*&help_tip_button*/, &main_dialog_area, tip_of_day_restorer);

//	const int pad = game_config::title_tip_padding;
//	beg_button.set_location(screen.w() - pad - beg_button.location().w,
//		screen.h() - pad - beg_button.location().h);
	events::raise_draw_event();

	LOG_DP << "drew buttons dialog\n";
	
	
	// draw logo over everything
#ifdef __IPAD__	
	std::string path = game_config::path + "/data/core/images/misc/logo.png";
#else
	std::string path = game_config::path + "/data/core/images/misc/logo_small.png";
#endif	
	surface logo_surface = IMG_Load(path.c_str());
	//blit_surface(480-logo_surface.get()->w, 0, logo_surface);
	
	

	CKey key;

	size_t keyboard_button = nbuttons;
	bool key_processed = false;

//	update_whole_screen();
	background_is_dirty_ = false;

	titlescreen_handler ts_handler(key[SDLK_ESCAPE] != 0); //!= 0 to avoid a MSVC warning C4800

	LOG_DP << "entering interactive loop...\n";
	
	
	memory_stats("At titlescreen");
	
	// Initialize OpenFeint now
	of_init();

	
	for(;;) {
		events::pump();
		for(size_t b = 0; b != buttons.size(); ++b) {
			if(buttons[b].pressed()) {
				free_title();
				return static_cast<TITLE_RESULT>(b + NEW_CAMPAIGN);
			}
		}

/*		if(previous_tip_button.pressed()) {
			next_tip_of_day(tips_of_day, true);
			draw_tip_of_day(screen, tips_of_day, gui::dialog_frame::titlescreen_style,
						&previous_tip_button, &next_tip_button, &help_tip_button, &main_dialog_area, tip_of_day_restorer);
		}
		if(next_tip_button.pressed()) {
			next_tip_of_day(tips_of_day, false);
			draw_tip_of_day(screen, tips_of_day, gui::dialog_frame::titlescreen_style,
						&previous_tip_button, &next_tip_button, &help_tip_button, &main_dialog_area, tip_of_day_restorer);
		}
*/
//		if(help_tip_button.pressed()) {
//			return SHOW_HELP;
//		}
//		if(beg_button.pressed()) {
//			return BEG_FOR_UPLOAD;
//		}
		if (key[SDLK_UP]) {
			if (!key_processed) {
				buttons[keyboard_button].set_active(false);
				if (keyboard_button == 0) {
					keyboard_button = nbuttons - 1;
				} else {
					keyboard_button--;
				}
				key_processed = true;
				buttons[keyboard_button].set_active(true);
			}
		} else if (key[SDLK_DOWN]) {
			if (!key_processed) {
				buttons[keyboard_button].set_active(false);
				if (keyboard_button > nbuttons - 1) {
					keyboard_button = 0;
				} else {
					keyboard_button++;
				}
				key_processed = true;
				buttons[keyboard_button].set_active(true);
			}
		} else {
			key_processed = false;
		}

		events::raise_process_event();
		
		
		// KP: redraw
		draw_background(screen);
		main_frame.draw_background();
		main_frame.draw_border();
		events::raise_draw_event();
		//blit_surface(480-logo_surface.get()->w, 0, logo_surface);
#ifdef __IPAD__
		blit_surface(-10, 0, logo_surface);
#else
		blit_surface(-15, -10, logo_surface);
#endif
		
		screen.flip();

//		if (key[SDLK_ESCAPE] && !ts_handler.get_esc_ignore())
//			return QUIT_GAME;
		if (key[SDLK_F5])
			return RELOAD_GAME_DATA;

		if (key[SDLK_RETURN] && keyboard_button < nbuttons) {
			return static_cast<TITLE_RESULT>(keyboard_button + NEW_CAMPAIGN);
		}



		// If the resolution has changed due to the user resizing the screen,
		// or from changing between windowed and fullscreen:
		if(screen.video().modeChanged()) {
			return REDRAW_BACKGROUND;
		}
		
		screen.delay(10);
	}

	free_title();
	return REDRAW_BACKGROUND;
}
示例#23
0
void tristate_button::draw_contents() {

	surface image(NULL);

	surface overlay(NULL);
	surface base = baseImage_;

	int offset = 0;
	switch (state_) {

	case UNINIT:
		return;

	case NORMAL:
		break;

	case TOUCHED_LEFT:
		overlay = touchedUpImage_;
		base = touchedBaseImage_;
		break;
	case TOUCHED_RIGHT:
		overlay = touchedDownImage_;
		base = touchedBaseImage_;
		break;
	case TOUCHED_BOTH_LEFT:
	case TOUCHED_BOTH_RIGHT:
		overlay = touchedBothImage_;
		base = touchedBaseImage_;
		break;
	case ACTIVE:
		//	overlay = activeImage_;
		base = activeBaseImage_;
		break;
	case PRESSED_LEFT:
		base = activeBaseImage_;
		overlay = pressedUpImage_;
		break;
	case PRESSED_RIGHT:
		base = activeBaseImage_;
		overlay = pressedDownImage_;
		break;
	case PRESSED_BOTH:
		base = activeBaseImage_;
		overlay = pressedBothImage_;
		break;
	case PRESSED_ACTIVE_LEFT:
		overlay = pressedUpActiveImage_;
		base = activeBaseImage_;
		break;
	case PRESSED_ACTIVE_BOTH:
		overlay = pressedBothActiveImage_;
		base = activeBaseImage_;
		break;
	case PRESSED_ACTIVE_RIGHT:
		overlay = pressedDownActiveImage_;
		base = activeBaseImage_;
		break;
	}

	image = base;

	const int image_w = image->w;
	SDL_Rect const &loc = location();
	SDL_Rect clipArea = loc;
	const int texty = loc.y + loc.h / 2 - textRect_.h / 2 + offset;
	int textx;

	clipArea.w += image_w + checkbox_horizontal_padding;
	textx = loc.x + image_w + checkbox_horizontal_padding / 2;

	SDL_Color button_color = font::BUTTON_COLOR;

	surface scalled_item;
	scalled_item.assign(scale_surface(itemImage_,
			36, 36));

	// blit_surface want neutral surfaces
	surface nitem = make_neutral_surface(scalled_item);
	surface nbase = make_neutral_surface(base);

	//TODO avoid magic numbers
	SDL_Rect r = sdl::create_rect(1, 1, 0, 0);
	blit_surface(nitem, NULL, nbase, &r);

	if (!overlay.null()) {
		surface noverlay = make_neutral_surface(overlay);
		blit_surface(noverlay, NULL, nbase, NULL);
	}

//  TODO for later reference
//	SDL_SetAlpha(nbase, SDL_SRCALPHA, SDL_ALPHA_OPAQUE);
//	SDL_SetAlpha(image, 0, 0);
//
//	TODO might be needed.
	bg_restore();

	image = nbase;
	video().blit_surface(loc.x, loc.y, image);

	clipArea.x += offset;
	clipArea.y += offset;
	clipArea.w -= 2 * offset;
	clipArea.h -= 2 * offset;
	font::draw_text(&video(), clipArea, font_size, button_color, label_, textx,
			texty);

	update_rect(loc);
}
示例#24
0
void menu::imgsel_style::draw_row(menu& menu_ref, const size_t row_index, const SDL_Rect& rect, ROW_TYPE type)
{
	if(!load_failed_) {
		//draw item inside
		style::draw_row(menu_ref, row_index, rect, type);

		if(type == SELECTED_ROW) {
			// draw border
			surface image;
			SDL_Rect area;
			SDL_Rect clip = rect;
			area.x = rect.x;
			area.y = rect.y;

			image = img_map_["border-top"];
			area.x = rect.x;
			area.y = rect.y;
			do {
				blit_surface(area.x,area.y,image,NULL,&clip);
				area.x += image->w;
			} while( area.x < rect.x + rect.w );

			image = img_map_["border-left"];
			area.x = rect.x;
			area.y = rect.y;
			do {
				blit_surface(area.x,area.y,image,NULL,&clip);
				area.y += image->h;
			} while( area.y < rect.y + rect.h );

			image = img_map_["border-right"];
			area.x = rect.x + rect.w - thickness_;
			area.y = rect.y;
			do {
				blit_surface(area.x,area.y,image,NULL,&clip);
				area.y += image->h;
			} while( area.y < rect.y + rect.h );

			image = img_map_["border-bottom"];
			area.x = rect.x;
			area.y = rect.y + rect.h - thickness_;
			do {
				blit_surface(area.x,area.y,image,NULL,&clip);
				area.x += image->w;
			} while( area.x < rect.x + rect.w );

			image = img_map_["border-topleft"];
			area.x = rect.x;
			area.y = rect.y;
			blit_surface(area.x,area.y,image);

			image = img_map_["border-topright"];
			area.x = rect.x + rect.w - image->w;
			area.y = rect.y;
			blit_surface(area.x,area.y,image);

			image = img_map_["border-botleft"];
			area.x = rect.x;
			area.y = rect.y + rect.h - image->h;
			blit_surface(area.x,area.y,image);

			image = img_map_["border-botright"];
			area.x = rect.x + rect.w - image->w;
			area.y = rect.y + rect.h - image->h;
			blit_surface(area.x,area.y,image);
		}
	} else {
		//default drawing
		style::draw_row(menu_ref, row_index, rect, type);
	}
}
示例#25
0
surface getMinimap(int w, int h, const gamemap &map, const team *vw)
{
	const int scale = 8;

	DBG_DP << "creating minimap " << int(map.w()*scale*0.75) << "," << map.h()*scale << "\n";

	const size_t map_width = map.w()*scale*3/4;
	const size_t map_height = map.h()*scale;
	if(map_width == 0 || map_height == 0) {
		return surface(NULL);
	}

	surface minimap(create_neutral_surface(map_width, map_height));
	if(minimap == NULL)
		return surface(NULL);

	typedef mini_terrain_cache_map cache_map;
	cache_map *normal_cache = &mini_terrain_cache;
	cache_map *fog_cache = &mini_fogged_terrain_cache;

	for(int y = 0; y != map.total_height(); ++y) {
		for(int x = 0; x != map.total_width(); ++x) {

			surface surf(NULL);

			const map_location loc(x,y);
			if(map.on_board(loc)) {

				const bool shrouded = (vw != NULL && vw->shrouded(loc));
				// shrouded hex are not considered fogged (no need to fog a black image)
				const bool fogged = (vw != NULL && !shrouded && vw->fogged(loc));
				const t_translation::t_terrain terrain = shrouded ?
						t_translation::VOID_TERRAIN : map[loc];
				const terrain_type& terrain_info = map.get_terrain_info(terrain);

				bool need_fogging = false;

				cache_map* cache = fogged ? fog_cache : normal_cache;
				cache_map::iterator i = cache->find(terrain);

				if (fogged && i == cache->end()) {
					// we don't have the fogged version in cache
					// try the normal cache and ask fogging the image
					cache = normal_cache;
					i = cache->find(terrain);
					need_fogging = true;
				}

				if(i == cache->end()) {
					std::string base_file =
							"terrain/" + terrain_info.minimap_image() + ".png";
					surface tile = get_image(base_file,image::HEXED);

					//Compose images of base and overlay if necessary
					// NOTE we also skip overlay when base is missing (to avoid hiding the error)
					if(tile != NULL && map.get_terrain_info(terrain).is_combined()) {
						std::string overlay_file =
								"terrain/" + terrain_info.minimap_image_overlay() + ".png";
						surface overlay = get_image(overlay_file,image::HEXED);

						if(overlay != NULL && overlay != tile) {
							surface combined = create_neutral_surface(tile->w, tile->h);
							SDL_Rect r = create_rect(0,0,0,0);
							sdl_blit(tile, NULL, combined, &r);
							r.x = std::max(0, (tile->w - overlay->w)/2);
							r.y = std::max(0, (tile->h - overlay->h)/2);
							//blit_surface needs neutral surface
							surface overlay_neutral = make_neutral_surface(overlay);
							blit_surface(overlay_neutral, NULL, combined, &r);
							tile = combined;
						}
					}

					surf = scale_surface_sharp(tile, scale, scale);

					i = normal_cache->insert(cache_map::value_type(terrain,surf)).first;
				}

				surf = i->second;

				if (need_fogging) {
					surf = adjust_surface_color(surf,-50,-50,-50);
					fog_cache->insert(cache_map::value_type(terrain,surf));
				}

				// we need a balanced shift up and down of the hexes.
				// if not, only the bottom half-hexes are clipped
				// and it looks asymmetrical.

				// also do 1-pixel shift because the scaling
				// function seems to do it with its rounding
				SDL_Rect maprect = create_rect(
						  x * scale * 3 / 4 - 1
						, y * scale + scale / 4 * (is_odd(x) ? 1 : -1) - 1
						, 0
						, 0);

				if(surf != NULL)
					sdl_blit(surf, NULL, minimap, &maprect);
			}
		}
	}

	double wratio = w*1.0 / minimap->w;
	double hratio = h*1.0 / minimap->h;
	double ratio = std::min<double>(wratio, hratio);

	minimap = scale_surface_sharp(minimap,
		static_cast<int>(minimap->w * ratio), static_cast<int>(minimap->h * ratio));

	DBG_DP << "done generating minimap\n";

	return minimap;
}
示例#26
0
文件: button.cpp 项目: AI0867/wesnoth
void button::draw_contents()
{
	surface image = image_;
	const int image_w = image_->w;

	int offset = 0;
	switch(state_) {
	case ACTIVE:
		image = activeImage_;
		break;
	case PRESSED:
		image = pressedImage_;
		if (type_ == TYPE_PRESS)
			offset = 1;
		break;
	case PRESSED_ACTIVE:
		image = pressedActiveImage_;
		break;
	case TOUCHED_NORMAL:
	case TOUCHED_PRESSED:
		image = touchedImage_;
		break;
	default:
		break;
	}

	SDL_Rect const &loc = location();
	SDL_Rect clipArea = loc;
	const int texty = loc.y + loc.h / 2 - textRect_.h / 2 + offset;
	int textx;

	if (type_ != TYPE_CHECK && type_ != TYPE_RADIO && type_ != TYPE_IMAGE)
		textx = loc.x + image->w / 2 - textRect_.w / 2 + offset;
	else {
		clipArea.w += image_w + checkbox_horizontal_padding;
		textx = loc.x + image_w + checkbox_horizontal_padding / 2;
	}

	SDL_Color button_color = font::BUTTON_COLOR;

	if (!enabled()) {

		if (state_ == PRESSED || state_ == PRESSED_ACTIVE)
			image = pressedDisabledImage_;
		else image = disabledImage_;

		button_color = font::GRAY_COLOR;
	}

	if (!overlayImage_.null()) {

		surface noverlay = make_neutral_surface(
				enabled() ? overlayImage_ : overlayDisabledImage_);

		if (!overlayPressedImage_.null()) {
			switch (state_) {
			case ACTIVE:
				if (!overlayActiveImage_.null())
					noverlay = make_neutral_surface(overlayActiveImage_);
				break;
			case PRESSED:
			case PRESSED_ACTIVE:
			case TOUCHED_NORMAL:
			case TOUCHED_PRESSED:
				noverlay = make_neutral_surface( enabled() ?
						overlayPressedImage_ : overlayPressedDisabledImage_);
				break;
			default:
				break;
			}
		}

		surface nimage = make_neutral_surface(image);
		blit_surface(noverlay, NULL, nimage, NULL);
		image = nimage;
	}

	video().blit_surface(loc.x, loc.y, image);
	if (type_ != TYPE_IMAGE){
		clipArea.x += offset;
		clipArea.y += offset;
		clipArea.w -= 2*offset;
		clipArea.h -= 2*offset;
		font::draw_text(&video(), clipArea, font_size, button_color, label_, textx, texty);
	}

	update_rect(loc);
}
示例#27
0
//blit a (tile) image into this image
void Image::blitFrom(Image* source, int tileNum /*= -1*/, int destX, int destY )
{
	//Image class objects default to clip = 0 unless explicitly set
	blit_surface(source->surface(), (tileNum<0)?NULL:&source->tile(tileNum),	//source
				this->_surface, destX, destY);									//dest
}
示例#28
0
void gui_show_listbox(gui_listbox *lb) {
	int i, item;
	SDL_Rect rect;
	
	if (lb == NULL)
		return;
	
	if (!lb->visible)
		return;
	
	/* draw the under area first */
	if (lb->trans_area == NULL) {
		SDL_Surface *area;
		SDL_Rect src, dest;
		
		area = SDL_CreateRGBSurface(SDL_SWSURFACE | SDL_SRCALPHA, lb->w - 17, lb->h, screen->format->BitsPerPixel, screen->format->Rmask, screen->format->Gmask, screen->format->Bmask, screen->format->Amask);
		assert(area);
		rect.x = 0;
		rect.y = 0;
		rect.w = area->w;
		rect.h = area->h;
		SDL_FillRect(area, &rect, SDL_MapRGB(area->format, 0, 0, 0));
		SDL_SetAlpha(area, SDL_SRCALPHA, 93);
		
		rect.x = lb->x;
		rect.y = lb->y;
		rect.w = area->w;
		rect.h = area->h;
		blit_surface(area, NULL, &rect, 0);
		
		SDL_FreeSurface(area);
		
		/* now that the trans area is drawn, back up that area there */
		lb->trans_area = SDL_CreateRGBSurface(SDL_SWSURFACE | SDL_SRCALPHA, lb->w - 17, lb->h, screen->format->BitsPerPixel, screen->format->Rmask, screen->format->Gmask, screen->format->Bmask, screen->format->Amask);
		src.x = lb->x;
		src.y = lb->y;
		src.w = lb->trans_area->w;
		src.h = lb->trans_area->h;
		dest.x = 0;
		dest.y = 0;
		dest.w = src.w;
		dest.h = src.h;
		
		SDL_BlitSurface(screen, &src, lb->trans_area, &dest);
	} else {
		rect.x = lb->x;
		rect.y = lb->y;
		rect.w = lb->trans_area->w;
		rect.h = lb->trans_area->h;
		
		blit_surface(lb->trans_area, NULL, &rect, 0);
	}
	
	if (lb->num_items == 0)
		return;
	
	/* now draw the items */
	/* set "item" to the first item for the top, as dedicated by the progress bar */
	item = (int)((float)lb->sb->progress * (float)(lb->num_items - 1));
	lb->top_scrolled = item;
	
	/* draw the top bar */
	rect.x = lb->x;
	rect.y = lb->y;
	rect.w = lb->w - 17;
	rect.h = 2;
	fill_rect(&rect, map_rgb(0, 93, 92));
	
	/* draw all the item borders and call the callback (if one exists) to draw what's inside each element */
	for (i = 0; (item < lb->num_items) && ((i * lb->item_h) < lb->h); i++) {
		if ((i + lb->top_scrolled) == lb->selected) {
			/* draw the selected bg */
			rect.x = lb->x;
			rect.y = lb->y + (i * lb->item_h) + 2;
			rect.w = lb->w - 17;
			rect.h = lb->item_h - 2;
			if ((rect.y + rect.h) > (lb->y + lb->h))
				rect.h = (lb->y + lb->h) - rect.y;
			
			fill_rect(&rect, map_rgb(0, 64, 65));
		}
		/* draw the bottom item bar */
		rect.x = lb->x;
		rect.y = lb->y + (i * lb->item_h) + lb->item_h;
		rect.w = lb->w - 17;
		rect.h = 2;
		if (rect.y < (lb->y + lb->h))
			fill_rect(&rect, map_rgb(0, 93, 92));
		
		if (lb->callback)
			(*lb->callback) (lb, rect.x, rect.y - lb->item_h, rect.w, lb->item_h, item);
		
		item++;
	}
}