00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018 #include "pent_include.h"
00019 #include "TextWidget.h"
00020 #include "ShapeFont.h"
00021 #include "RenderedText.h"
00022 #include "RenderSurface.h"
00023 #include "FontManager.h"
00024 #include "IDataSource.h"
00025 #include "ODataSource.h"
00026 #include "TTFont.h"
00027 #include "BarkGump.h"
00028 #include "AskGump.h"
00029 #include "ButtonWidget.h"
00030
00031 DEFINE_RUNTIME_CLASSTYPE_CODE(TextWidget,Gump);
00032
00033 TextWidget::TextWidget()
00034 : Gump(), cached_text(0)
00035 {
00036
00037 }
00038
00039 TextWidget::TextWidget(int X, int Y, std::string txt, bool gamefont_, int font,
00040 int w, int h, Font::TextAlign align) :
00041 Gump(X, Y, w, h), text(txt), gamefont(gamefont_), fontnum(font),
00042 blendColour(0), current_start(0), current_end(0),
00043 targetwidth(w), targetheight(h), cached_text(0), textalign(align)
00044 {
00045
00046 }
00047
00048 TextWidget::~TextWidget(void)
00049 {
00050 delete cached_text;
00051 cached_text = 0;
00052 }
00053
00054
00055 void TextWidget::InitGump(Gump* newparent, bool take_focus)
00056 {
00057 Gump::InitGump(newparent, take_focus);
00058
00059 Pentagram::Font *font = getFont();
00060
00061
00062 dims.y = -font->getBaseline();
00063
00064
00065 dims.x = 0;
00066
00067 if (gamefont && getFont()->isHighRes()) {
00068 int w = 0;
00069 int x = 0, y = 0;
00070 ScreenSpaceToGumpRect(x, y, w, dims.y, ROUND_OUTSIDE);
00071
00072 int tx = dims.x;
00073 int ty = dims.y;
00074
00075
00076
00077 GumpRectToScreenSpace(tx,ty, targetwidth,targetheight, ROUND_OUTSIDE);
00078
00079 dims.w = targetwidth;
00080 dims.h = targetheight;
00081 x = 0; y = 0;
00082 ScreenSpaceToGumpRect(x, y, dims.w, dims.h, ROUND_OUTSIDE);
00083 }
00084
00085 setupNextText();
00086 }
00087
00088 int TextWidget::getVlead()
00089 {
00090 renderText();
00091 assert(cached_text);
00092
00093 int vlead = cached_text->getVlead();
00094
00095 if (gamefont && getFont()->isHighRes()) {
00096 int x=0,y=0,w=0;
00097 ScreenSpaceToGumpRect(x, y, w, vlead, ROUND_OUTSIDE);
00098 }
00099
00100 return vlead;
00101 }
00102
00103 Pentagram::Font* TextWidget::getFont() const
00104 {
00105 if (gamefont)
00106 return FontManager::get_instance()->getGameFont(fontnum, true);
00107 else
00108 return FontManager::get_instance()->getTTFont(fontnum);
00109 }
00110
00111 bool TextWidget::setupNextText()
00112 {
00113 current_start = current_end;
00114
00115 if (current_start >= text.size()) return false;
00116
00117 Pentagram::Font *font = getFont();
00118
00119 unsigned int remaining;
00120 font->getTextSize(text.substr(current_start), tx, ty, remaining,
00121 targetwidth, targetheight, textalign, true);
00122
00123
00124 dims.w = tx;
00125 dims.h = ty;
00126 dims.y = -font->getBaseline();
00127 dims.x = 0;
00128 current_end = current_start + remaining;
00129
00130 delete cached_text;
00131 cached_text = 0;
00132
00133 if (gamefont)
00134 {
00135 Pentagram::Font *font = getFont();
00136 if (font->isHighRes())
00137 {
00138 int x = 0, y = 0;
00139 ScreenSpaceToGumpRect(x,y, dims.w,dims.h, ROUND_OUTSIDE);
00140
00141 int w = 0;
00142 x = 0; y = 0;
00143 ScreenSpaceToGumpRect(x, y, w, dims.y, ROUND_OUTSIDE);
00144 }
00145 }
00146
00147 return true;
00148 }
00149
00150 void TextWidget::rewind()
00151 {
00152 current_start = 0;
00153 current_end = 0;
00154 setupNextText();
00155 }
00156
00157 void TextWidget::renderText()
00158 {
00159 if (!cached_text) {
00160 Pentagram::Font *font = getFont();
00161
00162 unsigned int remaining;
00163 cached_text = font->renderText(text.substr(current_start,
00164 current_end-current_start),
00165 remaining, targetwidth, targetheight,
00166 textalign, true);
00167 }
00168 }
00169
00170
00171 void TextWidget::PaintThis(RenderSurface*surf, sint32 lerp_factor, bool scaled)
00172 {
00173 Gump::PaintThis(surf,lerp_factor,scaled);
00174
00175 renderText();
00176
00177 if (scaled && gamefont && getFont()->isHighRes())
00178 {
00179 surf->FillAlpha(0xFF,dims.x,dims.y,dims.w, dims.h);
00180 return;
00181 }
00182
00183 if (!blendColour)
00184 cached_text->draw(surf, 0, 0);
00185 else
00186 cached_text->drawBlended(surf, 0, 0, blendColour);
00187 }
00188
00189
00190 void TextWidget::PaintComposited(RenderSurface* surf, sint32 lerp_factor, sint32 sx, sint32 sy)
00191 {
00192 Pentagram::Font *font = getFont();
00193
00194 if (!gamefont || !font->isHighRes()) return;
00195
00196 int x=0,y=0;
00197 GumpToScreenSpace(x,y,ROUND_BOTTOMRIGHT);
00198
00199 if (!blendColour)
00200 cached_text->draw(surf, x, y, true);
00201 else
00202 cached_text->drawBlended(surf, x, y, blendColour, true);
00203
00204 if (parent->IsOfType<BarkGump>()) return;
00205
00206 if (parent->IsOfType<ButtonWidget>() && parent->GetParent()->IsOfType<AskGump>()) return;
00207
00208 x=dims.x; y=dims.y;
00209 int w=dims.w, h=dims.h;
00210 GumpRectToScreenSpace(x, y, w, h, ROUND_OUTSIDE);
00211 surf->FillAlpha(0x00, x, y, w, h);
00212 }
00213
00214
00215 Gump* TextWidget::OnMouseMotion(int mx, int my)
00216 {
00217 return 0;
00218 }
00219
00220
00221 void TextWidget::saveData(ODataSource* ods)
00222 {
00223 Gump::saveData(ods);
00224
00225 ods->write1(gamefont ? 1 : 0);
00226 ods->write4(static_cast<uint32>(fontnum));
00227 ods->write4(blendColour);
00228 ods->write4(static_cast<uint32>(current_start));
00229 ods->write4(static_cast<uint32>(current_end));
00230 ods->write4(static_cast<uint32>(targetwidth));
00231 ods->write4(static_cast<uint32>(targetheight));
00232 ods->write2(static_cast<uint16>(textalign));
00233 ods->write4(text.size());
00234 ods->write(text.c_str(), text.size());
00235 }
00236
00237 bool TextWidget::loadData(IDataSource* ids, uint32 version)
00238 {
00239 if (!Gump::loadData(ids, version)) return false;
00240
00241 gamefont = (ids->read1() != 0);
00242 fontnum = static_cast<int>(ids->read4());
00243 blendColour = ids->read4();
00244 current_start = static_cast<int>(ids->read4());
00245 current_end = static_cast<int>(ids->read4());
00246 targetwidth = static_cast<int>(ids->read4());
00247 targetheight = static_cast<int>(ids->read4());
00248 textalign = static_cast<Font::TextAlign>(ids->read2());
00249
00250 uint32 slen = ids->read4();
00251 if (slen > 0) {
00252 char* buf = new char[slen+1];
00253 ids->read(buf, slen);
00254 buf[slen] = 0;
00255 text = buf;
00256 delete[] buf;
00257 } else {
00258 text = "";
00259 }
00260
00261
00262
00263 Pentagram::Font *font = getFont();
00264
00265 int tx, ty;
00266 unsigned int remaining;
00267 font->getTextSize(text.substr(current_start), tx, ty, remaining,
00268 targetwidth, targetheight, textalign, true);
00269
00270
00271 dims.y = -font->getBaseline();
00272 dims.w = tx;
00273 dims.h = ty;
00274 current_end = current_start + remaining;
00275
00276 return true;
00277 }
00278
00279
00280