⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 glyph_buffer.h

📁 这是一款2d游戏引擎
💻 H
📖 第 1 页 / 共 2 页
字号:
/*  $Id: glyph_buffer.h,v 1.27 2004/01/02 15:42:43 mbn Exp $
**
**  ClanLib Game SDK
**  Copyright (C) 2003  The ClanLib Team
**  For a total list of contributers see the file CREDITS.
**
**  This library is free software; you can redistribute it and/or
**  modify it under the terms of the GNU Lesser General Public
**  License as published by the Free Software Foundation; either
**  version 2.1 of the License, or (at your option) any later version.
**
**  This library is distributed in the hope that it will be useful,
**  but WITHOUT ANY WARRANTY; without even the implied warranty of
**  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
**  Lesser General Public License for more details.
**
**  You should have received a copy of the GNU Lesser General Public
**  License along with this library; if not, write to the Free Software
**  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307  USA
**
*/

//! clanDisplay="Fonts"
//! header=display.h

#ifndef header_glyph_buffer
#define header_glyph_buffer

#if _MSC_VER > 1000
#pragma once
#endif

#ifdef _MSC_VER
#pragma warning( disable : 4786)
#endif

#include <map>
#include <vector>
#include <utility>

#include "font.h"
#include "../Core/Math/origin.h"
#include "color.h"

class CL_Point;
class CL_Rect;
class CL_GraphicContext;

//: Stores and draws glyphs in one or more fonts.
//- !group=Display/Fonts!
//- !header=display.h!
//- <p>CL_GlyphBuffer is mostly useful for text effects, for concatenating
//- multiple CL_Font or CL_TextStyler draw_to_gb()s, or for
//- when you need access to the low-level glyph positioning data. You can
//- also use it to save time by only rendering a bit of text once when you need
//- to, for example, both draw that text and know its bounding rectangle. But
//- for optimiziation purposes alone when dealing with unchanging text, you
//- should instead
//- have CL_Font or CL_TextStyler render onto a CL_Canvas or CL_Surface.</p>
//- <p>A glyph buffer consists of a series of characters and positions,
//- and markers for font changes and various other text-altering infomration. The internal data structures used
//- are made accessible and mutable externally. CL_Font
//- and CL_TextStyler both have draw_to_gb() methods, which allows them to
//- put data into a CL_GlyphBuffer rather than drawing to a CL_GraphicContext. </p>
//- <p>The effect maps for color, angle, and scale allow you to affect those properties
//- for individual glyphs during drawing and bounding rect calculation. The angle and scale maps are different
//- from the GlyphBuffer angle and scale properties; the properties apply to the entire CL_GlyphBuffer as a whole, while entries
//- in the effect maps affect individual glyphs seperately. It's not legal to insert
//- an effect map entry for a glyph that doesn't exist.</p>
//- <p>Unlike scale effects map entries, which are multiplied by the CL_Font's existing scale, 
//- color effect map entries entirely override the CL_Font's color. No blending between
//- the two colors is performed. Also, it's your responsibility to make sure that CL_Fonts have the right
//- blending functions.</p>
//- <p>In functions that calculate the size or bounding rectangle of the GlyphBuffer
//- (such as bouding_rect(), get_size(), and the alignment calculations within draw),
//- effect properties do take effect on the final rectangle, but GlyphBuffer rotation
//- and scaling (set with CL_GlyphBuffer::set_angle(), and CL_GlyphBuffer::set_scale(),
//- respectively) do not. This is consistent with the behavior of CL_Sprite and CL_Surface; the content
//- affects bounding rect calculation, but the other properties of the object
//- do not.</p>
class CL_GlyphBuffer
{
//! Construction:
public:
	//: Constructs a glyph buffer.
	CL_GlyphBuffer();
	
	virtual ~CL_GlyphBuffer() {;}
	
//! Subclasses:
public:
	//: A character and position describing a glyph in the buffer, stored in the glyphs vector.
	struct Glyph
	{
		//:Constructs a new Glyph
		//p: The CL_Point that will be assigned to pos
		//c: The unsigned char that will be assigned to character
		Glyph() {;}
		Glyph(CL_Point p, unsigned char c) : pos(p), character(c) {;}
		
		//: The position where the glyph is drawn.
		CL_Point pos;
		
		//: The character which determines the glyph that's drawn.
		unsigned char character;
	};

	//: Represents a subsection of the buffer
	struct Range
	{
		//:Constructs a new Range.
		//new_start: The starting index of the range, inclusive
		//new_end: The ending index of the range, exclusive
		//gb: Constructs a new Range that encompasses this entire CL_GlyphBuffer
		Range() : start(0), end(0) {;}
		Range(const CL_GlyphBuffer& gb) : start(0), end(int(gb.get_glyphs().size())) {;}
		Range(int new_start, int new_end) : start(new_start), end(new_end) {;}
		
		//: Makes range valid for a given GlyphBuffer.
		//- <p> This is automatically called when you pass the range to any GlyphBuffer method.</p>
		void verify(const CL_GlyphBuffer& gb);
		
		//: Pulls in the range at the beginning until it reaches a drawable glyph
		void remove_invis_left(const CL_GlyphBuffer& gb);
		
		//: Pulls in the range at the end until it reaches a drawable glyph
		void remove_invis_right(const CL_GlyphBuffer& gb);
		
		//: Pulls in the range at both sides until it reaches a drawable glyph
		void remove_invis_both(const CL_GlyphBuffer& gb)
			{remove_invis_left(gb); remove_invis_right(gb);}
		
		//The starting index of the range, inclusive.
		int start;
		
		//The ending index of the range, exclusive.
		int end;
	};
	
//! Attributes:
public:
	//: Returns a reference to the glyphs in the buffer and their drawing positions.
	//- <p>See CL_GlyphBuffer::Glyph for details./p>
	std::vector<Glyph>& get_glyphs() {return glyphs;}
	const std::vector<Glyph>& get_glyphs() const {return glyphs;}
	
	//: Returns a reference to the font map.
	//- <p>Elements of the glyphs vector before the first font marker are ignored. Each element
	//- within this map causes a change in the font while drawing, where the key of the
	//- element is the index in the glyphs vector before which the font is changed.</p>
	std::map<int, CL_Font>& get_font_markers() {return font_markers;}
	const std::map<int, CL_Font>& get_font_markers() const {return font_markers;}
	
	//: Returns a reference to the color effect map.
	std::map<int, CL_Color>& get_color_effects() {return color_effects;}
	const std::map<int, CL_Color>& get_color_effects() const {return color_effects;}
	
	//: Returns a reference to the x scale effect map.
	//- <p> Scaling occurs away from the upper-left corner of each glyph. </p>
	std::map<int, float>& get_scale_x_effects() {return scale_x_effects;}
	const std::map<int, float>& get_scale_x_effects() const {return scale_x_effects;}
	
	//: Returns a reference to the y scale effect map.
	//- <p> Scaling occurs away from the upper-left corner of each glyph. </p>
	std::map<int, float>& get_scale_y_effects() {return scale_y_effects;}
	const std::map<int, float>& get_scale_y_effects() const {return scale_y_effects;}
	
	//: Returns a reference to the character angle effect map.
	std::map<int, float>& get_angle_effects() {return angle_effects;}
	const std::map<int, float>& get_angle_effects() const {return angle_effects;}
	
	//: Returns an iterator to the font_marker associated with a particular glyph.
	//- <p> If a negative index is supplied, assumes glyph 0. If an index
	//- past the last element is supplied, assumes the last element. If
	//- there are no CL_Fonts in the GlyphBuffer, or if there is no CL_Font
	//- associated with that glyph, returns the end iterator.</p>
	std::map<int, CL_Font>::iterator get_font_for(int glyph_index);
	std::map<int, CL_Font>::const_iterator get_font_for(int glyph_index) const;
	
	//: Returns the width of the entire buffer, or a sub-Range.
	//return: The width in pixels.
	//param range: A subsection of the glyphs vector to get the width of.
	//param idx: The vector index of a single glyph to get the width of.
	//param ignore_invis: If true, ignores invisible glyphs (glyphs without an actual visual glyph in the font)
	int get_width(bool ignore_invis = true) const
		{return get_width(Range(*this), ignore_invis);}
	int get_width(int idx, bool ignore_invis = true) const
		{return get_width(Range(idx, idx+1), ignore_invis);}
	int get_width(Range range, bool ignore_invis = true) const
		{return get_size(range, ignore_invis).width;}
	
	//: Returns the height of the entire buffer, or a sub-Range.
	//return: The height in pixels.
	//param range: A subsection of the glyphs vector to get the height of.
	//param idx: The vector index of a single glyph to get the height of.
	//param ignore_invis: If true, ignores invisible glyphs (glyphs without an actual visual glyph in the font)
	int get_height(bool ignore_invis = true) const
		{return get_height(Range(*this), ignore_invis);}
	
	int get_height(int idx, bool ignore_invis = true) const
		{return get_height(Range(idx, idx+1), ignore_invis);}
	
	int get_height(Range range, bool ignore_invis = true) const
		{return get_size(range, ignore_invis).height;}
	
	//: Returns the size of the entire buffer, or a sub-Range.
	//return: The size in pixels.
	//param range: A subsection of the glyphs vector to get the size of.
	//param idx: The vector index of a single glyph to get the size of.
	//param ignore_invis: If true, ignores invisible glyphs (glyphs without an actual visual glyph in the font)
	CL_Size get_size(bool ignore_invis = true) const
		{return get_size(Range(*this), ignore_invis);}
	
	CL_Size get_size(int idx, bool ignore_invis = true) const
		{return get_size(Range(idx, idx+1), ignore_invis);}
	
	CL_Size get_size(Range range, bool ignore_invis = true) const
		{return internal_rect(range, ignore_invis).get_size();}
	
	//: Returns current angle.
	//- <p> This rotates the entire glyph field when drawing.
	//- The fonts' glyph rotation origin must be origin_top_left:0:0 for this
	//- to produce legible results. See CL_Font::set_glyph_rotation_hotspot(). </p>
	float get_angle() const
		{return rot_angle;}
	
	//: Returns scale for x and y.
	//- <p> 1.0f is normal scale, 2.0f is twice the size, etc. </p>
	void get_scale(float &x, float &y) const
		{x = scale_x; y = scale_y;}
	
	//: Returns translation hotspot for the entire glyph field.
	void get_alignment(CL_Origin &origin, int &x, int &y) const
		{origin = trans_origin; x = trans_x; y = trans_y;}
	
	//: Returns rotation hotspot for the entire glyph field.
	void get_rotation_hotspot(CL_Origin &origin, int &x, int &y) const
		{origin = rot_origin; x = rot_x; y = rot_y;}
	
	//: Returns the area that would be drawn to if a draw were performed.
	//return: The area into which any pixels would be drawn. If buffer is empty, returns a rectangle with zero size.
	//param x, y: Anchor position to start "drawing" at. Actual rendering position depends on the alignment mode.
	//param dest: Rectangle to render glyphs in. The glyphs will be positioned within the rectangle depending on the alignment mode.
	//param range: The subsection of the glyphs vector to use.
	//param ignore_invis: If true, ignores invisible glyphs (glyphs without an actual visual glyph in the font)
	CL_Rect bounding_rect(int x = 0, int y = 0, bool ignore_invis = true) const
		{return bounding_rect(Range(*this), x, y, ignore_invis);}
	
	CL_Rect bounding_rect(Range range, int x = 0, int y = 0, bool ignore_invis = true) const
		{return bounding_rect(range, CL_Rect(x, y, x, y), ignore_invis);}
	
	CL_Rect bounding_rect(CL_Rect dest, bool ignore_invis = true) const
		{return bounding_rect(Range(*this), dest, ignore_invis);}
	
	CL_Rect bounding_rect(Range range, CL_Rect dest, bool ignore_invis = true) const;
	
	//: Returns the area occupied by glyphs inside the glyph buffer's coordinate space.
	//return: The area occupied by all glyphs, inside the buffer. If buffer is empty, returns a rectangle with zero size.
	//param range: The subsection of the glyphs vector to get the internal bounding rect of.
	//param idx: The vector index of a single glyph to get the internal bounding rect of.
	//param ignore_invis: If true, ignores invisible glyphs (glyphs without an actual visual glyph in the font)
	CL_Rect internal_rect(bool ignore_invis = true) const
		{return internal_rect(Range(*this), ignore_invis);}
	CL_Rect internal_rect(int idx, bool ignore_invis = true) const
		{return internal_rect(Range(idx, idx+1), ignore_invis);}
	CL_Rect internal_rect(Range range, bool ignore_invis = true) const;
	
	//: Returns a vector of CL_GlyphBuffer::Range, each of which contains one line.
	//param range: The subsection of the glyphs vector to look through, which is expanded both ways.
	//- <p> The CL_GlyphBuffer's contents (the glyphs vector, the font markers map, and the effects maps),
	//- if any, must not have been created/altered by anything but CL_Font::draw_to_gb() or CL_TextStyler::draw_to_gb()
	//- or the CL_GlyphBuffer justification functions or using CL_GlyphBuffer::remove to take glyphs off the end
	//- for this method to work.</p>
	std::vector<Range> get_lines() const
		{return get_lines(Range(*this));}
		
	std::vector<Range> get_lines(Range range) const;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -