terrain_translation.hpp

Go to the documentation of this file.
00001 /* $Id: terrain_translation.hpp 52533 2012-01-07 02:35:17Z shadowmaster $ */
00002 /*
00003    Copyright (C) 2006 - 2012 by Mark de Wever <koraq@xs4all.nl>
00004    Part of the Battle for Wesnoth Project http://www.wesnoth.org/
00005 
00006    This program is free software; you can redistribute it and/or modify
00007    it under the terms of the GNU General Public License as published by
00008    the Free Software Foundation; either version 2 of the License, or
00009    (at your option) any later version.
00010    This program is distributed in the hope that it will be useful,
00011    but WITHOUT ANY WARRANTY.
00012 
00013    See the COPYING file for more details.
00014 */
00015 
00016 /** @file */
00017 
00018 #ifndef TERRAIN_TRANSLATION_H_INCLUDED
00019 #define TERRAIN_TRANSLATION_H_INCLUDED
00020 
00021 #include <SDL_types.h> //used for Uint32 definition
00022 #include <vector>
00023 #include <map>
00024 
00025 #include "exceptions.hpp"
00026 
00027 namespace t_translation {
00028 
00029     /**
00030      * Return the maximum allowed map size (in either dimension),
00031      * the maximum map area is, therefore, this value squared.
00032      */
00033     size_t max_map_size();
00034 
00035     typedef Uint32 t_layer;
00036     const t_layer WILDCARD = 0x2A000000;
00037     const t_layer NO_LAYER = 0xFFFFFFFF;
00038 
00039     // The definitions for a terrain
00040     /**
00041      * A terrain string which is converted to a terrain is a string with 1 or 2 layers
00042      * the layers are separated by a caret and each group consists of 2 to 4 characters
00043      * if no second layer is defined it is stored as 0xFFFFFFFF, if the second layer
00044      * is empty (needed for matching) the layer has the value 0.
00045      */
00046     struct t_terrain {
00047         t_terrain(const std::string& b, const std::string& o);
00048         t_terrain(const std::string& b, t_layer o = NO_LAYER);
00049         t_terrain(t_layer b, t_layer o) : base(b), overlay(o) {};
00050         t_terrain() : base(0), overlay(NO_LAYER) {}
00051 
00052         t_layer base;
00053         t_layer overlay;
00054     };
00055     const t_terrain NONE_TERRAIN = t_terrain();
00056 
00057     inline bool operator<(const t_terrain& a, const t_terrain& b)
00058         { return a.base < b.base ||  (a.base == b.base && a.overlay < b.overlay); }
00059 
00060     inline bool operator==(const t_terrain& a, const t_terrain& b)
00061         { return a.base == b.base && a.overlay == b.overlay; }
00062 
00063     inline bool operator!=(const t_terrain& a, const t_terrain& b)
00064         { return a.base != b.base || a.overlay != b.overlay; }
00065 
00066     inline t_terrain operator&(const t_terrain& a, const t_terrain& b)
00067         { return t_terrain(a.base & b.base, a.overlay & b.overlay); }
00068 
00069     inline t_terrain operator|(const t_terrain& a, const t_terrain& b)
00070         { return t_terrain(a.base | b.base, a.overlay | b.overlay); }
00071 
00072     // operator<< is defined later
00073 
00074     typedef std::vector<t_terrain> t_list;
00075     typedef std::vector<std::vector<t_terrain> > t_map;
00076 
00077     /**
00078      * This structure can be used for matching terrain strings.
00079      * It optimized for strings that need to be matched often,
00080      * and caches the wildcard info required for matching.
00081      */
00082     struct t_match{
00083         t_match();
00084         t_match(const std::string& str, const t_layer filler = NO_LAYER);
00085         t_match(const t_terrain& tcode);
00086 
00087         t_list terrain;
00088         t_list mask;
00089         t_list masked_terrain;
00090         bool has_wildcard;
00091         bool is_empty;
00092     };
00093 
00094     /**  Contains an x and y coordinate used for starting positions in maps. */
00095     struct coordinate {
00096         coordinate();
00097         coordinate(const size_t x_, const size_t y_);
00098         size_t x;
00099         size_t y;
00100     };
00101 
00102     // Exception thrown if there's an error with the terrain.
00103     // Note: atm most thrown result in a crash, but I like
00104     // an uncatched exception better than an assert.
00105     struct error : public game::error {
00106         error(const std::string& message) : game::error(message) {}
00107     };
00108 
00109     // Some types of terrain which must be known, and can't just
00110     // be loaded in dynamically because they're special.
00111     // It's asserted that there will be corresponding entries for
00112     // these types of terrain in the terrain configuration file.
00113     extern const t_terrain VOID_TERRAIN;
00114     extern const t_terrain FOGGED;
00115 
00116     // On the map the user can use this type to make odd shaped maps look good.
00117     extern const t_terrain OFF_MAP_USER;
00118 
00119     extern const t_terrain HUMAN_CASTLE;
00120     extern const t_terrain HUMAN_KEEP;
00121     extern const t_terrain SHALLOW_WATER;
00122     extern const t_terrain DEEP_WATER;
00123     extern const t_terrain GRASS_LAND;
00124     extern const t_terrain FOREST;
00125     extern const t_terrain MOUNTAIN;
00126     extern const t_terrain HILL;
00127 
00128     extern const t_terrain CAVE_WALL;
00129     extern const t_terrain CAVE;
00130     extern const t_terrain UNDERGROUND_VILLAGE;
00131     extern const t_terrain DWARVEN_CASTLE;
00132     extern const t_terrain DWARVEN_KEEP;
00133 
00134     extern const t_terrain PLUS;    // +
00135     extern const t_terrain MINUS;   // -
00136     extern const t_terrain NOT;     // !
00137     extern const t_terrain STAR;    // *
00138     extern const t_terrain BASE;    // references the base terrain in movement/defense aliases
00139 
00140     extern const t_match ALL_FORESTS;
00141     extern const t_match ALL_HILLS;
00142     extern const t_match ALL_MOUNTAINS; //excluding impassable mountains
00143     extern const t_match ALL_SWAMPS;
00144 
00145     /**
00146      * Reads a single terrain from a string.
00147      *
00148      * @param str       The string which should contain 1 terrain code;
00149                                         the new format of a terrain code
00150      *              is 2 to 4 characters in the set
00151      *@verbatim
00152      *              [a-Z][A-Z]/|\_
00153      *@endverbatim
00154      *              The underscore is intended for internal use.
00155      *              Other letters and characters are not validated but
00156      *              users of these letters can get nasty surprices.
00157      *              The * is used as wildcard in some cases.
00158      *              The terrain code can be two groups separated by a caret,
00159      *              the first group is the base terrain,
00160      *              the second the overlay terrain.
00161      *
00162      * @param filler    if there's no layer this value will be used as the second layer
00163      *
00164      * @return          A single terrain code
00165      */
00166     t_terrain read_terrain_code(const std::string& str, const t_layer filler = NO_LAYER);
00167 
00168     /**
00169      * Writes a single terrain code to a string.
00170      * The writers only support the new format.
00171      *
00172      * @param tcode The terrain code to convert to a string
00173      *
00174      * @return      A string containing the terrain code
00175      */
00176     std::string write_terrain_code(const t_terrain& tcode);
00177     inline std::ostream &operator<<(std::ostream &s, const t_terrain &a)
00178         { s << write_terrain_code(a); return s; }
00179 
00180     /**
00181      * Reads a list of terrains from a string, when reading the
00182      *
00183      * @param str       A string with one or more terrain codes (see read_terrain_code)
00184      * @param filler    If there's no layer, this value will be used as the second layer
00185      *
00186      * @returns     A vector which contains the terrain codes found in the string
00187      */
00188      t_list read_list(const std::string& str, const t_layer filler = NO_LAYER);
00189 
00190     /**
00191      * Writes a list of terrains to a string, only writes the new format.
00192      *
00193      * @param list      A vector with one or more terrain codes
00194      *
00195      * @returns     A string with the terrain codes, comma separated
00196      *          and a space behind the commas. Not padded.
00197      */
00198     std::string write_list(const t_list& list);
00199 
00200     /**
00201      * Reads a gamemap string into a 2D vector
00202      *
00203      * @param str       A string containing the gamemap, the following rules
00204      *                  are stated for a gamemap:
00205      *                  * The map is square
00206      *                  * The map can be prefixed with one or more empty lines,
00207      *                    these lines are ignored
00208      *                  * The map can be postfixed with one or more empty lines,
00209      *                    these lines are ignored
00210      *                  * Every end of line can be followed by one or more empty
00211      *                    lines, these lines are ignored.
00212      *        @deprecated NOTE it's deprecated to use this feature.
00213      *                  * Terrain strings are separated by comma's or an end of line
00214      *                    symbol, for the last terrain string in the row. For
00215      *                    readability it's allowed to pad strings with either spaces
00216      *                    or tab, however the tab is deprecated.
00217      *                  * A terrain string contains either a terrain or a terrain and
00218      *                    starting loction. The following format is used
00219      *                    [S ]T
00220      *                    S = starting location a positive non-zero number
00221      *                    T = terrain code (see read_terrain_code)
00222      * @param starting_positions This parameter will be filled with the starting
00223      *                  locations found. Starting locations can only occur once
00224      *                  if multiple definitions occur of the same position only
00225      *                  the last is stored. The returned value is a map:
00226      *                  * first     the starting locations
00227      *                  * second    a coordinate structure where the location was found
00228      *
00229      * @returns         A 2D vector with the terrains found the vector data is stored
00230      *                  like result[x][y] where x the column number is and y the row number.
00231      */
00232     t_map read_game_map(const std::string& str, std::map<int, coordinate>& starting_positions);
00233 
00234     /**
00235      * Write a gamemap in to a vector string.
00236      *
00237      * @param map                A terrain vector, as returned from read_game_map
00238      * @param starting_positions A starting positions map, as returned from read_game_map
00239      *
00240      * @returns         A terrain string which can be read with read_game_map.
00241      *                  For readability the map is padded to groups of 12 chars,
00242      *                  followed by a comma and space.
00243      */
00244     std::string write_game_map(const t_map& map, std::map<int, coordinate> starting_positions = std::map<int, coordinate>());
00245 
00246     /**
00247      * Tests whether a specific terrain matches a list of expressions.
00248      * The list can use wildcard matching with *.
00249      * It also has an inversion function.
00250      * When a ! is found the result of the match is inverted.
00251      * The matching stops at the first match (regardless of the ! found)
00252      * the data is match from start to end.
00253      *
00254      * Example:
00255      * Ww, W*       does match and returns true
00256      * Ww, {!, W*}  does match and returns false (due to the !)
00257      * WW, Ww       doesn't match and return false
00258      *
00259      * Multilayer rules:
00260      * If a terrain has multiple layers, each layer will be matched separately,
00261      * returning true only if both layers match.
00262      *
00263      * Example:
00264      * A*^*     matches Abcd but also Abcd^Abcd
00265      * A*^      matches Abcd but *not* Abcd^Abcd
00266      * A*^Abcd  does not match Abcd but matches Abcd^Abcd
00267      *
00268      * Note: If an expression doesn't specify a second layer (i.e. it contains
00269      * no caret) the second layer will be filled in with a default value
00270      * (See read_terrain_code and read_list).
00271      *
00272      * In the terrain building code, the second layer will default to the wildcard,
00273      * so both A* and A*^* will match Abcd^Abcd
00274      *
00275      * @param src   the value to match (may not contain wildcards)
00276      * @param dest  the list of expressions to match against
00277      *
00278      * @returns     the result of the match (depending on the !'s)
00279      */
00280     bool terrain_matches(const t_terrain& src, const t_list& dest);
00281 
00282     /**
00283      * Tests whether a specific terrain matches an expression,
00284      * for matching rules see above.
00285      *
00286      * @param src   the value to match (may not contain wildcards)
00287      * @param dest  the expression to match against
00288      *
00289      * @returns     the result of the match (depending on the !'s)
00290      */
00291     bool terrain_matches(const t_terrain& src, const t_terrain& dest);
00292 
00293     /**
00294      * Tests whether a certain terrain matches a list of expressions, for matching
00295      * rules see above. The matching requires some bit mask which impose a
00296      * certain overhead. This version uses a cache to cache the masks so if
00297      * a list needs to be matched often this version is preferred.
00298      *
00299      * @param src   the value to match (may not contain wildcards)
00300      * @param dest  the cached list of expressions to match against
00301      *
00302      * @returns     the result of the match (depending on the !'s)
00303      */
00304     bool terrain_matches(const t_terrain& src, const t_match& dest);
00305 
00306     /**
00307      * Tests whether a terrain code contains a wildcard
00308      *
00309      *  @param tcode    the terrain code to test for a wildcard
00310      *
00311      *  @returns        true if wildcard found, else false
00312      */
00313     bool has_wildcard(const t_terrain& tcode);
00314 
00315     /**
00316      * Tests whether a terrain-code list contains at least
00317      * one item with a wildcard
00318      *
00319      *  @param list     the list to test for a wildcard
00320      *
00321      *  @returns        true if a wildcard found, else false
00322      */
00323     bool has_wildcard(const t_list& list);
00324 
00325     // These terrain letters are in the builder format,
00326     // and not usable in other parts of the engine
00327     const t_layer TB_STAR = '*' << 24;  // It can be assumed this is the equivalent of STAR
00328     const t_layer TB_DOT  = '.' << 24;
00329 
00330     /**
00331      * Reads a builder map.
00332      * A builder map differs a great deal from a normal map,
00333      * hence the different functions.
00334      *
00335      * @param str       The map data, a terrain letter is either a * or a . or a number as
00336      *                  anchor. The star or dot are stored in the base part of the terrain
00337      *                  and the anchor in the overlay part. If more letters are allowed as
00338      *                  special case they will be stored in the base part.
00339      *                  Anchor 0 is no anchor.
00340      *
00341      * @returns         A 2D vector with the data found the vector data is stored
00342      *                  like result[y][x] where x the column number is and y the row number.
00343      */
00344     t_map read_builder_map(const std::string& str);
00345 
00346 } // end namespace t_translation
00347 
00348 #endif
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines

Generated by doxygen 1.7.1 on Fri May 25 2012 01:03:11 for The Battle for Wesnoth
Gna! | Forum | Wiki | CIA | devdocs