Main Page | Class Hierarchy | Alphabetical List | Data Structures | Directories | File List | Data Fields | Globals

SubTitleAgent.cpp

Go to the documentation of this file.
00001 /*
00002  * Copyright (C) 2004 Ivo Danihelka (ivo@danihelka.net)
00003  *
00004  * This program is free software; you can redistribute it and/or modify
00005  * it under the terms of the GNU General Public License as published by
00006  * the Free Software Foundation; either version 2 of the License, or
00007  * (at your option) any later version.
00008  */
00009 #include "SubTitleAgent.h"
00010 
00011 #include "Title.h"
00012 #include "Font.h"
00013 #include "ResColorPack.h"
00014 
00015 #include "Path.h"
00016 #include "OptionAgent.h"
00017 #include "minmax.h"
00018 
00019 //-----------------------------------------------------------------
00020     void
00021 SubTitleAgent::own_init()
00022 {
00023     m_limitY = TITLE_LIMIT_Y;
00024     m_colors = new ResColorPack();
00025 
00026     m_font = NULL;
00027     m_font = new Font(Path::dataReadPath("font/font_subtitle.ttf"), 20);
00028 }
00029 //-----------------------------------------------------------------
00030 /**
00031  * Shift all titles up.
00032  * Try remove the oldest subtitle.
00033  */
00034     void
00035 SubTitleAgent::own_update()
00036 {
00037     if (!m_titles.empty()) {
00038         shiftTitlesUp(TITLE_SPEED);
00039 
00040         if (m_titles.front()->isGone()) {
00041             delete m_titles.front();
00042             m_titles.pop_front();
00043         }
00044     }
00045 }
00046 //-----------------------------------------------------------------
00047     void
00048 SubTitleAgent::own_shutdown()
00049 {
00050     removeAll();
00051     delete m_colors;
00052     if (m_font) {
00053         delete m_font;
00054     }
00055 }
00056 
00057 //-----------------------------------------------------------------
00058     void
00059 SubTitleAgent::addFont(const std::string &fontname, Color *new_color)
00060 {
00061     m_colors->addRes(fontname, new_color);
00062 }
00063 //-----------------------------------------------------------------
00064 /**
00065  * Create new subtitle.
00066  * Shift all existing subtitles up.
00067  */
00068 void
00069 SubTitleAgent::newSubtitle(const std::string &original,
00070         const std::string &fontname)
00071 {
00072     const Color *color = m_colors->getRes(fontname);
00073 
00074     std::string subtitle = original;
00075     while (!subtitle.empty()) {
00076         subtitle = splitAndCreate(subtitle, color);
00077     }
00078 }
00079 //-----------------------------------------------------------------
00080 /**
00081  * Split subtitle, create title and return rest.
00082  * @return rest or empty string
00083  */
00084 std::string
00085 SubTitleAgent::splitAndCreate(const std::string &original,
00086         const Color *color)
00087 {
00088     std::string subtitle = original;
00089     int screen_width = OptionAgent::agent()->getAsInt("screen_width");
00090 
00091     int text_width = m_font->calcTextWidth(subtitle);
00092     while (text_width > screen_width - 2 * TITLE_BORDER) {
00093         trimRest(subtitle);
00094         text_width = m_font->calcTextWidth(subtitle);
00095     }
00096 
00097     std::string rest = "";
00098     if (!subtitle.empty()) {
00099         newShortSubtitle(subtitle, color);
00100 
00101         if (original.size() > subtitle.size()) {
00102             rest = original.substr(subtitle.size());
00103         }
00104     }
00105     return rest;
00106 }
00107 //-----------------------------------------------------------------
00108 /**
00109  * Break long string.
00110  * String is trimed at ' '
00111  * but not at " . " (single char surrounded with spaces).
00112  *
00113  * @param buffer buffer to change
00114  */
00115 void
00116 SubTitleAgent::trimRest(std::string &buffer)
00117 {
00118     int i;
00119     for (i = buffer.size() - 1; i >= 0; --i) {
00120         if (buffer[i] == ' ' &&
00121                 !(i - 2 >= 0 && buffer[i - 2] == ' '))
00122         {
00123             break;
00124         }
00125     }
00126 
00127     if (i <= 0) {
00128         LOG_WARNING(ExInfo("unbreakable string")
00129                 .addInfo("string", buffer));
00130         if (buffer.size() > 4) {
00131             buffer.erase(buffer.size() - 4);
00132         }
00133         else {
00134             buffer = "";
00135         }
00136     }
00137     else {
00138         buffer.erase(i);
00139     }
00140 }
00141 //-----------------------------------------------------------------
00142     void
00143 SubTitleAgent::newShortSubtitle(const std::string &subtitle,
00144         const Color *color)
00145 {
00146     int startY = lowestY();
00147     int finalY = TITLE_BASE + TITLE_ROW;
00148     int bonusTime = (TITLE_BASE - startY + m_limitY - TITLE_LIMIT_Y)
00149         / TITLE_SPEED;
00150     Title *title = new Title(startY, finalY, bonusTime, m_limitY,
00151             subtitle, m_font, color);
00152     shiftFinalsUp(TITLE_ROW);
00153     m_titles.push_back(title);
00154 }
00155 //-----------------------------------------------------------------
00156 /**
00157  * Increase Y for all existing titles.
00158  */
00159     void
00160 SubTitleAgent::shiftTitlesUp(int rate)
00161 {
00162     t_titles::iterator end = m_titles.end();
00163     for (t_titles::iterator i = m_titles.begin(); i != end; ++i) {
00164         (*i)->shiftUp(rate);
00165     }
00166 }
00167 //-----------------------------------------------------------------
00168 /**
00169  * Increase finalY for all existing titles.
00170  */
00171     void
00172 SubTitleAgent::shiftFinalsUp(int rate)
00173 {
00174     t_titles::iterator end = m_titles.end();
00175     for (t_titles::iterator i = m_titles.begin(); i != end; ++i) {
00176         (*i)->shiftFinalUp(rate);
00177     }
00178 }
00179 //-----------------------------------------------------------------
00180 /**
00181  * Get lowest possible Y.
00182  * It can be negative.
00183  */
00184     int
00185 SubTitleAgent::lowestY()
00186 {
00187     int lowest = TITLE_BASE;
00188     if (!m_titles.empty()) {
00189         int lastest = m_titles.back()->getY() - TITLE_ROW;
00190         lowest = min(lowest, lastest);
00191     }
00192     return lowest;
00193 }
00194 //-----------------------------------------------------------------
00195 /**
00196  * Kill all running subtitles.
00197  */
00198 void
00199 SubTitleAgent::killTalks()
00200 {
00201     t_titles::iterator end = m_titles.end();
00202     for (t_titles::iterator i = m_titles.begin(); i != end; ++i) {
00203         delete *i;
00204     }
00205     m_titles.clear();
00206 }
00207 //-----------------------------------------------------------------
00208 /**
00209  * Kill all subtitles and remove fonts.
00210  */
00211     void
00212 SubTitleAgent::removeAll()
00213 {
00214     killTalks();
00215     m_colors->removeAll();
00216 }
00217 
00218 //-----------------------------------------------------------------
00219 /**
00220  * Draw all subtitles.
00221  */
00222 void
00223 SubTitleAgent::drawOn(SDL_Surface *screen)
00224 {
00225     if (OptionAgent::agent()->getAsBool("subtitles", true)) {
00226         t_titles::iterator end = m_titles.end();
00227         for (t_titles::iterator i = m_titles.begin(); i != end; ++i) {
00228             (*i)->drawOn(screen);
00229         }
00230     }
00231 }

Generated on Wed Jun 1 09:54:31 2005 for Fish Fillets - Next Generation by  doxygen 1.4.2