Scribus Developer Documentation - API
logo-pen

Scribus Developer Documentation - API

story.cpp

Go to the documentation of this file.
00001 /*
00002 For general Scribus (>=1.3.2) copyright and licensing information please refer
00003 to the COPYING file provided with the program. Following this notice may exist
00004 a copyright and/or license notice that predates the release of Scribus 1.3.2
00005 for which a new license (GPL+exception) is in place.
00006 */
00007 /***************************************************************************
00008                           story.cpp  -  description
00009                              -------------------
00010     begin                : Tue Nov 11 2003
00011     copyright            : (C) 2003 by Franz Schmid
00012     email                : Franz.Schmid@altmuehlnet.de
00013  ***************************************************************************/
00014 
00015 /***************************************************************************
00016  *                                                                         *
00017  *   This program is free software; you can redistribute it and/or modify  *
00018  *   it under the terms of the GNU General Public License as published by  *
00019  *   the Free Software Foundation; either version 2 of the License, or     *
00020  *   (at your option) any later version.                                   *
00021  *                                                                         *
00022  ***************************************************************************/
00023 
00024 #include <QApplication>
00025 #include <QCloseEvent>
00026 #include <QColorDialog>
00027 #include <QComboBox>
00028 #include <QCursor>
00029 #include <QDesktopWidget>
00030 #include <QEvent>
00031 #include <QFocusEvent>
00032 #include <QFontDialog>
00033 #include <QFrame>
00034 #include <QGridLayout>
00035 #include <QHBoxLayout>
00036 #include <QHideEvent>
00037 #include <QKeyEvent>
00038 #include <QLabel>
00039 #include <QList>
00040 #include <QMouseEvent>
00041 #include <QPaintEvent>
00042 #include <QPalette>
00043 #include <QPixmap>
00044 #include <QRegExp>
00045 #include <QShowEvent>
00046 #include <QTextBlock>
00047 #include <QTextCodec>
00048 #include <QTextLayout>
00049 #include <QToolTip>
00050 
00051 #include "actionmanager.h"
00052 #include "alignselect.h"
00053 #include "charselect.h"
00054 #include "colorcombo.h"
00055 #include "colorlistbox.h"
00056 #include "commonstrings.h"
00057 #include "customfdialog.h"
00058 #include "fontcombo.h"
00059 #include "menumanager.h"
00060 #include "pageitem.h"
00061 #include "pageitem_textframe.h"
00062 #include "pluginmanager.h"
00063 #include "prefscontext.h"
00064 #include "prefsfile.h"
00065 #include "prefsmanager.h"
00066 #include "scfonts.h"
00067 #include "scmessagebox.h"
00068 #include "scplugin.h"
00069 #include "scraction.h"
00070 #include "scribuscore.h"
00071 #include "scrspinbox.h"
00072 #include "search.h"
00073 #include "serializer.h"
00074 #include "shadebutton.h"
00075 #include "spalette.h"
00076 #include "story.h"
00077 #include "styleitem.h"
00078 #include "stylemanager.h"
00079 #include "styleselect.h"
00080 #include "text/nlsconfig.h"
00081 #include "util.h"
00082 #include "util_icon.h"
00083 
00084 class StyledTextMimeData : public QMimeData
00085 {
00086 protected:
00087     StoryText m_styledText;
00088 
00089 public:
00090     const StoryText& styledText(void) const { return m_styledText; }
00091     void  setStyledText(const StoryText& text)
00092     {
00093         QByteArray styledTextData (sizeof(void*), 0);
00094         m_styledText.clear();
00095         m_styledText.insert(0, text, true);
00096         styledTextData.setNum((quintptr)((quintptr*) &m_styledText));
00097         setData("application/x-scribus-styledtext", styledTextData);
00098     };
00099 };
00100 
00101 SideBar::SideBar(QWidget *pa) : QLabel(pa)
00102 {
00103     QPalette pal;
00104     pal.setColor(QPalette::Window, QColor(255,255,255));
00105     setAutoFillBackground(true);
00106     setPalette(pal);
00107     offs = 0;
00108     editor = 0;
00109     noUpdt = true;
00110     inRep = false;
00111     pmen = new QMenu(this);
00112     setMinimumWidth(fontMetrics().width( tr("No Style") )+30);
00113 }
00114 
00115 void SideBar::mouseReleaseEvent(QMouseEvent *m)
00116 {
00117     int p = editor->cursorForPosition(QPoint(2, m->y()+offs)).position();
00118     CurrentPar = editor->StyledText.nrOfParagraph(p);
00119     int pos = editor->StyledText.startOfParagraph(p);
00120 
00121     ParaStyleComboBox* paraStyleCombo = new ParaStyleComboBox(this);
00122     paraStyleCombo->setDoc(editor->doc);
00123     if ((CurrentPar < static_cast<int>(editor->StyledText.nrOfParagraphs())) && (editor->StyledText.length() != 0))
00124     {
00125         int len = editor->StyledText.endOfParagraph(CurrentPar) - editor->StyledText.startOfParagraph(CurrentPar);
00126         if (len > 0)
00127             paraStyleCombo->setFormat(editor->StyledText.paragraphStyle(pos).displayName());
00128         else
00129             paraStyleCombo->setFormat("");
00130     }
00131     else
00132         paraStyleCombo->setFormat("");
00133     connect(paraStyleCombo, SIGNAL(newStyle(const QString&)), this, SLOT(setPStyle(const QString&)));
00134     pmen->clear();
00135     paraStyleAct = new QWidgetAction(this);
00136     paraStyleAct->setDefaultWidget(paraStyleCombo);
00137     pmen->addAction(paraStyleAct);
00138     pmen->addAction( tr("Edit Styles..."), this, SLOT(editStyles()));
00139     pmen->exec(QCursor::pos());
00140 }
00141 
00142 void SideBar::editStyles()
00143 {
00144     emit sigEditStyles();
00145 }
00146 
00147 void SideBar::setPStyle(const QString& name)
00148 {
00149     emit ChangeStyle(CurrentPar, name);
00150     pmen->close();
00151 }
00152 
00153 void SideBar::paintEvent(QPaintEvent *e)
00154 {
00155     inRep = true;
00156     QLabel::paintEvent(e);
00157     QList<QRect> paraList;
00158     for (uint pr = 0; pr < editor->StyledText.nrOfParagraphs(); ++pr)
00159     {
00160         int pos = editor->StyledText.startOfParagraph(pr);
00161         QTextCursor cur(editor->document());
00162         cur.setPosition(pos);
00163         QTextBlock tb = cur.block();
00164         paraList.append(tb.layout()->boundingRect().toRect());
00165     }
00166     QPainter p;
00167     p.begin(this);
00168     if ((editor != 0) && (noUpdt))
00169     {
00170         int gesY = 0;
00171         for (uint pa = 0; pa < editor->StyledText.nrOfParagraphs(); ++pa)
00172         {
00173             QRect re = paraList[pa];
00174             if (!re.isValid())
00175                 break;
00176             int hh = re.height();
00177             re.setWidth(width()-5);
00178             re.setHeight(re.height()-2);
00179             re.translate(5, 2);
00180             if (((re.y()+re.height())-offs + gesY < height()) && ((re.y()+re.height())-offs + gesY >= 0))
00181                 p.drawLine(0, (re.y()+re.height())-offs + gesY, width()-1, (re.y()+re.height())-offs + gesY);
00182             if ((re.y()-offs + gesY < height()) && (re.y()-offs + gesY >= 0))
00183             {
00184                 re.moveTop(gesY-offs+2);
00185                 QString parname = editor->StyledText.paragraphStyle(editor->StyledText.startOfParagraph(pa)).parent();
00186                 if (parname.isEmpty())
00187                     parname = tr("No Style");
00188                 p.drawText(re, Qt::AlignLeft | Qt::AlignTop, parname);
00189             }
00190             gesY += hh;
00191         }
00192     }
00193     p.end();
00194     inRep = false;
00195 }
00196 
00197 void SideBar::doMove(int, int y)
00198 {
00199     offs -= y;
00200     if (!inRep)
00201         update();
00202 }
00203 
00204 void SideBar::doRepaint()
00205 {
00206     if (!inRep)
00207         update();
00208 }
00209 
00210 void SideBar::setRepaint(bool r)
00211 {
00212     noUpdt = r;
00213 }
00214 
00215 SEditor::SEditor(QWidget* parent, ScribusDoc *docc, StoryEditor* parentSE) : QTextEdit(parent)
00216 {
00217     setCurrentDocument(docc);
00218     parentStoryEditor=parentSE;
00219     wasMod = false;
00220     StoredSel = false;
00221     SelCharStart = 0;
00222     SelParaStart = 0;
00223     StyledText.clear();
00224     document()->setUndoRedoEnabled(true);
00225     viewport()->setAcceptDrops(false);
00226     unicodeTextEditMode = false;
00227     blockContentsChangeHook = 0;
00228     setAutoFillBackground(true);
00229     connect(QApplication::clipboard(), SIGNAL(dataChanged()), this, SLOT(ClipChange()));
00230     connect(this->document(), SIGNAL(contentsChange(int, int, int)), this, SLOT(handleContentsChange(int, int, int)));
00231 }
00232 
00233 void SEditor::setCurrentDocument(ScribusDoc *docc)
00234 {
00235     doc = docc;
00236     StyledText = StoryText(docc);
00237 }
00238 
00239 void SEditor::inputMethodEvent(QInputMethodEvent *event)
00240 {
00241     QString uc = event->commitString();
00242     if ((!uc.isEmpty()) && ((*doc->AllFonts)[CurrFont].canRender(uc[0])))
00243     {
00244         // Should be processed by the handleContentsChange slot
00245         // insertCharsInternal(event->commitString());
00246         QTextEdit::inputMethodEvent(event);
00247         emit SideBarUp(true);
00248         emit SideBarUpdate();
00249     }
00250 }
00251 
00252 void SEditor::keyPressEvent(QKeyEvent *k)
00253 {
00254     emit SideBarUp(false);
00255     int pos = textCursor().position();
00256     int keyMod=0;
00257     if (k->modifiers() & Qt::ShiftModifier)
00258         keyMod |= Qt::SHIFT;
00259     if (k->modifiers() & Qt::ControlModifier)
00260         keyMod |= Qt::CTRL;
00261     if (k->modifiers() & Qt::AltModifier)
00262         keyMod |= Qt::ALT;
00263 
00264     QString uc = k->text();
00265     if ((k->modifiers() == Qt::ControlModifier) ||
00266         (k->modifiers() == (Qt::ControlModifier | Qt::ShiftModifier)) ||
00267         (k->modifiers() == (Qt::ControlModifier | Qt::KeypadModifier)) ||
00268         (k->modifiers() == (Qt::ControlModifier | Qt::ShiftModifier | Qt::KeypadModifier))
00269        )
00270     {
00271         switch (k->key())
00272         {
00273             case Qt::Key_K:
00274                 moveCursor(QTextCursor::EndOfLine, QTextCursor::KeepAnchor);
00275                 textCursor().removeSelectedText();
00276                 break;
00277             case Qt::Key_D:
00278                 moveCursor(QTextCursor::NextCharacter, QTextCursor::KeepAnchor);
00279                 textCursor().removeSelectedText();
00280                 break;
00281             case Qt::Key_H:
00282                 moveCursor(QTextCursor::PreviousCharacter, QTextCursor::KeepAnchor);
00283                 textCursor().removeSelectedText();
00284                 break;
00285             /*case Qt::Key_X:
00286                 cut();
00287                 return;
00288                 break;
00289             case Qt::Key_V:
00290                 paste();
00291                 return;
00292                 break;*/
00293             case Qt::Key_Y:
00294             case Qt::Key_Z:
00295                 emit SideBarUp(true);
00296                 return;
00297                 break;
00298         }
00299     }
00300     if ((k->modifiers() == Qt::NoModifier) ||
00301         (k->modifiers() == Qt::KeypadModifier) ||
00302         (k->modifiers() == Qt::ShiftModifier) ||
00303         (k->modifiers() == (Qt::ControlModifier | Qt::AltModifier)) ||
00304         (k->modifiers() == (Qt::ControlModifier | Qt::AltModifier | Qt::ShiftModifier)) // Shift + AltGr on Windows for polish characters
00305        )
00306     {
00307         if (unicodeTextEditMode)
00308         {
00309             int conv = 0;
00310             bool ok = false;
00311             unicodeInputString += k->text();
00312             conv = unicodeInputString.toInt(&ok, 16);
00313             if (!ok)
00314             {
00315                 unicodeTextEditMode = false;
00316                 unicodeInputCount = 0;
00317                 unicodeInputString = "";
00318                 return;
00319             }
00320             unicodeInputCount++;
00321             if (unicodeInputCount == 4)
00322             {
00323                 unicodeTextEditMode = false;
00324                 unicodeInputCount = 0;
00325                 unicodeInputString = "";
00326                 if (ok)
00327                 {
00328                     if (conv < 31)
00329                         conv = 32;
00330                     insertPlainText(QString(QChar(conv)));
00331                     emit SideBarUp(true);
00332                     emit SideBarUpdate();
00333                     return;
00334                 }
00335             }
00336             else
00337             {
00338                 emit SideBarUp(true);
00339                 emit SideBarUpdate();
00340                 return;
00341             }
00342         }
00343         wasMod = false;
00344         switch (k->key())
00345         {
00346             case Qt::Key_Escape:
00347                 k->ignore();
00348                 break;
00349             case Qt::Key_Shift:
00350             case Qt::Key_Control:
00351             case Qt::Key_Alt:
00352                 wasMod = true;
00353                 break;
00354             case Qt::Key_F12:
00355                 unicodeTextEditMode = true;
00356                 unicodeInputCount = 0;
00357                 unicodeInputString = "";
00358                 return;
00359                 break;
00360             case Qt::Key_Return:
00361             case Qt::Key_Enter:
00362                 {
00363                     insertChars(SpecialChars::PARSEP, k->text());
00364                     emit SideBarUp(true);
00365                     emit SideBarUpdate();
00366                     return;
00367                 }
00368                 break;
00369             case Qt::Key_Delete:
00370             case Qt::Key_Backspace:
00371             case Qt::Key_Left:
00372             case Qt::Key_Right:
00373             case Qt::Key_PageUp:
00374             case Qt::Key_PageDown:
00375             case Qt::Key_Up:
00376             case Qt::Key_Down:
00377             case Qt::Key_Home:
00378             case Qt::Key_End:
00379                 break;
00380             default:
00381                 if ((!k->text().isEmpty()) && ((*doc->AllFonts)[CurrFont].canRender(uc[0])))
00382                 {
00383                     QTextEdit::keyPressEvent(k);
00384                     emit SideBarUp(true);
00385                     emit SideBarUpdate();
00386                 }
00387                 return;
00388                 break;
00389         }
00390     }
00391     QTextEdit::keyPressEvent(k);
00392     emit SideBarUp(true);
00393     emit SideBarUpdate();
00394 }
00395 
00396 void SEditor::handleContentsChange(int position, int charsRemoved, int charsAdded)
00397 {
00398     if (blockContentsChangeHook <= 0)
00399     {
00400         if (charsRemoved > 0)
00401             StyledText.removeChars(position, charsRemoved);
00402         if (charsAdded > 0)
00403         {
00404             QTextCursor cursor = textCursor();
00405             cursor.setPosition(position);
00406             cursor.setPosition(position + charsAdded, QTextCursor::KeepAnchor);
00407             QString addedChars = cursor.selectedText();
00408             if (addedChars.length() > 0)
00409                 StyledText.insertChars(position, addedChars, true);
00410             qDebug("handleContentsChange : - %01d, + %01d, len %01d", charsRemoved, charsAdded, addedChars.length());
00411         }   
00412     }
00413 }
00414 
00415 void SEditor::focusOutEvent(QFocusEvent *e)
00416 {
00417     if (textCursor().hasSelection())
00418     {
00419         SelParaStart = textCursor().selectionStart();
00420         SelParaEnd = textCursor().selectionEnd();
00421         StoredSel = true;
00422     }
00423     else
00424     {
00425         SelParaStart = textCursor().position();
00426         StoredSel = false;
00427     }
00428     QTextEdit::focusOutEvent(e);
00429 }
00430 
00431 void SEditor::focusInEvent(QFocusEvent *e)
00432 {
00433     if (StoredSel)
00434     {
00435         textCursor().setPosition(SelParaStart);
00436         textCursor().setPosition(SelParaEnd, QTextCursor::KeepAnchor);
00437         StoredSel = false;
00438     }
00439     else
00440     {
00441         textCursor().setPosition(SelParaStart);
00442         StoredSel = false;
00443     }
00444         
00445     QTextEdit::focusInEvent(e);
00446 }
00447 
00448 void SEditor::insertChars(const QString& text)
00449 {
00450     if (textCursor().hasSelection())
00451         textCursor().removeSelectedText();
00452     ++blockContentsChangeHook;
00453     int pos = qMin(textCursor().position(), StyledText.length());
00454     StyledText.insertChars(pos, text, true);
00455     insertPlainText(text);
00456     --blockContentsChangeHook;
00457 }
00458 
00459 void SEditor::insertChars(const QString& styledText, const QString& editText)
00460 {
00461     if (textCursor().hasSelection())
00462         textCursor().removeSelectedText();
00463     if ((styledText.length() == editText.length()) && !styledText.isEmpty())
00464     {
00465         ++blockContentsChangeHook;
00466         int pos = qMin(textCursor().position(), StyledText.length());
00467         StyledText.insertChars(pos, styledText, true);
00468         insertPlainText(editText);
00469         --blockContentsChangeHook;
00470     }
00471 }
00472 
00473 void SEditor::insertCharsInternal(const QString& t)
00474 {
00475     if (textCursor().hasSelection())
00476         deleteSel();
00477     int pos = qMin(textCursor().position(), StyledText.length());
00478     StyledText.insertChars(pos, t, true);
00479 }
00480 
00481 void SEditor::insertCharsInternal(const QString& t, int pos)
00482 {
00483     if (textCursor().hasSelection())
00484         deleteSel();
00485     StyledText.insertChars(pos, t, true);
00486 }
00487 
00488 void SEditor::insertStyledText(const StoryText& styledText)
00489 {
00490     if (styledText.length() == 0)
00491         return;
00492     if (textCursor().hasSelection())
00493         deleteSel();
00494     int pos = qMin(textCursor().position(), StyledText.length());
00495     StyledText.insert(pos, styledText);
00496 }
00497 
00498 void SEditor::insertStyledText(const StoryText& styledText, int pos)
00499 {
00500     if (styledText.length() == 0)
00501         return;
00502     if (textCursor().hasSelection())
00503         deleteSel();
00504     StyledText.insert(pos, styledText);
00505 }
00506 
00507 void SEditor::saveItemText(PageItem *currItem)
00508 {
00509     currItem->CPos = 0;
00510     currItem->itemText.clear();
00511     currItem->itemText.setDefaultStyle(StyledText.defaultStyle());
00512     currItem->itemText.append(StyledText);
00513 /* uh... FIXME
00514         if (ch == SpecialChars::OBJECT)
00515             {
00516                 PageItem* embedded = chars->at(c)->cembedded;
00517                 currItem->doc()->FrameItems.append(embedded);
00518                 if (embedded->Groups.count() != 0)
00519                 {
00520                     for (uint ga=0; ga<FrameItems.count(); ++ga)
00521                     {
00522                         if (FrameItems.at(ga)->Groups.count() != 0)
00523                         {
00524                             if (FrameItems.at(ga)->Groups.top() == embedded->Groups.top())
00525                             {
00526                                 if (FrameItems.at(ga)->ItemNr != embedded->ItemNr)
00527                                 {
00528                                     if (currItem->doc()->FrameItems.find(FrameItems.at(ga)) == -1)
00529                                         currItem->doc()->FrameItems.append(FrameItems.at(ga));
00530                                 }
00531                             }
00532                         }
00533                     }
00534                 }
00535                 currItem->itemText.insertObject(pos, embedded);
00536             }
00537 */
00538 }
00539 
00540 void SEditor::setAlign(int align)
00541 {
00542     ++blockContentsChangeHook;
00543     switch (align)
00544     {
00545     case 0:
00546         setAlignment(Qt::AlignLeft);
00547         break;
00548     case 1:
00549         setAlignment(Qt::AlignCenter);
00550         break;
00551     case 2:
00552         setAlignment(Qt::AlignRight);
00553         break;
00554     case 3:
00555     case 4:
00556         setAlignment(Qt::AlignJustify);
00557         break;
00558     default:
00559         break;
00560     }
00561     --blockContentsChangeHook;
00562 }
00563 
00564 
00565 void SEditor::loadItemText(PageItem *currItem)
00566 {
00567     StyledText.clear();
00568     FrameItems.clear();
00569     StyledText.append(currItem->itemText);
00570     updateAll();
00571     int npars = currItem->itemText.nrOfParagraphs();
00572     SelParaStart = 0;
00573     while (currItem->CPos >= (SelCharStart = currItem->itemText.endOfParagraph(SelParaStart))
00574            && SelParaStart < npars)
00575         ++SelParaStart;
00576     if (currItem->CPos < SelCharStart)
00577         SelCharStart = currItem->CPos;
00578     SelCharStart -= currItem->itemText.startOfParagraph(SelParaStart);
00579     StoredSel = false;
00580     //qDebug("SE::loadItemText: cursor");
00581 //  setCursorPosition(SelParaStart, SelCharStart);
00582     emit setProps(SelParaStart, SelCharStart);
00583     SelParaStart = 0;
00584 }
00585 
00586 void SEditor::loadText(QString tx, PageItem *currItem)
00587 {
00588     setUpdatesEnabled(false);
00589     QString Text = "";
00590     StyledText.clear();
00591     StyledText.setDefaultStyle(currItem->itemText.defaultStyle());
00592     StyledText.insertChars(0, tx);
00593     updateAll();
00594     if (StyledText.length() != 0)
00595         emit setProps(0, 0);
00596     //qDebug("SE::loadText: cursor");
00597     textCursor().setPosition(0);
00598 }
00599 
00600 void SEditor::updateAll()
00601 {
00602     ++blockContentsChangeHook;
00603     clear();
00604     if (StyledText.length() == 0)
00605     {
00606         --blockContentsChangeHook;
00607         return;
00608     }
00609     setUpdatesEnabled(false);
00610     int pos = textCursor().position();
00611     QString Text = "";
00612     QString chars;
00613     int Csty = StyledText.charStyle(0).effects();
00614     int Ali = StyledText.paragraphStyle(0).alignment();
00615     setAlign(Ali);
00616     setStyle(Csty);
00617     for (uint pa = 0; pa < StyledText.nrOfParagraphs(); ++pa)
00618     {
00619         int start = StyledText.startOfParagraph(pa);
00620         int end = StyledText.endOfParagraph(pa);
00621         const ParagraphStyle& pstyle(StyledText.paragraphStyle(start));
00622         Ali = pstyle.alignment();
00623         setAlign(Ali);
00624         if (start >= end && pa < StyledText.nrOfParagraphs()-1)
00625         {
00626             Text += "\n";
00627             continue;
00628         }
00629         for (int a = start; a < end; ++a)
00630         {
00631             const CharStyle& cstyle(StyledText.charStyle(a));
00632             const QChar ch = StyledText.text(a);
00633             if (Csty != cstyle.effects() ||
00634                 ch == SpecialChars::OBJECT ||
00635                 ch == SpecialChars::PAGENUMBER ||
00636                 ch == SpecialChars::NBSPACE ||
00637                 ch == SpecialChars::FRAMEBREAK ||
00638                 ch == SpecialChars::COLBREAK ||
00639                 ch == SpecialChars::NBHYPHEN ||
00640                 ch == SpecialChars::LINEBREAK)
00641             {
00642                 setAlign(Ali);
00643                 setStyle(Csty);
00644                 insertPlainText(Text);
00645                 Text = "";
00646                 Csty = cstyle.effects();
00647             }
00648 
00649             if (ch == SpecialChars::OBJECT)
00650             {
00651                 setColor(true);
00652                 insertPlainText("@");
00653                 setColor(false);
00654             }
00655             else if (ch == SpecialChars::PAGENUMBER)
00656             {
00657                 setColor(true);
00658                 insertPlainText("#");
00659                 setColor(false);
00660             }
00661             else if (ch == SpecialChars::NBSPACE)
00662             {
00663                 setColor(true);
00664                 insertPlainText("_");
00665                 setColor(false);
00666             }
00667             else if (ch == SpecialChars::FRAMEBREAK)
00668             {
00669                 setColor(true);
00670                 insertPlainText("|");
00671                 setColor(false);
00672             }
00673             else if (ch == SpecialChars::COLBREAK)
00674             {
00675                 setColor(true);
00676                 insertPlainText("^");
00677                 setColor(false);
00678             }
00679             else if (ch == SpecialChars::NBHYPHEN)
00680             {
00681                 setColor(true);
00682                 insertPlainText("=");
00683                 setColor(false);
00684             }
00685             else if (ch == SpecialChars::LINEBREAK)
00686             {
00687                 setColor(true);
00688                 insertPlainText("*");
00689                 setColor(false);
00690             }
00691             else
00692                 Text += ch;
00693         }
00694         if (pa < StyledText.nrOfParagraphs()-1)
00695             Text += "\n";
00696     }
00697     setAlign(Ali);
00698     setStyle(Csty);
00699     insertPlainText(Text);
00700     textCursor().setPosition(pos);
00701     setUpdatesEnabled(true);
00702     --blockContentsChangeHook;
00703     //CB Removed to fix 2083 setCursorPosition(p, i);
00704 }
00705 
00706 
00707 void SEditor::updateFromChars(int pa)
00708 {
00709     int start = StyledText.startOfParagraph(pa);
00710     int end = StyledText.endOfParagraph(pa);
00711     if (start >= end)
00712         return;
00713     setUpdatesEnabled(false);
00714     int SelStart = start;
00715     int SelEnd = 0;
00716     int pos = textCursor().position();
00717     textCursor().clearSelection();
00718     int Csty = StyledText.charStyle(start).effects();
00719     for (int a = start; a < end; ++a)
00720     {
00721         if (Csty == StyledText.charStyle(a).effects())
00722             SelEnd++;
00723         else
00724         {
00725             textCursor().setPosition(SelStart);
00726             textCursor().setPosition(SelEnd, QTextCursor::KeepAnchor);
00727             setStyle(Csty);
00728             textCursor().clearSelection();
00729             Csty = StyledText.charStyle(a).effects();
00730             SelStart = SelEnd;
00731             SelEnd++;
00732         }
00733     }
00734     textCursor().setPosition(SelStart);
00735     textCursor().setPosition(SelEnd, QTextCursor::KeepAnchor);
00736     setStyle(Csty);
00737     textCursor().clearSelection();
00738     setAlign(StyledText.paragraphStyle(start).alignment());
00739     setUpdatesEnabled(true);
00740     textCursor().setPosition(pos);
00741 }
00742 
00743 /* updates the internal StyledText structure, applies 'newStyle' to the selection */
00744 void SEditor::updateSel(const ParagraphStyle& newStyle)
00745 {
00746     int PStart, PEnd, SelStart, SelEnd, start;
00747     if (StoredSel)
00748     {
00749         textCursor().setPosition(SelParaStart);
00750         textCursor().setPosition(SelParaEnd, QTextCursor::KeepAnchor);
00751         StoredSel = false;
00752     }
00753     SelStart = textCursor().selectionStart();
00754     PStart = StyledText.nrOfParagraph(SelStart);
00755     SelEnd = textCursor().selectionEnd();
00756     PEnd = StyledText.nrOfParagraph(SelEnd);
00757     for (int pa = PStart; pa <= PEnd; ++pa)
00758     {
00759         start = StyledText.startOfParagraph(pa);
00760         StyledText.applyStyle(start, newStyle);
00761     }
00762 }
00763 
00764 void SEditor::updateSel(const CharStyle& newStyle)
00765 {
00766     if (StoredSel)
00767     {
00768         textCursor().setPosition(SelParaStart);
00769         textCursor().setPosition(SelParaEnd, QTextCursor::KeepAnchor);
00770         StoredSel = false;
00771     }
00772     int start = textCursor().selectionStart();
00773     int end = textCursor().selectionEnd();
00774     if (start >= 0 && start < end)
00775         StyledText.applyCharStyle(start, end-start, newStyle);
00776 }
00777 
00778 
00779 void SEditor::deleteSel()
00780 {
00781     int start = textCursor().selectionStart();
00782     int end   = textCursor().selectionEnd();
00783     if (end > start)
00784         StyledText.removeChars(start, end-start);
00785     textCursor().setPosition(start);
00786     StoredSel = false;
00787 }
00788 
00789 void SEditor::setStyle(int Csty)
00790 {
00791     ++blockContentsChangeHook;
00792     QTextCharFormat charF;
00793     if (Csty & 8)
00794         charF.setFontUnderline(true);
00795     else
00796         charF.setFontUnderline(false);
00797     if (Csty & 16)
00798         charF.setFontStrikeOut(true);
00799     else
00800         charF.setFontStrikeOut(false);
00801     if (Csty & 1)
00802         charF.setVerticalAlignment(QTextCharFormat::AlignSuperScript);
00803     else if (Csty & 2)
00804         charF.setVerticalAlignment(QTextCharFormat::AlignSubScript);
00805     else
00806         charF.setVerticalAlignment(QTextCharFormat::AlignNormal);
00807     textCursor().setCharFormat(charF);
00808     --blockContentsChangeHook;
00809 }
00810 
00811 void SEditor::setColor(bool marker)
00812 {
00813     QColor tmp;
00814     if (marker)
00815         tmp = QColor(Qt::red);
00816     else
00817         tmp = QColor(Qt::black);
00818     setTextColor(tmp);
00819 }
00820 
00821 void SEditor::copy()
00822 {
00823     emit SideBarUp(false);
00824     if ((textCursor().hasSelection()) && (!textCursor().selectedText().isEmpty()))
00825     {
00826         disconnect(QApplication::clipboard(), SIGNAL(dataChanged()), this, SLOT(ClipChange()));
00827         QMimeData* mimeData = createMimeDataFromSelection();
00828         QApplication::clipboard()->setMimeData(mimeData, QClipboard::Clipboard);
00829         connect(QApplication::clipboard(), SIGNAL(dataChanged()), this, SLOT(ClipChange()));
00830         emit PasteAvail();
00831     }
00832     emit SideBarUp(true);
00833 }
00834 
00835 void SEditor::cut()
00836 {
00837     copy();
00838     emit SideBarUp(false);
00839     if (textCursor().hasSelection())
00840         textCursor().removeSelectedText();
00841     emit SideBarUp(true);
00842     emit SideBarUpdate();
00843 }
00844 
00845 void SEditor::paste()
00846 {
00847     emit SideBarUp(false);
00848     QString data = "";
00849     int newParaCount, lengthLastPara;
00850     int advanceLen = 0;
00851     int pos = textCursor().hasSelection() ? textCursor().selectionStart() : textCursor().position();
00852     const QMimeData* mimeData = QApplication::clipboard()->mimeData(QClipboard::Clipboard);
00853     if (mimeData->hasFormat("application/x-scribus-styledtext"))
00854     {
00855         const StyledTextMimeData* styledData = dynamic_cast<const StyledTextMimeData*>(mimeData);
00856         if (mimeData)
00857         {
00858             const StoryText& styledText = styledData->styledText();
00859             advanceLen = styledText.length();
00860             insertStyledText(styledText, pos);
00861         }
00862     }
00863     else
00864     {
00865 //      QString data = QApplication::clipboard()->text(QClipboard::Selection);
00866 //      if (data.isNull())
00867         data = QApplication::clipboard()->text(QClipboard::Clipboard);
00868         if (!data.isEmpty())
00869         {
00870             data.replace(QRegExp("\r"), "");
00871             newParaCount=data.count("\n");
00872             lengthLastPara=data.length()-data.lastIndexOf("\n");
00873             data.replace(QRegExp("\n"), SpecialChars::PARSEP);
00874 //          inserted=true;
00875             advanceLen = data.length() /*- newParaCount*/;
00876             insertCharsInternal(data, pos);
00877             emit PasteAvail();
00878         }
00879         else
00880         {
00881             emit SideBarUp(true);
00882             return;
00883         }
00884     }
00885     updateAll();
00886     setUpdatesEnabled(false);
00887     //qDebug("SE::paste: cursor");
00888 //  setCursorPosition(currentPara, currentCharPos);
00889     QTextCursor tCursor = textCursor();
00890     tCursor.setPosition(pos + advanceLen);
00891     setTextCursor(tCursor);
00892     /*for (int a = 0; a < advanceLen; ++a)
00893     {
00894         moveCursor(QTextCursor::Right, QTextCursor::MoveAnchor);
00895     }*/
00896     setUpdatesEnabled(true);
00897 //  if (inserted)
00898 //      setCursorPosition(currentPara+newParaCount,(newParaCount==0?currentCharPos:0)+lengthLastPara-1);
00899     repaint();
00900     emit SideBarUp(true);
00901     emit SideBarUpdate();
00902 }
00903 
00904 bool SEditor::canInsertFromMimeData( const QMimeData * source ) const
00905 {
00906     if (source->hasText() || source->hasFormat("application/x-scribus-styledtext"))
00907         return true;
00908     return false;
00909 }
00910 
00911 QMimeData* SEditor::createMimeDataFromSelection () const
00912 {
00913     StyledTextMimeData* mimeData = new StyledTextMimeData();
00914     int start = textCursor().selectionStart();
00915     int end   = textCursor().selectionEnd();
00916     if (start < 0 || end <= start)
00917         return mimeData;
00918     StoryText* that = const_cast<StoryText*> (&StyledText);
00919     that->select(start, end-start);
00920     mimeData->setText(textCursor().selectedText());
00921     mimeData->setStyledText(*that);
00922     return mimeData;
00923 }
00924 
00925 void SEditor::insertFromMimeData ( const QMimeData * source )
00926 {
00927     paste();
00928 }
00929 
00930 /*
00931 Q_3PopupMenu* SEditor::createPopupMenu(const QPoint & pos)
00932 {
00933     Q_3PopupMenu *p = Q_3TextEdit::createPopupMenu(pos);
00934     p->removeItemAt(0);
00935     p->removeItemAt(0);
00936     p->removeItemAt(0);
00937     p->removeItemAt(3);
00938     return p;
00939 }
00940 */
00941 void SEditor::SelClipChange()
00942 {
00943     emit PasteAvail();
00944 }
00945 
00946 void SEditor::ClipChange()
00947 {
00948     emit PasteAvail();
00949 }
00950 
00951 void SEditor::scrollContentsBy(int dx, int dy)
00952 {
00953     emit contentsMoving(dx, dy);
00954     QTextEdit::scrollContentsBy(dx, dy);
00955 }
00956 
00957 /* Toolbar for Fill Colour */
00958 SToolBColorF::SToolBColorF(QMainWindow* parent, ScribusDoc *doc) : QToolBar( tr("Fill Color Settings"), parent)
00959 {
00960     FillIcon = new QLabel(this);
00961     FillIcon->setPixmap(loadIcon("16/color-fill.png"));
00962     FillIcon->setScaledContents( false );
00963     fillIconAction=addWidget(FillIcon);
00964     fillIconAction->setVisible(true);
00965     TxFill = new ColorCombo(false, this);
00966     txFillAction=addWidget(TxFill);
00967     txFillAction->setVisible(true);
00968     PM2 = new ShadeButton(this);
00969     pm2Action=addWidget(PM2);
00970     pm2Action->setVisible(true);
00971     
00972     setCurrentDocument(doc);
00973     //TxFill->listBox()->setMinimumWidth(TxFill->listBox()->maxItemWidth()+24);
00974     connect(TxFill, SIGNAL(activated(int)), this, SLOT(newShadeHandler()));
00975     connect(PM2, SIGNAL(clicked()), this, SLOT(newShadeHandler()));
00976 
00977     languageChange();
00978 }
00979 
00980 void SToolBColorF::changeEvent(QEvent *e)
00981 {
00982     if (e->type() == QEvent::LanguageChange)
00983     {
00984         languageChange();
00985     }
00986     else
00987         QWidget::changeEvent(e);
00988 }
00989 
00990 
00991 void SToolBColorF::languageChange()
00992 {
00993     TxFill->setToolTip("");
00994     PM2->setToolTip("");
00995     TxFill->setToolTip( tr( "Color of text fill" ));
00996     PM2->setToolTip( tr( "Saturation of color of text fill" ));
00997 }
00998 
00999 void SToolBColorF::setCurrentDocument(ScribusDoc *doc)
01000 {
01001     if (doc!=NULL)
01002         TxFill->updateBox(doc->PageColors, ColorCombo::smallPixmaps, true);
01003     else
01004     {
01005         TxFill->clear();
01006         TxFill->addItem(CommonStrings::tr_NoneColor);
01007     }
01008 //  if (doc!=NULL)
01009 //      TxFill->insertItems(doc->PageColors, ColorCombo::smallPixmaps);
01010     resize(minimumSizeHint());
01011 }
01012 
01013 void SToolBColorF::SetColor(int c)
01014 {
01015     disconnect(TxFill, SIGNAL(activated(int)), this, SLOT(newShadeHandler()));
01016     TxFill->setCurrentIndex(c);
01017     connect(TxFill, SIGNAL(activated(int)), this, SLOT(newShadeHandler()));
01018 }
01019 
01020 void SToolBColorF::SetShade(double s)
01021 {
01022     disconnect(PM2, SIGNAL(clicked()), this, SLOT(newShadeHandler()));
01023     PM2->setValue(qRound(s));
01024     connect(PM2, SIGNAL(clicked()), this, SLOT(newShadeHandler()));
01025 }
01026 
01027 void SToolBColorF::newShadeHandler()
01028 {
01029     emit NewColor(TxFill->currentIndex(), PM2->getValue());
01030 }
01031 
01032 /* Toolbar for Stroke Colour */
01033 SToolBColorS::SToolBColorS(QMainWindow* parent, ScribusDoc *doc) : QToolBar( tr("Stroke Color Settings"), parent)
01034 {
01035     StrokeIcon = new QLabel( "", this );
01036     StrokeIcon->setPixmap(loadIcon("16/color-stroke.png"));
01037     StrokeIcon->setScaledContents( false );
01038     strokeIconAction=addWidget(StrokeIcon);
01039     strokeIconAction->setVisible(true);
01040     TxStroke = new ColorCombo(false, this);
01041     txStrokeAction=addWidget(TxStroke);
01042     txStrokeAction->setVisible(true);
01043     PM1 = new ShadeButton(this);
01044     pm1Action=addWidget(PM1);
01045     pm1Action->setVisible(true);
01046     setCurrentDocument(doc);
01047     //TxStroke->listBox()->setMinimumWidth(TxStroke->listBox()->maxItemWidth()+24);
01048     connect(TxStroke, SIGNAL(activated(int)), this, SLOT(newShadeHandler()));
01049     connect(PM1, SIGNAL(clicked()), this, SLOT(newShadeHandler()));
01050 
01051     languageChange();
01052 }
01053