00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #include "TextElement.h"
00023
00024
00025 #include <QFontMetrics>
00026 #include <QPainter>
00027
00028 #include <kdebug.h>
00029
00030 #include "BasicElement.h"
00031 #include "contextstyle.h"
00032 #include "fontstyle.h"
00033 #include "FormulaElement.h"
00034 #include "kformulacommand.h"
00035 #include "SequenceElement.h"
00036 #include "symboltable.h"
00037
00038
00039 namespace KFormula {
00040
00041 TextElement::TextElement( BasicElement* parent ) : BasicElement(parent),
00042 character(' '),
00043 symbol(false)
00044 {
00045 charStyle( anyChar );
00046 charFamily( anyFamily );
00047 }
00048
00049 const QList<BasicElement*> TextElement::childElements()
00050 {
00051 return QList<BasicElement*>();
00052 }
00053
00054 void TextElement::readMathML( const QDomElement& element )
00055 {
00056 }
00057
00058 void TextElement::writeMathML( KoXmlWriter* writer, bool oasisFormat )
00059 {
00060 }
00061
00062
00063 TokenType TextElement::getTokenType() const
00064 {
00065 if ( isSymbol() ) {
00066 return getSymbolTable().charClass( character );
00067 }
00068
00069 switch ( character.unicode() ) {
00070 case '+':
00071 case '-':
00072 case '*':
00073
00074 return BINOP;
00075 case '=':
00076 case '<':
00077 case '>':
00078 return RELATION;
00079 case ',':
00080 case ';':
00081 case ':':
00082 return PUNCTUATION;
00083 case '\\':
00084 return SEPARATOR;
00085 case '\0':
00086 return ELEMENT;
00087 default:
00088 if ( character.isNumber() ) {
00089 return NUMBER;
00090 }
00091 else {
00092 return ORDINARY;
00093 }
00094 }
00095 }
00096
00097
00098
00099 bool TextElement::isInvisible() const
00100 {
00101
00102
00103
00104
00105 return false;
00106 }
00107
00108
00113 void TextElement::calcSizes(const ContextStyle& context, ContextStyle::TextStyle tstyle, ContextStyle::IndexStyle )
00114 {
00115 luPt mySize = context.getAdjustedSize( tstyle );
00116
00117
00118 QFont font = getFont( context );
00119 font.setPointSizeF( context.layoutUnitPtToPt( mySize ) );
00120
00121 QFontMetrics fm( font );
00122 QChar ch = getRealCharacter(context);
00123 if ( ch != QChar::Null ) {
00124 QRect bound = fm.boundingRect( ch );
00125 setWidth( context.ptToLayoutUnitPt( fm.width( ch ) ) );
00126 setHeight( context.ptToLayoutUnitPt( bound.height() ) );
00127 setBaseline( context.ptToLayoutUnitPt( -bound.top() ) );
00128
00129
00130
00131 if ( getBaseline() == 0 ) {
00132
00133 setBaseline( -1 );
00134 }
00135 }
00136 else {
00137 setWidth( qRound( context.getEmptyRectWidth() * 2./3. ) );
00138 setHeight( qRound( context.getEmptyRectHeight() * 2./3. ) );
00139 setBaseline( getHeight() );
00140 }
00141
00142
00143
00144 }
00145
00151 void TextElement::draw( QPainter& painter, const LuPixelRect& ,
00152 const ContextStyle& context,
00153 ContextStyle::TextStyle tstyle,
00154 ContextStyle::IndexStyle ,
00155 const LuPixelPoint& parentOrigin )
00156 {
00157 LuPixelPoint myPos( parentOrigin.x()+getX(), parentOrigin.y()+getY() );
00158
00159
00160
00161 setUpPainter( context, painter );
00162
00163 luPt mySize = context.getAdjustedSize( tstyle );
00164 QFont font = getFont( context );
00165 font.setPointSizeF( context.layoutUnitToFontSize( mySize, false ) );
00166 painter.setFont( font );
00167
00168
00169
00170
00171
00172
00173
00174
00175
00176
00177
00178
00179
00180
00181
00182
00183
00184
00185
00186
00187
00188
00189
00190
00191
00192
00193
00194
00195
00196
00197
00198
00199
00200
00201
00202 }
00203
00204
00205 void TextElement::dispatchFontCommand( FontCommand* cmd )
00206 {
00207 cmd->addTextElement( this );
00208 }
00209
00210 void TextElement::setCharStyle( CharStyle cs )
00211 {
00212 charStyle( cs );
00213
00214 }
00215
00216 void TextElement::setCharFamily( CharFamily cf )
00217 {
00218 charFamily( cf );
00219
00220 }
00221
00222 QChar TextElement::getRealCharacter(const ContextStyle& context)
00223 {
00224 if ( !isSymbol() ) {
00225 const FontStyle& fontStyle = context.fontStyle();
00226 const AlphaTable* alphaTable = fontStyle.alphaTable();
00227 if ( alphaTable != 0 ) {
00228 #warning "port it"
00229
00230
00231
00232
00233
00234
00235 }
00236 return character;
00237 }
00238 else {
00239 return getSymbolTable().character(character, charStyle());
00240 }
00241 }
00242
00243
00244 QFont TextElement::getFont(const ContextStyle& context)
00245 {
00246 if ( !isSymbol() ) {
00247 const FontStyle& fontStyle = context.fontStyle();
00248 const AlphaTable* alphaTable = fontStyle.alphaTable();
00249 if ( alphaTable != 0 ) {
00250 #warning "kde4: port it"
00251
00252
00253
00254
00255
00256
00257 }
00258 QFont font;
00259
00260
00261
00262
00263
00264
00265 switch ( charStyle() ) {
00266 case anyChar:
00267 break;
00268 case normalChar:
00269 font.setItalic( false );
00270 font.setBold( false );
00271 break;
00272 case boldChar:
00273 font.setItalic( false );
00274 font.setBold( true );
00275 break;
00276 case italicChar:
00277 font.setItalic( true );
00278 font.setBold( false );
00279 break;
00280 case boldItalicChar:
00281 font.setItalic( true );
00282 font.setBold( true );
00283 break;
00284 }
00285 return font;
00286 }
00287 return context.symbolTable().font( character, charStyle() );
00288 }
00289
00290
00291 void TextElement::setUpPainter(const ContextStyle& context, QPainter& painter)
00292 {
00293
00294
00295
00296
00297
00298
00299 }
00300
00301 const SymbolTable& TextElement::getSymbolTable() const
00302 {
00303 static SymbolTable s;
00304 return s;
00305 }
00306
00307
00311 void TextElement::writeDom(QDomElement element)
00312 {
00313 BasicElement::writeDom(element);
00314 element.setAttribute("CHAR", QString(character));
00315
00316
00317 if (symbol) element.setAttribute("SYMBOL", "3");
00318
00319 switch ( charStyle() ) {
00320 case anyChar: break;
00321 case normalChar: element.setAttribute("STYLE", "normal"); break;
00322 case boldChar: element.setAttribute("STYLE", "bold"); break;
00323 case italicChar: element.setAttribute("STYLE", "italic"); break;
00324 case boldItalicChar: element.setAttribute("STYLE", "bolditalic"); break;
00325 }
00326
00327 switch ( charFamily() ) {
00328 case normalFamily: element.setAttribute("FAMILY", "normal"); break;
00329 case scriptFamily: element.setAttribute("FAMILY", "script"); break;
00330 case frakturFamily: element.setAttribute("FAMILY", "fraktur"); break;
00331 case doubleStruckFamily: element.setAttribute("FAMILY", "doublestruck"); break;
00332 case anyFamily: break;
00333 }
00334 }
00335
00340 bool TextElement::readAttributesFromDom(QDomElement element)
00341 {
00342 if (!BasicElement::readAttributesFromDom(element)) {
00343 return false;
00344 }
00345 QString charStr = element.attribute("CHAR");
00346 if(!charStr.isNull()) {
00347 character = charStr.at(0);
00348 }
00349 QString symbolStr = element.attribute("SYMBOL");
00350 if(!symbolStr.isNull()) {
00351 int symbolInt = symbolStr.toInt();
00352 if ( symbolInt == 1 ) {
00353 character = getSymbolTable().unicodeFromSymbolFont(character);
00354 }
00355 if ( symbolInt == 2 ) {
00356 switch ( character.unicode() ) {
00357 case 0x03D5: character = 0x03C6; break;
00358 case 0x03C6: character = 0x03D5; break;
00359 case 0x03Ba: character = 0x03BA; break;
00360 case 0x00B4: character = 0x2032; break;
00361 case 0x2215: character = 0x2244; break;
00362 case 0x00B7: character = 0x2022; break;
00363 case 0x1D574: character = 0x2111; break;
00364 case 0x1D579: character = 0x211C; break;
00365 case 0x2219: character = 0x22C5; break;
00366 case 0x2662: character = 0x26C4; break;
00367 case 0x220B: character = 0x220D; break;
00368 case 0x224C: character = 0x2245; break;
00369 case 0x03DB: character = 0x03C2; break;
00370 }
00371 }
00372 symbol = symbolInt != 0;
00373 }
00374
00375 QString styleStr = element.attribute("STYLE");
00376 if ( styleStr == "normal" ) {
00377 charStyle( normalChar );
00378 }
00379 else if ( styleStr == "bold" ) {
00380 charStyle( boldChar );
00381 }
00382 else if ( styleStr == "italic" ) {
00383 charStyle( italicChar );
00384 }
00385 else if ( styleStr == "bolditalic" ) {
00386 charStyle( boldItalicChar );
00387 }
00388 else {
00389 charStyle( anyChar );
00390 }
00391
00392 QString familyStr = element.attribute( "FAMILY" );
00393 if ( familyStr == "normal" ) {
00394 charFamily( normalFamily );
00395 }
00396 else if ( familyStr == "script" ) {
00397 charFamily( scriptFamily );
00398 }
00399 else if ( familyStr == "fraktur" ) {
00400 charFamily( frakturFamily );
00401 }
00402 else if ( familyStr == "doublestruck" ) {
00403 charFamily( doubleStruckFamily );
00404 }
00405 else {
00406 charFamily( anyFamily );
00407 }
00408
00409 return true;
00410 }
00411
00417 bool TextElement::readContentFromDom(QDomNode& node)
00418 {
00419 return BasicElement::readContentFromDom(node);
00420 }
00421
00422 }