lib

KoParagDia.cpp

00001 /* This file is part of the KDE project
00002    Copyright (C) 1998, 1999 Reginald Stadlbauer <reggie@kde.org>
00003    Copyright (C) 2005 Martin Ellis <martin.ellis@kdemail.net>
00004    Copyright (C) 2006 Thomas Zander <zander@kde.org>
00005 
00006    This library is free software; you can redistribute it and/or
00007    modify it under the terms of the GNU Library General Public
00008    License as published by the Free Software Foundation; either
00009    version 2 of the License, or (at your option) any later version.
00010 
00011    This library is distributed in the hope that it will be useful,
00012    but WITHOUT ANY WARRANTY; without even the implied warranty of
00013    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00014    Library General Public License for more details.
00015 
00016    You should have received a copy of the GNU Library General Public License
00017    along with this library; see the file COPYING.LIB.  If not, write to
00018    the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
00019  * Boston, MA 02110-1301, USA.
00020 */
00021 
00022 #include "KoParagDia.h"
00023 #include "KoParagDia_p.h"
00024 #include "KoDocument.h"
00025 #include "KoTextFormat.h"
00026 #include "KoTextParag.h"
00027 #include "KoTextDocument.h"
00028 #include "KoTextZoomHandler.h"
00029 #include "KoParagDecorationTab.h"
00030 
00031 #include <KoCharSelectDia.h>
00032 #include <KoUnitWidgets.h>
00033 #include <kcolorbutton.h>
00034 #include <kdebug.h>
00035 #include <kiconloader.h>
00036 #include <klocale.h>
00037 #include <knumvalidator.h>
00038 #include <KoGlobal.h>
00039 #include <qgroupbox.h>
00040 #include <knuminput.h>
00041 #include <kdeversion.h>
00042 #include <kpushbutton.h>
00043 #include <kcombobox.h>
00044 
00045 #include <qcheckbox.h>
00046 #include <qcombobox.h>
00047 #include <qhbuttongroup.h>
00048 #include <qlabel.h>
00049 #include <qradiobutton.h>
00050 #include <qvbox.h>
00051 #include <qhbox.h>
00052 #include <qtooltip.h>
00053 #include <qlayout.h>
00054 #include <qapplication.h>
00055 #include <qwidgetstack.h>
00056 
00057 KoCounterStyleWidget::KoCounterStyleWidget( bool displayDepth, bool onlyStyleTypeLetter, bool disableAll, QWidget * parent, const char* name  )
00058     :QWidget( parent, name ),
00059     stylesList()
00060 {
00061     noSignals = true;
00062     styleBuffer = 999;
00063     QVBoxLayout *vbox = new QVBoxLayout( this,0, 0/*KDialog::marginHint(), KDialog::spacingHint()*/ );
00064     gStyle = new QGroupBox( i18n( "St&yle" ), this, "styleLayout" );
00065     vbox->addWidget( gStyle);
00066     QGridLayout * grid = new QGridLayout(gStyle, 12, 5, KDialog::marginHint(), KDialog::spacingHint());
00067     grid->addRowSpacing(0, fontMetrics().height()/2);
00068 
00069     makeCounterRepresenterList( stylesList, onlyStyleTypeLetter );
00070 
00071     lstStyle = new QListBox( gStyle, "styleListBox" );
00072     grid->addMultiCellWidget( lstStyle, 1, 11, 0, 0);
00073     fillStyleCombo();
00074     connect( lstStyle, SIGNAL( selectionChanged() ), this, SLOT( numStyleChanged() ) );
00075 
00076 
00077     QLabel *lPrefix = new QLabel( gStyle, "lPrefix" );
00078     lPrefix->setText( i18n( "Pre&fix text:" ) );
00079     grid->addWidget( lPrefix, 1, 1);
00080 
00081     sPrefix = new QLineEdit( gStyle, "sPrefix" );
00082     lPrefix->setBuddy( sPrefix );
00083     grid->addWidget( sPrefix, 1, 2);
00084 
00085     QLabel *lSuffix = new QLabel( gStyle, "lSuffix" );
00086     lSuffix->setText( i18n( "Suffi&x text:" ) );
00087     grid->addWidget( lSuffix, 1, 3);
00088 
00089     sSuffix = new QLineEdit( gStyle, "sSuffix" );
00090     lSuffix->setBuddy( sSuffix );
00091     grid->addWidget( sSuffix, 1, 4 );
00092 
00093     lStart = new QLabel( gStyle, "lStart" );
00094     lStart->setText( i18n( "&Start at:" ) );
00095     grid->addWidget( lStart, 2, 1 );
00096 
00097 
00098     spnDepth = new QSpinBox( 0, 15, 1, gStyle );
00099     if (  displayDepth )
00100         grid->addWidget( spnDepth, 3, 2 );
00101     else
00102         spnDepth->hide();
00103 
00104     spnDisplayLevels = new QSpinBox( 0, 15, 1, gStyle );
00105     spnDisplayLevels->setMinValue( 1 );
00106     if ( displayDepth )
00107         grid->addWidget( spnDisplayLevels, 3, 4 );
00108     else
00109         spnDisplayLevels->hide();
00110 
00111 
00112     QHBoxLayout *customCharBox = new QHBoxLayout(0, 0, 6);
00113     lCustom = new QLabel( i18n( "Custo&m character:" ), gStyle, "custom char label" );
00114     customCharBox->addWidget( lCustom );
00115 
00116     bCustom = new QPushButton( "", gStyle, "bCustom" );
00117     lCustom->setBuddy( bCustom );
00118     customCharBox->addWidget( bCustom );
00119     connect( bCustom, SIGNAL( clicked() ), this, SLOT( selectCustomBullet() ) );
00120 
00121     QSpacerItem* spacer_2 = new QSpacerItem( 0, 0, QSizePolicy::Expanding, QSizePolicy::Minimum );
00122     customCharBox->addItem( spacer_2 );
00123 
00124     grid->addMultiCellLayout(customCharBox, 4, 4, 1, 4, Qt::AlignLeft);
00125 
00126     spnStart = new KoSpinBox( gStyle );
00127     spnStart->setMinValue ( 1);
00128     lStart->setBuddy( spnStart );
00129     grid->addWidget( spnStart, 2, 2);
00130 
00131     lAlignment = new QLabel( gStyle, "lAlignment" );
00132     lAlignment->setText( i18n( "Counter alignment:" ) );
00133     grid->addWidget( lAlignment, 2, 3 );
00134 
00135     cbAlignment = new KComboBox( gStyle, "cbAlignment" );
00136     cbAlignment->insertItem(i18n("Align Auto"));
00137     cbAlignment->insertItem(i18n("Align Left"));
00138     cbAlignment->insertItem(i18n("Align Right"));
00139     cbAlignment->setCurrentItem(0);
00140     grid->addWidget( cbAlignment, 2, 4 );
00141 
00142     QLabel *lDepth = new QLabel( gStyle, "lDepth" );
00143     lDepth->setText( i18n( "&Depth:" ) );
00144     lDepth->setBuddy( spnDepth );
00145     if ( displayDepth )
00146         grid->addWidget( lDepth, 3, 1 );
00147     else
00148         lDepth->hide();
00149 
00150     QLabel *lDisplayLevels = new QLabel( gStyle );
00151     lDisplayLevels->setText( i18n( "Display le&vels:" ) );
00152     lDisplayLevels->setBuddy( spnDisplayLevels );
00153     if ( displayDepth )
00154         grid->addWidget( lDisplayLevels, 3, 3 );
00155     else
00156         lDisplayLevels->hide();
00157 
00158     cbRestart = new QCheckBox( i18n( "&Restart numbering at this paragraph" ), gStyle );
00159     grid->addMultiCellWidget( cbRestart, 5, 5, 1, 3 );
00160 
00161     if ( onlyStyleTypeLetter )
00162     {
00163         lCustom->hide();
00164         bCustom->hide();
00165         cbRestart->hide();
00166     }
00167 
00168 
00169     connect( cbRestart, SIGNAL( toggled(bool) ), this, SLOT( restartChanged(bool) ) );
00170 
00171     connect( sSuffix, SIGNAL( textChanged (const QString &) ), this, SLOT( suffixChanged(const QString &) ) );
00172     connect( sPrefix, SIGNAL( textChanged (const QString &) ), this, SLOT( prefixChanged(const QString &) ) );
00173     connect( spnStart, SIGNAL( valueChanged (int) ), this, SLOT( startChanged(int) ) );
00174     connect( spnDepth, SIGNAL( valueChanged (int) ), this, SLOT( depthChanged(int) ) );
00175     connect( spnDisplayLevels, SIGNAL( valueChanged (int) ), this, SLOT( displayLevelsChanged(int) ) );
00176     connect( cbAlignment, SIGNAL( activated (const QString&) ), this, SLOT( alignmentChanged(const QString&) ) );
00177     noSignals = false;
00178     if ( disableAll )
00179     {
00180         gStyle->setEnabled( false );
00181         lstStyle->setEnabled( false );
00182         sSuffix->setEnabled( false );
00183         sPrefix->setEnabled( false );
00184         bCustom->setEnabled( false );
00185         spnStart->setEnabled( false );
00186         spnDepth->setEnabled( false );
00187         spnDisplayLevels->setEnabled( false );
00188         lStart->setEnabled( false );
00189         lCustom->setEnabled( false );
00190         cbRestart->setEnabled( false );
00191         cbAlignment->setEnabled( false );
00192     }
00193 }
00194 
00195 void KoCounterStyleWidget::alignmentChanged(const QString& s)
00196 {
00197     int a;
00198     if(s==i18n("Align Left"))
00199         a=Qt::AlignLeft;
00200     else if(s==i18n("Align Right"))
00201         a=Qt::AlignRight;
00202     else if(s==i18n("Align Auto"))
00203         a=Qt::AlignAuto;
00204     else {
00205         kdError()<<"Not Implemented"<<endl;
00206         return;
00207     }
00208     m_counter.setAlignment(a);
00209     emit sig_alignmentChanged(a);
00210 }
00211 
00212 void KoCounterStyleWidget::setCounter( const KoParagCounter& counter )
00213 {
00214     noSignals = true;
00215     KoParagCounter::Style st = counter.style();
00216     m_counter = counter;
00217     // Huh? doesn't the line above do this already?
00218     //m_counter.setStyle( st );
00219     changeKWSpinboxType( st);
00220     displayStyle( st );
00221     noSignals = false;
00222 }
00223 
00224 void KoCounterStyleWidget::changeKWSpinboxType(KoParagCounter::Style st) {
00225     switch(st)
00226     {
00227         case KoParagCounter::STYLE_NONE:
00228             spnStart->setCounterType(KoSpinBox::NONE);
00229             break;
00230         case KoParagCounter::STYLE_NUM:
00231             spnStart->setCounterType(KoSpinBox::NUM);
00232             break;
00233         case KoParagCounter::STYLE_ALPHAB_L:
00234             spnStart->setCounterType(KoSpinBox::ALPHAB_L);
00235             break;
00236         case KoParagCounter::STYLE_ALPHAB_U:
00237             spnStart->setCounterType(KoSpinBox::ALPHAB_U);
00238             break;
00239         case KoParagCounter::STYLE_ROM_NUM_L:
00240             spnStart->setCounterType(KoSpinBox::ROM_NUM_L);
00241             break;
00242         case KoParagCounter::STYLE_ROM_NUM_U:
00243             spnStart->setCounterType(KoSpinBox::ROM_NUM_U);
00244             break;
00245         default:
00246             spnStart->setCounterType(KoSpinBox::NONE);
00247     }
00248 }
00249 
00250 
00251 void KoCounterStyleWidget::fillStyleCombo(KoParagCounter::Numbering type) {
00252     if(lstStyle==NULL) return;
00253     noSignals=true;
00254     unsigned int cur = lstStyle->currentItem();
00255     lstStyle->clear();
00256     QPtrListIterator<StyleRepresenter> style( stylesList );
00257     while ( style.current() ) {
00258         if(style.current()->style() == KoParagCounter::STYLE_NONE) {
00259             if(type == KoParagCounter::NUM_NONE)
00260                 lstStyle->insertItem( style.current()->name() );
00261         }
00262         else if(type == KoParagCounter::NUM_LIST || !style.current()->isBullet())
00263             if(type != KoParagCounter::NUM_NONE)
00264                 lstStyle->insertItem( style.current()->name() );
00265         ++style;
00266     }
00267 
00268     if(styleBuffer <= lstStyle->count())
00269         lstStyle->setCurrentItem(styleBuffer);
00270     else
00271         if(cur <= lstStyle->count())
00272             lstStyle->setCurrentItem(cur);
00273 
00274     if(cur > lstStyle->count()) {
00275         styleBuffer = cur;
00276     }
00277     noSignals=false;
00278 }
00279 
00280 void KoCounterStyleWidget::displayStyle( KoParagCounter::Style style )
00281 {
00282     unsigned int i = 0;
00283     while ( stylesList.count() > i && stylesList.at(i)->style() != style )
00284         ++i;
00285     lstStyle->setCurrentItem(i);
00286 
00287     bCustom->setText( m_counter.customBulletCharacter() );
00288     if ( !m_counter.customBulletFont().isEmpty() )
00289         bCustom->setFont( QFont( m_counter.customBulletFont() ) );
00290 
00291     sPrefix->setText( m_counter.prefix() );
00292     sSuffix->setText( m_counter.suffix() );
00293 
00294     spnDepth->setValue( m_counter.depth() );
00295     spnDisplayLevels->setValue( m_counter.displayLevels() );
00296     spnStart->setValue( m_counter.startNumber() );
00297 
00298     cbRestart->setChecked( m_counter.restartCounter() );
00299     if(m_counter.alignment()==Qt::AlignLeft)
00300         cbAlignment->setCurrentText(i18n("Align Left"));
00301     else if(m_counter.alignment()==Qt::AlignRight)
00302         cbAlignment->setCurrentText(i18n("Align Right"));
00303     else if(m_counter.alignment()==Qt::AlignAuto)
00304         cbAlignment->setCurrentText(i18n("Align Auto"));
00305     else
00306         kdError()<<"Not Implemented"<<endl;
00307 }
00308 
00309 void KoCounterStyleWidget::display( const KoParagLayout & lay ) {
00310     KoParagCounter::Style style = KoParagCounter::STYLE_NONE;
00311     if ( lay.counter )
00312     {
00313         style=lay.counter->style();
00314         m_counter = *lay.counter;
00315     }
00316     else
00317     {
00318         m_counter = KoParagCounter();
00319     }
00320     styleBuffer = 999;
00321 
00322     numTypeChanged( m_counter.numbering() );
00323     emit sig_numTypeChanged( m_counter.numbering() );
00324 
00325     displayStyle( style );
00326 }
00327 
00328 
00329 void KoCounterStyleWidget::numTypeChanged( int nType ) {
00330     m_counter.setNumbering( static_cast<KoParagCounter::Numbering>( nType ) );
00331     gStyle->setEnabled( m_counter.numbering() != KoParagCounter::NUM_NONE );
00332     fillStyleCombo(m_counter.numbering());
00333     bool state=m_counter.numbering()==KoParagCounter::NUM_LIST;
00334     bCustom->setEnabled(state);
00335     lCustom->setEnabled(state);
00336 }
00337 
00338 
00339 void KoCounterStyleWidget::makeCounterRepresenterList( QPtrList<StyleRepresenter>& stylesList, bool onlyStyleTypeLetter )
00340 {
00341     stylesList.setAutoDelete( true );
00342     stylesList.append( new StyleRepresenter(i18n( "Arabic Numbers" )
00343             ,  KoParagCounter::STYLE_NUM));
00344     stylesList.append( new StyleRepresenter(i18n( "Lower Alphabetical" )
00345             ,  KoParagCounter::STYLE_ALPHAB_L ));
00346     stylesList.append( new StyleRepresenter(i18n( "Upper Alphabetical" )
00347             ,  KoParagCounter::STYLE_ALPHAB_U ));
00348     stylesList.append( new StyleRepresenter(i18n( "Lower Roman Numbers" )
00349             ,  KoParagCounter::STYLE_ROM_NUM_L ));
00350     stylesList.append( new StyleRepresenter(i18n( "Upper Roman Numbers" )
00351             ,  KoParagCounter::STYLE_ROM_NUM_U ));
00352     if ( !onlyStyleTypeLetter )
00353     {
00354         stylesList.append( new StyleRepresenter(i18n( "Disc Bullet" )
00355                                                 ,  KoParagCounter::STYLE_DISCBULLET , true));
00356         stylesList.append( new StyleRepresenter(i18n( "Square Bullet" )
00357                                                 ,  KoParagCounter::STYLE_SQUAREBULLET , true));
00358         stylesList.append( new StyleRepresenter(i18n( "Box Bullet" )
00359                                                 ,  KoParagCounter::STYLE_BOXBULLET , true));
00360         stylesList.append( new StyleRepresenter(i18n( "Circle Bullet" )
00361                                                 ,  KoParagCounter::STYLE_CIRCLEBULLET , true));
00362         stylesList.append( new StyleRepresenter(i18n( "Custom Bullet" )
00363                                                 ,  KoParagCounter::STYLE_CUSTOMBULLET , true));
00364     }
00365     stylesList.append( new StyleRepresenter(i18n( "None" ), KoParagCounter::STYLE_NONE));
00366 }
00367 
00368 
00369 void KoCounterStyleWidget::selectCustomBullet() {
00370     unsigned int i = 0;
00371     while ( stylesList.count() > i && stylesList.at(i)->style() != KoParagCounter::STYLE_CUSTOMBULLET )
00372         ++i;
00373     lstStyle->setCurrentItem(i);
00374 
00375     QString f = m_counter.customBulletFont();
00376     if ( f.isEmpty() )
00377         f = "symbol";
00378     QChar c = m_counter.customBulletCharacter();
00379 
00380     if ( KoCharSelectDia::selectChar( f, c ) ) {
00381         emit changeCustomBullet( f, c );
00382         m_counter.setCustomBulletFont( f );
00383         m_counter.setCustomBulletCharacter( c );
00384         if ( !f.isEmpty() )
00385             bCustom->setFont( QFont( f ) );
00386         bCustom->setText( c );
00387     }
00388 }
00389 
00390 void KoCounterStyleWidget::numStyleChanged() {
00391     if ( noSignals )
00392         return;
00393     // We selected another style from the list box.
00394     styleBuffer = 999;
00395     StyleRepresenter *sr = stylesList.at(lstStyle->currentItem());
00396     emit changeStyle( sr->style() );
00397     m_counter.setStyle( sr->style() );
00398     bool isNumbered = !sr->isBullet() && !sr->style() == KoParagCounter::STYLE_NONE;
00399     lStart->setEnabled( isNumbered );
00400     spnStart->setEnabled( isNumbered );
00401     cbRestart->setEnabled( isNumbered );
00402     spnDisplayLevels->setEnabled( isNumbered );
00403     changeKWSpinboxType(sr->style() );
00404 }
00405 
00406 
00407 
00408 KoSpinBox::KoSpinBox( QWidget * parent, const char * name )
00409     : QSpinBox(parent,name)
00410 {
00411     m_Etype=NONE;
00412     //max value supported by roman number
00413     setMaxValue ( 3999 );
00414 }
00415 KoSpinBox::~KoSpinBox( )
00416 {
00417 }
00418 
00419 KoSpinBox::KoSpinBox( int minValue, int maxValue, int step ,
00420            QWidget * parent , const char * name  )
00421     : QSpinBox(minValue, maxValue,step ,
00422            parent , name)
00423 {
00424     m_Etype=NONE;
00425 }
00426 
00427 void KoSpinBox::setCounterType(counterType _type)
00428 {
00429     m_Etype=_type;
00430     editor()->setText(mapValueToText(value()));
00431 }
00432 
00433 
00434 QString KoSpinBox::mapValueToText( int value )
00435 {
00436     if(value==0 && m_Etype==NUM)
00437         return QString("0");
00438     else if(value==0 && m_Etype!=NUM)
00439         return QString::null;
00440     switch(m_Etype)
00441     {
00442         case NUM:
00443             return QString::number(value);
00444         case ALPHAB_L:
00445             return KoParagCounter::makeAlphaLowerNumber( value );
00446         case ALPHAB_U:
00447             return KoParagCounter::makeAlphaUpperNumber( value );
00448         case ROM_NUM_L:
00449             return KoParagCounter::makeRomanNumber( value );
00450         case ROM_NUM_U:
00451             return KoParagCounter::makeRomanNumber( value ).upper();
00452         case NONE:
00453         default:
00454             return QString::null;
00455     }
00456     //never here
00457     return QString::null;
00458 }
00459 
00460 int KoSpinBox::mapTextToValue( bool * ok )
00461 {
00462     int ret;
00463     QString txt = text();
00464 
00465     *ok = TRUE;
00466     switch(m_Etype)
00467     {
00468         case NUM:
00469             ret = txt.toInt ( ok );
00470             break;
00471         case ALPHAB_L:
00472             ret = KoParagCounter::fromAlphaLowerNumber( txt.lower() );
00473             break;
00474         case ALPHAB_U:
00475             ret = KoParagCounter::fromAlphaUpperNumber( txt.upper() );
00476             break;
00477         case ROM_NUM_L:
00478             ret = KoParagCounter::fromRomanNumber( txt.lower() );
00479             break;
00480         case ROM_NUM_U:
00481             ret = KoParagCounter::fromRomanNumber( txt.lower() ); // _not_ upper()
00482             break;
00483         case NONE:
00484         default:
00485             ret = -1;
00486             break;
00487     }
00488 
00489     if (ret == -1)
00490         *ok = FALSE;
00491 
00492     return ret;
00493 }
00494 
00495 
00496 /******************************************************************/
00497 /* class KPagePreview                                            */
00498 /******************************************************************/
00499 
00500 KPagePreview::KPagePreview( QWidget* parent, const char* name )
00501     : QGroupBox( i18n( "Preview" ), parent, name )
00502 {
00503     left = 0;
00504     right = 0;
00505     first = 0;
00506     spacing = 0;
00507     before = 0;
00508     after = 0;
00509 }
00510 
00511 void KPagePreview::drawContents( QPainter* p )
00512 {
00513     int wid = 148;
00514     int hei = 210;
00515     int _x = ( width() - wid ) / 5;
00516     int _y = ( height() - hei ) / 5;
00517 
00518     int dl = convert(left);
00519     int dr = convert(right);
00520 
00521     //first+left because firstlineIndent is relative to leftIndent
00522     int df = convert(first + left);
00523 
00524     int spc = convert(spacing);
00525 
00526     // draw page
00527     p->setPen( QPen( black ) );
00528     p->setBrush( QBrush( black ) );
00529 
00530     p->drawRect( _x + 1, _y + 1, wid, hei );
00531 
00532     p->setBrush( QBrush( white ) );
00533     p->drawRect( _x, _y, wid, hei );
00534 
00535     // draw parags
00536     p->setPen( NoPen );
00537     p->setBrush( QBrush( lightGray ) );
00538 
00539     for ( int i = 1; i <= 4; i++ )
00540         p->drawRect( _x + 6, _y + 6 + ( i - 1 ) * 12 + 2, wid - 12 - ( ( i / 4 ) * 4 == i ? 50 : 0 ), 6 );
00541 
00542     p->setBrush( QBrush( darkGray ) );
00543 
00544     for ( int i = 5; i <= 8; i++ )
00545       {
00546     QRect rect( ( i == 5 ? df : dl ) + _x + 6, _y + 6 + ( i - 1 ) * 12 + 2 + ( i - 5 ) * spc + static_cast<int>( before / 2 ),
00547             wid - 12 - ( ( i / 4 ) * 4 == i ? 50 : 0 ) - ( ( i == 12 ? 0 : dr ) + ( i == 5 ? df : dl ) ), 6);
00548 
00549     if(rect.width ()>=0)
00550       p->drawRect( rect );
00551       }
00552     p->setBrush( QBrush( lightGray ) );
00553 
00554     for ( int i = 9; i <= 12; i++ )
00555         p->drawRect( _x + 6, _y + 6 + ( i - 1 ) * 12 + 2 + 3 * spc +
00556                      static_cast<int>( before / 2 ) + static_cast<int>( after / 2 ),
00557                      wid - 12 - ( ( i / 4 ) * 4 == i ? 50 : 0 ), 6 );
00558 
00559 }
00560 
00561 int KPagePreview::convert(double input) {
00562     if(input < 1) return 0;
00563     if(input <= 5) return 3;
00564     if(input <= 10) return 4 + static_cast<int>( (input-5) / 2.5 );
00565     if(input <= 20) return 6 + static_cast<int>( (input-10) / 4 );
00566     if(input <= 100) return 10 + static_cast<int>( (input-20) / 8 );
00567     return static_cast<int>( input / 5);
00568 }
00569 
00570 /******************************************************************/
00571 /* class KPagePreview2                                           */
00572 /******************************************************************/
00573 
00574 KPagePreview2::KPagePreview2( QWidget* parent, const char* name )
00575     : QGroupBox( i18n( "Preview" ), parent, name )
00576 {
00577     align = Qt::AlignLeft;
00578 }
00579 
00580 void KPagePreview2::drawContents( QPainter* p )
00581 {
00582     int wid = 148;
00583     int hei = 210;
00584     int _x = ( width() - wid ) / 2;
00585     int _y = ( height() - hei ) / 2;
00586 
00587     // draw page
00588     p->setPen( QPen( black ) );
00589     p->setBrush( QBrush( black ) );
00590 
00591     p->drawRect( _x + 1, _y + 1, wid, hei );
00592 
00593     p->setBrush( QBrush( white ) );
00594     p->drawRect( _x, _y, wid, hei );
00595 
00596     // draw parags
00597     p->setPen( NoPen );
00598     p->setBrush( QBrush( lightGray ) );
00599 
00600     for ( int i = 1; i <= 4; i++ )
00601         p->drawRect( _x + 6, _y + 6 + ( i - 1 ) * 12 + 2, wid - 12 - ( ( i / 4 ) * 4 == i ? 50 : 0 ), 6 );
00602 
00603     p->setBrush( QBrush( darkGray ) );
00604 
00605     int __x = 0, __w = 0;
00606     for ( int i = 5; i <= 8; i++ ) {
00607         switch ( i ) {
00608         case 5: __w = wid - 12;
00609             break;
00610         case 6: __w = wid - 52;
00611             break;
00612         case 7: __w = wid - 33;
00613             break;
00614         case 8: __w = wid - 62;
00615         default: break;
00616         }
00617 
00618         switch ( align ) {
00619             case Qt::AlignAuto:
00620             case Qt::AlignLeft:
00621                 __x = _x + 6;
00622                 break;
00623             case Qt::AlignHCenter:
00624                 __x = _x + ( wid - __w ) / 2;
00625                 break;
00626             case Qt::AlignRight:
00627                 __x = _x + ( wid - __w ) - 6;
00628                 break;
00629             case Qt::AlignJustify:
00630             {
00631                 if ( i < 8 ) __w = wid - 12;
00632                 __x = _x + 6;
00633             } break;
00634         }
00635 
00636         p->drawRect( __x, _y + 6 + ( i - 1 ) * 12 + 2 + ( i - 5 ), __w, 6 );
00637     }
00638 
00639     p->setBrush( QBrush( lightGray ) );
00640 
00641     for ( int i = 9; i <= 12; i++ )
00642         p->drawRect( _x + 6, _y + 6 + ( i - 1 ) * 12 + 2 + 3, wid - 12 - ( ( i / 4 ) * 4 == i ? 50 : 0 ), 6 );
00643 
00644 }
00645 
00646 /******************************************************************/
00647 /* class KoBorderPreview                                          */
00648 /******************************************************************/
00649 
00650 
00651 KoBorderPreview::KoBorderPreview( QWidget* parent, const char* name )
00652     :QFrame(parent,name)
00653 {
00654 }
00655 
00656 void KoBorderPreview::mousePressEvent( QMouseEvent *_ev )
00657 {
00658     emit choosearea(_ev);
00659 }
00660 
00661 void KoBorderPreview::setBorder( KoBorder::BorderType which, const KoBorder& border)
00662 {
00663     switch( which ) {
00664     case KoBorder::TopBorder:
00665         setTopBorder( border );
00666         break;
00667     case KoBorder::BottomBorder:
00668         setBottomBorder( border );
00669         break;
00670     case KoBorder::LeftBorder:
00671         setLeftBorder( border );
00672         break;
00673     case KoBorder::RightBorder:
00674         setRightBorder( border );
00675         break;
00676     default:
00677         kdError() << "KoBorderPreview: unknown border type" << endl;
00678     }
00679 }
00680 
00681 void KoBorderPreview::drawContents( QPainter* painter )
00682 {
00683     QRect r = contentsRect();
00684     QFontMetrics fm( font() );
00685 
00686     painter->fillRect( r.x() + fm.width( 'W' ), r.y() + fm.height(), r.width() - 2 * fm.width( 'W' ),
00687                        r.height() - 2 * fm.height(), white );
00688     painter->setClipRect( r.x() + fm.width( 'W' ), r.y() + fm.height(), r.width() - 2 * fm.width( 'W' ),
00689                           r.height() - 2 * fm.height() );
00690 
00691     bool leftdouble = m_leftBorder.width() > 0 && m_leftBorder.getStyle() == KoBorder::DOUBLE_LINE;
00692     bool rightdouble = m_rightBorder.width() > 0 && m_rightBorder.getStyle() == KoBorder::DOUBLE_LINE;
00693     bool topdouble = m_topBorder.width() > 0 && m_topBorder.getStyle() == KoBorder::DOUBLE_LINE;
00694     bool bottomdouble = m_bottomBorder.width() > 0 && m_bottomBorder.getStyle() == KoBorder::DOUBLE_LINE;
00695 
00696     if ( m_topBorder.width() > 0 ) {
00697         painter->setPen( setBorderPen( m_topBorder ) );
00698         painter->drawLine( r.x() + 20, r.y() + 30, r.right() - 19, r.y() + 30 );
00699         if ( m_topBorder.getStyle()==KoBorder::DOUBLE_LINE)
00700             painter->drawLine( int(r.x() + 20 + ( leftdouble ? m_leftBorder.width() + 1 : 0) ),
00701                                int(r.y() + 30 + m_topBorder.width()+1),
00702                                int(r.right() - 19 - ( rightdouble ? m_rightBorder.width() + 1 : 0) ),
00703                                int(r.y() + 30 + m_topBorder.width()+1)
00704                              );
00705     }
00706 
00707     if ( m_bottomBorder.width() > 0 ) {
00708         painter->setPen( setBorderPen( m_bottomBorder ) );
00709         painter->drawLine( r.x() + 20, r.bottom() - 30, r.right() - 19, r.bottom() - 30 );
00710         if ( m_bottomBorder.getStyle()==KoBorder::DOUBLE_LINE)
00711             painter->drawLine( int(r.x() + 20 + ( leftdouble ? m_leftBorder.width() + 1 : 0) ),
00712                                int(r.bottom() - 30 - m_bottomBorder.width()-1),
00713                                int(r.right() - 19 - ( rightdouble ? m_rightBorder.width() + 1 : 0) ),
00714                                int(r.bottom() - 30 - m_bottomBorder.width() - 1)
00715                              );
00716     }
00717 
00718     if ( m_leftBorder.width() > 0 ) {
00719         painter->setPen( setBorderPen( m_leftBorder ) );
00720         painter->drawLine( r.x() + 20, r.y() + 30, r.x() + 20, r.bottom() - 29 );
00721         if ( m_leftBorder.getStyle()==KoBorder::DOUBLE_LINE)
00722             painter->drawLine( int(r.x() + 20 + m_leftBorder.width() +1),
00723                                int(r.y() + 30 + ( topdouble ? m_topBorder.width() + 1 : 0) ),
00724                                int(r.x() + 20 + m_leftBorder.width() +1),
00725                                int(r.bottom() - 29 - ( bottomdouble ? m_bottomBorder.width() + 1 : 0) )
00726                              );
00727     }
00728 
00729     if ( m_rightBorder.width() > 0 ) {
00730         painter->setPen( setBorderPen( m_rightBorder ) );
00731         painter->drawLine( r.right() - 20, r.y() + 30, r.right() - 20, r.bottom() - 29 );
00732         if ( m_rightBorder.getStyle()==KoBorder::DOUBLE_LINE)
00733             painter->drawLine( int(r.right() - 20 - m_rightBorder.width() - 1 ),
00734                                int(r.y() + 30 + ( topdouble ? m_topBorder.width() + 1 : 0) ),
00735                                int(r.right() - 20 - m_rightBorder.width() - 1),
00736                                int(r.bottom() - 29 - ( bottomdouble ? m_bottomBorder.width() + 1 : 0) )
00737                              );
00738     }
00739 }
00740 
00741 QPen KoBorderPreview::setBorderPen( KoBorder _brd )
00742 {
00743     QPen pen( black, 1, SolidLine );
00744 
00745     pen.setWidth( static_cast<int>( _brd.penWidth() ) );
00746     pen.setColor( _brd.color );
00747 
00748     switch ( _brd.getStyle() ) {
00749     case KoBorder::SOLID:
00750         pen.setStyle( SolidLine );
00751         break;
00752     case KoBorder::DASH:
00753         pen.setStyle( DashLine );
00754         break;
00755     case KoBorder::DOT:
00756         pen.setStyle( DotLine );
00757         break;
00758     case KoBorder::DASH_DOT:
00759         pen.setStyle( DashDotLine );
00760         break;
00761     case KoBorder::DASH_DOT_DOT:
00762         pen.setStyle( DashDotDotLine );
00763         break;
00764     case KoBorder::DOUBLE_LINE:
00765         pen.setStyle( SolidLine );
00766         break;
00767     }
00768 
00769     return QPen( pen );
00770 }
00771 
00772 /******************************************************************/
00773 /* Class: KoStylePreview. Previewing text with style ;)           */
00774 /******************************************************************/
00775 class MyFlow : public KoTextFlow {
00776     public:
00777         MyFlow(QWidget *parent, KoTextZoomHandler *zoom) {
00778             m_parent = parent;
00779             m_zoomHandler = zoom;
00780         }
00781         int availableHeight() const {
00782             return m_zoomHandler->pixelToLayoutUnitY(m_parent->height());
00783         }
00784     private:
00785         QWidget *m_parent;
00786         KoTextZoomHandler *m_zoomHandler;
00787 };
00788 
00789 KoStylePreview::KoStylePreview( const QString& title, const QString& text, QWidget* parent, const char* name )
00790     : QGroupBox( title, parent, name )
00791 {
00792     setMinimumHeight(80);
00793     m_zoomHandler = new KoTextZoomHandler;
00794     QFont font = KoGlobal::defaultFont();
00795     m_textdoc = new KoTextDocument( m_zoomHandler, new KoTextFormatCollection( font, QColor(), KGlobal::locale()->language(), false ) );
00796 
00797     m_textdoc->setFlow( new MyFlow(this, m_zoomHandler) );
00798     //m_textdoc->setWidth( KoTextZoomHandler::ptToLayoutUnitPt( 1000 ) );
00799     KoTextParag * parag = m_textdoc->firstParag();
00800     parag->insert( 0, text );
00801 }
00802 
00803 KoStylePreview::~KoStylePreview()
00804 {
00805     delete m_textdoc;
00806     delete m_zoomHandler;
00807 }
00808 
00809 void KoStylePreview::setCounter( const KoParagCounter & counter )
00810 {
00811     KoTextParag * parag = m_textdoc->firstParag();
00812     parag->setCounter( counter );
00813     repaint( true );
00814 }
00815 
00816 void KoStylePreview::setStyle( KoParagStyle * style )
00817 {
00818     KoTextParag * parag = m_textdoc->firstParag();
00819     parag->applyStyle( style );
00820     repaint(true);
00821 }
00822 
00823 void KoStylePreview::drawContents( QPainter *painter )
00824 {
00825     painter->save();
00826     QRect r = contentsRect();
00827     //kdDebug(32500) << "KoStylePreview::drawContents contentsRect=" << DEBUGRECT(r) << endl;
00828 
00829     QRect whiteRect( r.x() + 10, r.y() + 10,
00830                      r.width() - 20, r.height() - 20 );
00831     QColorGroup cg = QApplication::palette().active();
00832     painter->fillRect( whiteRect, cg.brush( QColorGroup::Base ) );
00833 
00834     KoTextParag * parag = m_textdoc->firstParag();
00835     int widthLU = m_zoomHandler->pixelToLayoutUnitX( whiteRect.width() - 2 ); // keep one pixel border horizontally
00836     if ( m_textdoc->width() != widthLU )
00837     {
00838         // For centering to work, and to even get word wrapping when the thing is too big :)
00839         m_textdoc->setWidth( widthLU );
00840         parag->invalidate(0);
00841     }
00842 
00843     parag->format();
00844     QRect textRect = parag->pixelRect( m_zoomHandler );
00845 
00846     // Center vertically, but not horizontally, to keep the parag alignment working,
00847     textRect.moveTopLeft( QPoint( whiteRect.x(),
00848                                   whiteRect.y() + ( whiteRect.height() - textRect.height() ) / 2 ) );
00849     // Move it from the left border a little
00850     textRect.rLeft() += 4;
00851     textRect.rRight() += 4;
00852     //kdDebug(32500) << "KoStylePreview::drawContents textRect=" << DEBUGRECT(textRect)
00853     //          << " textSize=" << textSize.width() << "," << textSize.height() << endl;
00854     painter->setClipRect( textRect.intersect( whiteRect ) );
00855     painter->translate( textRect.x(), textRect.y() );
00856 
00857     m_textdoc->drawWYSIWYG( painter, 0, 0, textRect.width(), textRect.height(), cg, m_zoomHandler );
00858     painter->restore();
00859 }
00860 
00861 KoIndentSpacingWidget::KoIndentSpacingWidget( KoUnit::Unit unit,  double _frameWidth,QWidget * parent, const char * name )
00862         : KoParagLayoutWidget( KoParagDia::PD_SPACING, parent, name ), m_unit( unit )
00863 {
00864     QString unitName = KoUnit::unitName( m_unit );
00865     QGridLayout *mainGrid = new QGridLayout( this, 3, 2, KDialog::marginHint(), KDialog::spacingHint() );
00866 
00867     // mainGrid gives equal space to each groupbox, apparently
00868     // I tried setRowStretch but the result is awful (much space between them and not equal!)
00869     // Any other way (in order to make the 2nd, the one with a single checkbox, a bit
00870     // smaller than the other 3) ? (DF)
00871 
00872 
00873     // --------------- indent ---------------
00874     double frameWidth=_frameWidth;
00875     QString length;
00876     if(frameWidth==-1) {
00877         frameWidth=9999;
00878     } else {
00879         length=i18n("Frame width: %1 %2")
00880         .arg(KoUnit::toUserStringValue(frameWidth,m_unit))
00881         .arg(KoUnit::unitName(m_unit));
00882         frameWidth=KoUnit::toUserValue(frameWidth,m_unit);
00883     }
00884 
00885     QGroupBox * indentFrame = new QGroupBox( i18n( "Indent" ), this );
00886     QGridLayout * indentGrid = new QGridLayout( indentFrame, 5, 2, KDialog::marginHint(), KDialog::spacingHint() );
00887 
00888     QLabel * lLimit = new QLabel(length , indentFrame );
00889     if(frameWidth!=-1)
00890     {
00891         lLimit->setAlignment( AlignRight );
00892         indentGrid->addWidget( lLimit, 1,0 );
00893     }
00894 
00895     QLabel * lLeft = new QLabel( i18n("&Left:"), indentFrame );
00896     lLeft->setAlignment( Qt::AlignVCenter | Qt::AlignRight );
00897     indentGrid->addWidget( lLeft, 1, 0 );
00898 
00899     eLeft = new KoUnitDoubleSpinBox( indentFrame, 0, 9999, 1, 0.0, m_unit );
00900     lLeft->setBuddy( eLeft );
00901     indentGrid->addWidget( eLeft, 1, 1 );
00902     connect( eLeft, SIGNAL( valueChangedPt(double ) ), this, SLOT( leftChanged( double ) ) );
00903 
00904     QLabel * lRight = new QLabel( i18n("&Right:"), indentFrame );
00905     lRight->setAlignment( Qt::AlignVCenter | Qt::AlignRight );
00906     indentGrid->addWidget( lRight, 2, 0 );
00907 
00908     eRight = new KoUnitDoubleSpinBox( indentFrame, 0, 9999, 1, 0.0, m_unit );
00909     lRight->setBuddy( eRight );
00910     indentGrid->addWidget( eRight, 2, 1 );
00911     connect( eRight, SIGNAL( valueChangedPt( double ) ), this, SLOT( rightChanged( double ) ) );
00912 
00913     QLabel * lFirstLine = new QLabel( i18n("&First line:"), indentFrame );
00914     lFirstLine->setAlignment( Qt::AlignVCenter | Qt::AlignRight );
00915     indentGrid->addWidget( lFirstLine, 3, 0 );
00916 
00917     eFirstLine = new KoUnitDoubleSpinBox( indentFrame, -9999, 9999, 1, 0.0, m_unit );
00918     lFirstLine->setBuddy( eFirstLine );
00919     connect( eFirstLine, SIGNAL( valueChangedPt( double ) ), this, SLOT( firstChanged( double ) ) );
00920     indentGrid->addWidget( eFirstLine, 3, 1 );
00921 
00922     // grid row spacing
00923     indentGrid->addRowSpacing( 0, fontMetrics().height() / 2 ); // groupbox title
00924     for ( int i = 1 ; i < indentGrid->numRows() ; ++i )
00925         indentGrid->setRowStretch( i, 1 );
00926     mainGrid->addWidget( indentFrame, 0, 0 );
00927 
00928         // --------------- line spacing ---------------
00929     QGroupBox * spacingFrame = new QGroupBox( i18n( "Line &Spacing" ), this, "spacingFrame" );
00930     QGridLayout * spacingGrid = new QGridLayout( spacingFrame, 2, 1,
00931                                                  KDialog::marginHint(), KDialog::spacingHint() );
00932 
00933     cSpacing = new QComboBox( false, spacingFrame, "" );
00934     // Keep order in sync with lineSpacingType() and display()
00935     cSpacing->insertItem( i18n( "Line spacing value", "Single" ) );
00936     cSpacing->insertItem( i18n( "Line spacing value", "1.5 Lines" ) );
00937     cSpacing->insertItem( i18n( "Line spacing value", "Double" ) );
00938     cSpacing->insertItem( i18n( "Proportional") ); // LS_MULTIPLE, called Proportional like in OO
00939     cSpacing->insertItem( i18n( "Line Distance (%1)" ).arg(unitName) ); // LS_CUSTOM
00940     cSpacing->insertItem( i18n( "At Least (%1)" ).arg(unitName) );
00941     cSpacing->insertItem( i18n( "Fixed (%1)").arg(unitName) ); // LS_FIXED
00942 
00943     connect( cSpacing, SIGNAL( activated( int ) ), this, SLOT( spacingActivated( int ) ) );
00944     spacingGrid->addWidget( cSpacing, 1, 0 );
00945 
00946     sSpacingStack = new QWidgetStack( spacingFrame );
00947     
00948     eSpacing = new KoUnitDoubleSpinBox( spacingFrame, 0, 9999, CM_TO_POINT(1),
00949                     0.0, m_unit );
00950     eSpacing->setRange( 0, 9999, 1, false);
00951     connect( eSpacing, SIGNAL( valueChanged( double ) ), this, SLOT( spacingChanged( double ) ) );
00952     eSpacingPercent = new KIntNumInput( 100, spacingFrame );
00953     eSpacingPercent->setRange( 0, 1000, 10, false );
00954     eSpacingPercent->setSuffix( " %" );
00955     connect( eSpacingPercent, SIGNAL( valueChanged( int ) ), this, SLOT( spacingChanged( int ) ) );
00956     
00957     sSpacingStack->addWidget( eSpacing );
00958     sSpacingStack->addWidget( eSpacingPercent );
00959     spacingGrid->addWidget( sSpacingStack, 1, 1 );
00960 
00961     // grid row spacing
00962     spacingGrid->addRowSpacing( 0, fontMetrics().height() / 2 ); // groupbox title
00963     for ( int i = 1 ; i < spacingGrid->numRows() ; ++i )
00964         spacingGrid->setRowStretch( i, 1 );
00965     mainGrid->addWidget( spacingFrame, 1, 0 );
00966 
00967     eSpacing->setEnabled( true );
00968 
00969     // --------------- paragraph spacing ---------------
00970     QGroupBox * pSpaceFrame = new QGroupBox( i18n( "Para&graph Space" ), this, "pSpaceFrame" );
00971     QGridLayout * pSpaceGrid = new QGridLayout( pSpaceFrame, 3, 2,
00972                                                 KDialog::marginHint(), KDialog::spacingHint() );
00973 
00974     QLabel * lBefore = new QLabel( i18n("Before:"), pSpaceFrame );
00975     lBefore->setAlignment( AlignRight );
00976     pSpaceGrid->addWidget( lBefore, 1, 0 );
00977 
00978     eBefore = new KoUnitDoubleSpinBox( pSpaceFrame, 0, 9999, CM_TO_POINT(1), 0.0, m_unit );
00979     eBefore->setRange( 0 , 9999, 1, false);
00980     connect( eBefore, SIGNAL( valueChanged( double ) ), this, SLOT( beforeChanged( double ) ) );
00981     pSpaceGrid->addWidget( eBefore, 1, 1 );
00982 
00983     QLabel * lAfter = new QLabel( i18n("After:"), pSpaceFrame );
00984     lAfter->setAlignment( AlignRight );
00985     pSpaceGrid->addWidget( lAfter, 2, 0 );
00986 
00987     eAfter = new KoUnitDoubleSpinBox( pSpaceFrame, 0, 9999, 1, 0.0, m_unit );
00988     eAfter->setRange( 0, 9999, 1, false);
00989     connect( eAfter, SIGNAL( valueChanged( double ) ), this, SLOT( afterChanged( double ) ) );
00990     pSpaceGrid->addWidget( eAfter, 2, 1 );
00991 
00992     // grid row spacing
00993     pSpaceGrid->addRowSpacing( 0, fontMetrics().height() / 2 ); // groupbox title
00994     for ( int i = 1 ; i < pSpaceGrid->numRows() ; ++i )
00995         pSpaceGrid->setRowStretch( i, 1 );
00996     mainGrid->addWidget( pSpaceFrame, 2, 0 );
00997 
00998     // --------------- preview --------------------
00999     prev1 = new KPagePreview( this, "KPagePreview" );
01000     mainGrid->addMultiCellWidget( prev1, 0, mainGrid->numRows()-1, 1, 1 );
01001 
01002     mainGrid->setColStretch( 1, 1 );
01003     //mainGrid->setRowStretch( 4, 1 );
01004 }
01005 
01006 double KoIndentSpacingWidget::leftIndent() const
01007 {
01008     return QMAX(0, eLeft->value() );
01009 }
01010 
01011 double KoIndentSpacingWidget::rightIndent() const
01012 {
01013     return QMAX(0,eRight->value() );
01014 }
01015 
01016 double KoIndentSpacingWidget::firstLineIndent() const
01017 {
01018     return eFirstLine->value();
01019 }
01020 
01021 double KoIndentSpacingWidget::spaceBeforeParag() const
01022 {
01023     return QMAX(0, eBefore->value() );
01024 }
01025 
01026 double KoIndentSpacingWidget::spaceAfterParag() const
01027 {
01028     return QMAX(0, eAfter->value() );
01029 }
01030 
01031 KoParagLayout::SpacingType KoIndentSpacingWidget::lineSpacingType() const
01032 {
01033     int index = cSpacing->currentItem();
01034     switch ( index ) {
01035     case 0:
01036         return KoParagLayout::LS_SINGLE;
01037     case 1:
01038         return KoParagLayout::LS_ONEANDHALF;
01039     case 2:
01040         return KoParagLayout::LS_DOUBLE;
01041     case 3:
01042         return KoParagLayout::LS_MULTIPLE;
01043     case 4:
01044         return KoParagLayout::LS_CUSTOM;
01045     case 5:
01046         return KoParagLayout::LS_AT_LEAST;
01047     case 6:
01048         return KoParagLayout::LS_FIXED;
01049     default:
01050         kdError(32500) << "Error in KoIndentSpacingWidget::lineSpacingType" << endl;
01051         return KoParagLayout::LS_SINGLE;
01052     }
01053 }
01054 
01055 double KoIndentSpacingWidget::lineSpacing() const
01056 {
01057     return (lineSpacingType() == KoParagLayout::LS_MULTIPLE)
01058                                ? QMAX( 1, eSpacingPercent->value() ) / 100.0
01059                                : QMAX( 0, eSpacing->value() );
01060 }
01061 
01062 
01063 void KoIndentSpacingWidget::display( const KoParagLayout & lay )
01064 {
01065     double _left = lay.margins[QStyleSheetItem::MarginLeft];
01066     eLeft->changeValue( _left );
01067     //prev1->setLeft( _left );  done by leftChanged() below
01068     leftChanged( _left ); // sets min value for eFirstLine
01069 
01070     double _right = lay.margins[QStyleSheetItem::MarginRight];
01071     eRight->changeValue( _right );
01072     prev1->setRight( _right );
01073 
01074     double _first = lay.margins[QStyleSheetItem::MarginFirstLine];
01075     eFirstLine->changeValue( _first );
01076     prev1->setFirst( _first );
01077 
01078     double _before = lay.margins[QStyleSheetItem::MarginTop];
01079     eBefore->changeValue( _before );
01080     prev1->setBefore( _before );
01081 
01082     double _after = lay.margins[QStyleSheetItem::MarginBottom];
01083     eAfter->changeValue( _after );
01084     prev1->setAfter( _after );
01085 
01086     double _spacing = lay.lineSpacingValue();
01087     KoParagLayout::SpacingType _type = lay.lineSpacingType;
01088     switch ( _type ) {
01089     case KoParagLayout::LS_SINGLE: // single
01090         cSpacing->setCurrentItem( 0 );
01091         break;
01092     case KoParagLayout::LS_ONEANDHALF:
01093         cSpacing->setCurrentItem( 1 );
01094         break;
01095     case KoParagLayout::LS_DOUBLE:
01096         cSpacing->setCurrentItem( 2 );
01097         break;
01098     case KoParagLayout::LS_MULTIPLE:
01099         cSpacing->setCurrentItem( 3 );
01100         break;
01101     case KoParagLayout::LS_CUSTOM:
01102         cSpacing->setCurrentItem( 4 );
01103         break;
01104     case KoParagLayout::LS_AT_LEAST:
01105         cSpacing->setCurrentItem( 5 );
01106         break;
01107     case KoParagLayout::LS_FIXED:
01108         cSpacing->setCurrentItem( 6 );
01109         break;
01110     default:
01111         cSpacing->setCurrentItem( 0 );
01112         break;
01113     }
01114 
01115     updateLineSpacing( _type );
01116     eSpacing->setValue( (_type == KoParagLayout::LS_MULTIPLE) ? QMAX( 1, _spacing )
01117                         : KoUnit::toUserValue( _spacing, m_unit ) );
01118     eSpacingPercent->setValue( ( _type == KoParagLayout::LS_MULTIPLE ) ? qRound( _spacing * 100 ) : 100 );
01119 }
01120 
01121 void KoIndentSpacingWidget::save( KoParagLayout & lay )
01122 {
01123     lay.setLineSpacingValue(lineSpacing());
01124     lay.lineSpacingType = lineSpacingType();
01125     lay.margins[QStyleSheetItem::MarginLeft] = leftIndent();
01126     lay.margins[QStyleSheetItem::MarginRight] = rightIndent();
01127     lay.margins[QStyleSheetItem::MarginFirstLine] = firstLineIndent();
01128     lay.margins[QStyleSheetItem::MarginTop] = spaceBeforeParag();
01129     lay.margins[QStyleSheetItem::MarginBottom] = spaceAfterParag();
01130 }
01131 
01132 QString KoIndentSpacingWidget::tabName()
01133 {
01134     return i18n( "Indent && S&pacing" );
01135 }
01136 
01137 void KoIndentSpacingWidget::leftChanged( double val )
01138 {
01139     prev1->setLeft( val );
01140     // The minimum first-line margin is -leftMargin() (where leftMargin>=0)
01141     eFirstLine->setMinValue( -QMAX( 0, val ) );
01142 }
01143 
01144 void KoIndentSpacingWidget::rightChanged( double val )
01145 {
01146     prev1->setRight( val );
01147 }
01148 
01149 void KoIndentSpacingWidget::firstChanged( double val )
01150 {
01151     prev1->setFirst( val );
01152 }
01153 
01154 void KoIndentSpacingWidget::updateLineSpacing( KoParagLayout::SpacingType _type )
01155 {
01156     bool needsValue = (_type != KoParagLayout::LS_SINGLE &&
01157                        _type != KoParagLayout::LS_ONEANDHALF &&
01158                        _type != KoParagLayout::LS_DOUBLE);
01159 
01160     if ( _type == KoParagLayout::LS_MULTIPLE )
01161     {
01162         sSpacingStack->raiseWidget( eSpacingPercent );
01163     }
01164     else
01165     {
01166         sSpacingStack->raiseWidget( eSpacing );
01167     }
01168     eSpacing->setEnabled( needsValue );
01169     if ( needsValue )
01170         prev1->setSpacing( eSpacing->value() );
01171     else
01172     {
01173         prev1->setSpacing( _type == KoParagLayout::LS_ONEANDHALF ? 8 :
01174                            _type == KoParagLayout::LS_DOUBLE ? 16 :0 );
01175     }
01176 }
01177 
01178 void KoIndentSpacingWidget::spacingActivated( int /*_index*/ )
01179 {
01180     updateLineSpacing( lineSpacingType() );
01181     if ( eSpacing->isEnabled() ) // i.e. needsValue = true
01182         eSpacing->setFocus();
01183 }
01184 
01185 void KoIndentSpacingWidget::spacingChanged( double _val )
01186 {
01187     prev1->setSpacing( _val );
01188 }
01189 
01190 void KoIndentSpacingWidget::spacingChanged( int _val )
01191 {
01192     prev1->setSpacing( _val / 100.0 );
01193 }
01194 
01195 void KoIndentSpacingWidget::beforeChanged( double _val )
01196 {
01197     prev1->setBefore( KoUnit::fromUserValue( _val, m_unit ) );
01198 }
01199 
01200 void KoIndentSpacingWidget::afterChanged( double _val )
01201 {
01202     prev1->setAfter( KoUnit::fromUserValue( _val, m_unit ) );
01203 }
01204 
01205 
01206 KoParagAlignWidget::KoParagAlignWidget( bool breakLine, QWidget * parent, const char * name )
01207         : KoParagLayoutWidget( KoParagDia::PD_ALIGN, parent, name )
01208 {
01209     QGridLayout *grid = new QGridLayout( this, 3, 2, KDialog::marginHint(), KDialog::spacingHint() );
01210 
01211     QVGroupBox * AlignGroup = new QVGroupBox( i18n( "Alignment" ), this );
01212 
01213     rLeft = new QRadioButton( i18n( "&Left" ), AlignGroup );
01214     connect( rLeft, SIGNAL( clicked() ), this, SLOT( alignLeft() ) );
01215 
01216     rCenter = new QRadioButton( i18n( "C&enter" ), AlignGroup );
01217     connect( rCenter, SIGNAL( clicked() ), this, SLOT( alignCenter() ) );
01218 
01219     rRight = new QRadioButton( i18n( "&Right" ), AlignGroup );
01220     connect( rRight, SIGNAL( clicked() ), this, SLOT( alignRight() ) );
01221 
01222     rJustify = new QRadioButton( i18n( "&Justify" ), AlignGroup );
01223     connect( rJustify, SIGNAL( clicked() ), this, SLOT( alignJustify() ) );
01224 
01225     clearAligns();
01226     rLeft->setChecked( true );
01227 
01228     grid->addWidget(AlignGroup, 0, 0);
01229 
01230     // --------------- End of page /frame ---------------
01231     QGroupBox * endFramePage = new QGroupBox( i18n( "Behavior at &End of Frame/Page" ), this );
01232     QGridLayout * endFramePageGrid = new QGridLayout( endFramePage, 4, 1,
01233                                                       KDialog::marginHint(), KDialog::spacingHint() );
01234 
01235     cKeepLinesTogether = new QCheckBox( i18n("&Keep lines together"),endFramePage);
01236     endFramePageGrid->addWidget( cKeepLinesTogether, 1, 0 );
01237     cHardBreakBefore = new QCheckBox( i18n("Insert break before paragraph"),endFramePage);
01238     endFramePageGrid->addWidget( cHardBreakBefore, 2, 0 );
01239     cHardBreakAfter = new QCheckBox( i18n("Insert break after paragraph"),endFramePage);
01240     endFramePageGrid->addWidget( cHardBreakAfter, 3, 0 );
01241 
01242     endFramePageGrid->addRowSpacing( 0, fontMetrics().height() / 2 ); // groupbox title
01243     for ( int i = 0 ; i < endFramePageGrid->numRows()-1 ; ++i )
01244         endFramePageGrid->setRowStretch( 0, 0 );
01245     endFramePageGrid->setRowStretch( endFramePageGrid->numRows()-1, 1 );
01246     grid->addWidget( endFramePage, 2, 0 );
01247 
01248     endFramePage->setEnabled(breakLine);
01249 
01250     // --------------- preview --------------------
01251     prev2 = new KPagePreview2( this, "KPagePreview2" );
01252     grid->addMultiCellWidget( prev2, 0, 2, 1, 1 );
01253 
01254     // --------------- main grid ------------------
01255     grid->setColStretch( 1, 1 );
01256     grid->setRowStretch( 1, 1 );
01257 }
01258 
01259 int KoParagAlignWidget::pageBreaking() const
01260 {
01261     int pb = 0;
01262     if ( cKeepLinesTogether->isChecked() )
01263         pb |= KoParagLayout::KeepLinesTogether;
01264     if ( cHardBreakBefore->isChecked() )
01265         pb |= KoParagLayout::HardFrameBreakBefore;
01266     if ( cHardBreakAfter->isChecked() )
01267         pb |= KoParagLayout::HardFrameBreakAfter;
01268     return pb;
01269 }
01270 
01271 
01272 void KoParagAlignWidget::display( const KoParagLayout & lay )
01273 {
01274     int align = lay.alignment;
01275     prev2->setAlign( align );
01276 
01277     clearAligns();
01278     switch ( align ) {
01279         case Qt::AlignAuto: // see KoView::setAlign
01280         case Qt::AlignLeft:
01281             rLeft->setChecked( true );
01282             break;
01283         case Qt::AlignHCenter:
01284             rCenter->setChecked( true );
01285             break;
01286         case Qt::AlignRight:
01287             rRight->setChecked( true );
01288             break;
01289         case Qt::AlignJustify:
01290             rJustify->setChecked( true );
01291     }
01292 
01293     cKeepLinesTogether->setChecked( lay.pageBreaking & KoParagLayout::KeepLinesTogether );
01294     cHardBreakBefore->setChecked( lay.pageBreaking & KoParagLayout::HardFrameBreakBefore );
01295     cHardBreakAfter->setChecked( lay.pageBreaking & KoParagLayout::HardFrameBreakAfter );
01296     // ## preview support for end-of-frame ?
01297 }
01298 
01299 void KoParagAlignWidget::save( KoParagLayout & lay )
01300 {
01301     lay.alignment = align();
01302     lay.pageBreaking = pageBreaking();
01303 }
01304 
01305 int KoParagAlignWidget::align() const
01306 {
01307     if ( rLeft->isChecked() ) return Qt::AlignLeft;
01308     else if ( rCenter->isChecked() ) return Qt::AlignHCenter;
01309     else if ( rRight->isChecked() ) return Qt::AlignRight;
01310     else if ( rJustify->isChecked() ) return Qt::AlignJustify;
01311 
01312     return Qt::AlignLeft;
01313 }
01314 
01315 QString KoParagAlignWidget::tabName()
01316 {
01317     return i18n( "General &Layout" );
01318 }
01319 
01320 void KoParagAlignWidget::alignLeft()
01321 {
01322     prev2->setAlign( Qt::AlignLeft );
01323     clearAligns();
01324     rLeft->setChecked( true );
01325 }
01326 
01327 void KoParagAlignWidget::alignCenter()
01328 {
01329     prev2->setAlign( Qt::AlignHCenter );
01330     clearAligns();
01331     rCenter->setChecked( true );
01332 }
01333 
01334 void KoParagAlignWidget::alignRight()
01335 {
01336     prev2->setAlign( Qt::AlignRight );
01337     clearAligns();
01338     rRight->setChecked( true );
01339 }
01340 
01341 void KoParagAlignWidget::alignJustify()
01342 {
01343     prev2->setAlign( Qt::AlignJustify );
01344     clearAligns();
01345     rJustify->setChecked( true );
01346 }
01347 
01348 void KoParagAlignWidget::clearAligns()
01349 {
01350     rLeft->setChecked( false );
01351     rCenter->setChecked( false );
01352     rRight->setChecked( false );
01353     rJustify->setChecked( false );
01354 }
01355 
01357 
01358 KoParagDecorationWidget::KoParagDecorationWidget( QWidget * parent,
01359                                                     const char * name )
01360     : KoParagLayoutWidget( KoParagDia::PD_DECORATION, parent, name )
01361 {
01362     QVBoxLayout *tabLayout = new QVBoxLayout( this );
01363     wDeco = new KoParagDecorationTab( this );
01364     tabLayout->add( wDeco );
01365 
01366     // Set up Border Style combo box
01367     wDeco->cbBorderStyle->insertItem( KoBorder::getStyle( KoBorder::SOLID ) );
01368     wDeco->cbBorderStyle->insertItem( KoBorder::getStyle( KoBorder::DASH ) );
01369     wDeco->cbBorderStyle->insertItem( KoBorder::getStyle( KoBorder::DOT ) );
01370     wDeco->cbBorderStyle->insertItem( KoBorder::getStyle( KoBorder::DASH_DOT ) );
01371     wDeco->cbBorderStyle->insertItem( KoBorder::getStyle( KoBorder::DASH_DOT_DOT ) );
01372     wDeco->cbBorderStyle->insertItem( KoBorder::getStyle( KoBorder::DOUBLE_LINE  ) );
01373 
01374     // Set up Border Width combo box
01375     for( unsigned int i = 1; i <= 10; i++ )
01376         wDeco->cbBorderWidth->insertItem(QString::number(i));
01377 
01378     // Setup the border toggle buttons, and merge checkbox
01379     connect( wDeco->bBorderLeft, SIGNAL( toggled( bool ) ),
01380              this, SLOT( brdLeftToggled( bool ) ) );
01381     connect( wDeco->bBorderRight, SIGNAL( toggled( bool ) ),
01382              this, SLOT( brdRightToggled( bool ) ) );
01383     connect( wDeco->bBorderTop, SIGNAL( toggled( bool ) ),
01384              this, SLOT( brdTopToggled( bool ) ) );
01385     connect( wDeco->bBorderBottom, SIGNAL( toggled( bool ) ),
01386              this, SLOT( brdBottomToggled( bool ) ) );
01387     connect( wDeco->cbJoinBorder, SIGNAL( toggled( bool ) ),
01388              this, SLOT( brdJoinToggled( bool ) ) );
01389 
01390     // Set up Border preview widget
01391     wPreview  = new KoBorderPreview( wDeco->borderPreview );
01392     QVBoxLayout *previewLayout = new QVBoxLayout( wDeco->borderPreview );
01393     previewLayout->addWidget( wPreview );
01394     connect( wPreview, SIGNAL( choosearea(QMouseEvent * ) ),
01395              this, SLOT( slotPressEvent(QMouseEvent *) ) );
01396 }
01397 
01399 // Current GUI selections
01400 KoBorder::BorderStyle KoParagDecorationWidget::curBorderStyle() const
01401 {
01402     QString selection = wDeco->cbBorderStyle->currentText();
01403     return KoBorder::getStyle( selection );
01404 }
01405 
01406 unsigned int KoParagDecorationWidget::curBorderWidth() const {
01407     return wDeco->cbBorderWidth->currentText().toUInt();
01408 }
01409 
01410 QColor KoParagDecorationWidget::curBorderColor() const {
01411     return wDeco->bBorderColor->color();
01412 }
01414 
01415 // Check whether a border is the same as that selected in the GUI
01416 bool KoParagDecorationWidget::borderChanged( const KoBorder& border ) {
01417     return (unsigned int)border.penWidth() != curBorderWidth() ||
01418            border.color != curBorderColor() ||
01419            border.getStyle() != curBorderStyle();
01420 }
01421 
01422 // Set a given border according to the values selected in the GUI
01423 void KoParagDecorationWidget::updateBorder( KoBorder& border )
01424 {
01425     border.setPenWidth( curBorderWidth() );
01426     border.color = curBorderColor();
01427     border.setStyle( curBorderStyle () );
01428 }
01429 
01430 void KoParagDecorationWidget::clickedBorderPreview( KoBorder& border,
01431                                                      KoBorder::BorderType position,
01432                                                      KPushButton *corresponding )
01433 {
01434     if ( borderChanged( border ) && corresponding->isOn() ) {
01435         updateBorder( border );
01436         wPreview->setBorder( position, border );
01437     }
01438     else
01439         corresponding->setOn( !corresponding->isOn() );
01440 }
01441 
01442 // Establish which border position was clicked in the border preview,
01443 // and update the appropriate border
01444 void KoParagDecorationWidget::slotPressEvent(QMouseEvent *_ev)
01445 {
01446     const int OFFSETX = 15;
01447     const int OFFSETY = 7;
01448     const int Ko_SPACE = 30;
01449 
01450     QRect r = wPreview->contentsRect();
01451     QRect rect(r.x() + OFFSETX, r.y() + OFFSETY,
01452                r.width() - OFFSETX, r.y() + OFFSETY + Ko_SPACE);
01453     if(rect.contains(QPoint(_ev->x(),_ev->y())))
01454     {
01455         clickedBorderPreview( m_topBorder, KoBorder::TopBorder,
01456                               wDeco->bBorderTop );
01457     }
01458 
01459     rect.setCoords(r.x() + OFFSETX, r.height() - OFFSETY - Ko_SPACE,
01460                    r.width() - OFFSETX, r.height() - OFFSETY);
01461     if(rect.contains(QPoint(_ev->x(),_ev->y())))
01462     {
01463         clickedBorderPreview( m_bottomBorder, KoBorder::BottomBorder,
01464                               wDeco->bBorderBottom );
01465     }
01466 
01467     rect.setCoords(r.x() + OFFSETX, r.y() + OFFSETY,
01468                    r.x() + Ko_SPACE + OFFSETX, r.height() - OFFSETY);
01469     if(rect.contains(QPoint(_ev->x(),_ev->y())))
01470     {
01471         clickedBorderPreview( m_leftBorder, KoBorder::LeftBorder,
01472                               wDeco->bBorderLeft );
01473     }
01474 
01475     rect.setCoords(r.width() - OFFSETX - Ko_SPACE, r.y() + OFFSETY,
01476                    r.width() - OFFSETX, r.height() - OFFSETY);
01477     if(rect.contains(QPoint(_ev->x(),_ev->y())))
01478     {
01479         clickedBorderPreview( m_rightBorder, KoBorder::RightBorder,
01480                               wDeco->bBorderRight );
01481     }
01482 }
01483 
01484 void KoParagDecorationWidget::display( const KoParagLayout & lay )
01485 {
01486     wDeco->bBackgroundColor->setColor( lay.backgroundColor );
01487 
01488     m_leftBorder = lay.leftBorder;
01489     m_rightBorder = lay.rightBorder;
01490     m_topBorder = lay.topBorder;
01491     m_bottomBorder = lay.bottomBorder;
01492     m_joinBorder = lay.joinBorder;
01493 
01494     wDeco->bBorderLeft->blockSignals( true );
01495     wDeco->bBorderRight->blockSignals( true );
01496     wDeco->bBorderTop->blockSignals( true );
01497     wDeco->bBorderBottom->blockSignals( true );
01498     updateBorders();
01499     wDeco->bBorderLeft->blockSignals( false );
01500     wDeco->bBorderRight->blockSignals( false );
01501     wDeco->bBorderTop->blockSignals( false );
01502     wDeco->bBorderBottom->blockSignals( false );
01503 }
01504 
01505 void KoParagDecorationWidget::updateBorders()
01506 {
01507     wDeco->bBorderLeft->setOn( m_leftBorder.penWidth() > 0 );
01508     wDeco->bBorderRight->setOn( m_rightBorder.penWidth() > 0 );
01509     wDeco->bBorderTop->setOn( m_topBorder.penWidth() > 0 );
01510     wDeco->bBorderBottom->setOn( m_bottomBorder.penWidth() > 0 );
01511     wDeco->cbJoinBorder->setChecked( m_joinBorder );
01512     wPreview->setLeftBorder( m_leftBorder );
01513     wPreview->setRightBorder( m_rightBorder );
01514     wPreview->setTopBorder( m_topBorder );
01515     wPreview->setBottomBorder( m_bottomBorder );
01516 }
01517 
01518 
01519 void KoParagDecorationWidget::save( KoParagLayout & lay )
01520 {
01521     lay.backgroundColor = wDeco->bBackgroundColor->color();
01522     lay.topBorder = m_topBorder;
01523     lay.bottomBorder = m_bottomBorder;
01524     lay.leftBorder = m_leftBorder;
01525     lay.rightBorder = m_rightBorder;
01526     lay.joinBorder = m_joinBorder;
01527 }
01528 
01529 QColor KoParagDecorationWidget::backgroundColor() const {
01530     return wDeco->bBackgroundColor->color();
01531 }
01532 
01533 QString KoParagDecorationWidget::tabName() {
01534     // Why D&e..?  Because &De.. conflicts with &Delete in
01535     // the style manager.
01536     return i18n( "D&ecorations" );
01537 }
01538 
01539 void KoParagDecorationWidget::brdLeftToggled( bool _on )
01540 {
01541     if ( !_on )
01542         m_leftBorder.setPenWidth(0);
01543     else {
01544         m_leftBorder.setPenWidth( curBorderWidth() );
01545         m_leftBorder.color = curBorderColor();
01546         m_leftBorder.setStyle( curBorderStyle() );
01547     }
01548     wPreview->setLeftBorder( m_leftBorder );
01549 }
01550 
01551 void KoParagDecorationWidget::brdRightToggled( bool _on )
01552 {
01553     if ( !_on )
01554         m_rightBorder.setPenWidth(0);
01555     else {
01556         m_rightBorder.setPenWidth( curBorderWidth() );
01557         m_rightBorder.color = curBorderColor();
01558         m_rightBorder.setStyle( curBorderStyle() );
01559     }
01560     wPreview->setRightBorder( m_rightBorder );
01561 }
01562 
01563 void KoParagDecorationWidget::brdTopToggled( bool _on )
01564 {
01565     if ( !_on )
01566         m_topBorder.setPenWidth(0);
01567     else {
01568         m_topBorder.setPenWidth( curBorderWidth() );
01569         m_topBorder.color = curBorderColor();
01570         m_topBorder.setStyle( curBorderStyle() );
01571     }
01572     wPreview->setTopBorder( m_topBorder );
01573 }
01574 
01575 void KoParagDecorationWidget::brdBottomToggled( bool _on )
01576 {
01577     if ( !_on )
01578         m_bottomBorder.setPenWidth ( 0 );
01579     else {
01580         m_bottomBorder.setPenWidth( curBorderWidth() );
01581         m_bottomBorder.color = curBorderColor();
01582         m_bottomBorder.setStyle( curBorderStyle() );
01583     }
01584     wPreview->setBottomBorder( m_bottomBorder );
01585 }
01586 
01587 void KoParagDecorationWidget::brdJoinToggled( bool _on ) {
01588     m_joinBorder = _on;
01589 }
01591 
01592 
01593 KoParagCounterWidget::KoParagCounterWidget( bool disableAll, QWidget * parent, const char * name )
01594     : KoParagLayoutWidget( KoParagDia::PD_NUMBERING, parent, name )
01595 {
01596 
01597     QVBoxLayout *Form1Layout = new QVBoxLayout( this );
01598     Form1Layout->setSpacing( KDialog::spacingHint() );
01599     Form1Layout->setMargin( KDialog::marginHint() );
01600 
01601     gNumbering = new QButtonGroup( this, "numberingGroup" );
01602     gNumbering->setTitle( i18n( "Numbering" ) );
01603     gNumbering->setColumnLayout(0, Qt::Vertical );
01604     gNumbering->layout()->setSpacing( 0 );
01605     gNumbering->layout()->setMargin( 0 );
01606     QHBoxLayout *numberingGroupLayout = new QHBoxLayout( gNumbering->layout() );
01607     numberingGroupLayout->setAlignment( Qt::AlignTop );
01608     numberingGroupLayout->setSpacing( KDialog::spacingHint() );
01609     numberingGroupLayout->setMargin( KDialog::marginHint() );
01610 
01611     // What type of numbering is required?
01612     QRadioButton *rNone = new QRadioButton( gNumbering, "rNone" );
01613     rNone->setText( i18n( "&None" ) );
01614     numberingGroupLayout->addWidget( rNone );
01615 
01616     gNumbering->insert( rNone , KoParagCounter::NUM_NONE);
01617 
01618     QRadioButton *rList = new QRadioButton( gNumbering, "rList" );
01619     rList->setText( i18n( "&List" ) );
01620     gNumbering->insert( rList , KoParagCounter::NUM_LIST);
01621     numberingGroupLayout->addWidget( rList );
01622 
01623     QRadioButton *rChapter = new QRadioButton( gNumbering, "rChapter" );
01624     rChapter->setText( i18n( "Chapt&er" ) );
01625     gNumbering->insert( rChapter , KoParagCounter::NUM_CHAPTER);
01626     numberingGroupLayout->addWidget( rChapter );
01627     Form1Layout->addWidget( gNumbering );
01628     connect( gNumbering, SIGNAL( clicked( int ) ), this, SLOT( numTypeChanged( int ) ) );
01629 
01630     m_styleWidget = new KoCounterStyleWidget( true, false, disableAll, this );
01631 
01632     connect( m_styleWidget, SIGNAL( sig_suffixChanged (const QString &) ), this, SLOT( suffixChanged(const QString &) ) );
01633     connect( m_styleWidget, SIGNAL( sig_prefixChanged (const QString &) ), this, SLOT( prefixChanged(const QString &) ) );
01634     connect( m_styleWidget, SIGNAL( sig_startChanged(int) ), this, SLOT( startChanged(int) ) );
01635     connect( m_styleWidget, SIGNAL( sig_restartChanged(bool) ), this, SLOT( restartChanged(bool) ) );
01636     connect( m_styleWidget, SIGNAL( sig_depthChanged (int) ), this, SLOT( depthChanged(int) ) );
01637     connect( m_styleWidget, SIGNAL( sig_displayLevelsChanged (int) ), this, SLOT( displayLevelsChanged(int) ) );
01638     connect( m_styleWidget, SIGNAL( sig_alignmentChanged (int) ), this, SLOT( alignmentChanged(int) ) );
01639     connect( m_styleWidget, SIGNAL( changeCustomBullet( const QString & , QChar ) ), this, SLOT( slotChangeCustomBullet( const QString & , QChar ) ) );
01640 
01641     connect( m_styleWidget, SIGNAL( sig_numTypeChanged( int ) ), this, SLOT( numTypeChanged(int ) ) );
01642     connect( m_styleWidget, SIGNAL( changeStyle( KoParagCounter::Style ) ), this, SLOT( styleChanged (KoParagCounter::Style ) ) );
01643 
01644     Form1Layout->addWidget( m_styleWidget );
01645 
01646 
01647     preview = new KoStylePreview( i18n( "Preview" ), i18n("Normal paragraph text"), this, "counter preview" );
01648     Form1Layout->addWidget( preview );
01649     if ( disableAll)
01650     {
01651         gNumbering->setEnabled( false);
01652         preview->setEnabled( false );
01653     }
01654 
01655     QSpacerItem* spacer = new QSpacerItem( 0, 0, QSizePolicy::Minimum, QSizePolicy::Expanding);
01656     Form1Layout->addItem( spacer );
01657 }
01658 
01659 void KoParagCounterWidget::styleChanged( KoParagCounter::Style st )
01660 {
01661     m_counter.setStyle( st );
01662     updatePreview();
01663 }
01664 
01665 void KoParagCounterWidget::slotChangeCustomBullet( const QString & f, QChar c)
01666 {
01667     m_counter.setCustomBulletFont( f );
01668     m_counter.setCustomBulletCharacter( c );
01669     preview->setCounter( m_counter );
01670 }
01671 
01672 QString KoParagCounterWidget::tabName() {
01673     return i18n( "B&ullets/Numbers" );
01674 }
01675 
01676 void KoParagCounterWidget::numTypeChanged( int nType ) {
01677     // radio buttons pressed to change numbering type
01678     m_counter.setNumbering( static_cast<KoParagCounter::Numbering>( nType ) );
01679     preview->setEnabled( m_counter.numbering() != KoParagCounter::NUM_NONE );
01680     m_styleWidget->numTypeChanged( nType );
01681 
01682     updatePreview();
01683 }
01684 
01685 void KoParagCounterWidget::display( const KoParagLayout & lay ) {
01686     KoParagCounter::Style style = KoParagCounter::STYLE_NONE;
01687     if ( lay.counter )
01688     {
01689         style=lay.counter->style();
01690         m_counter = *lay.counter;
01691     }
01692     else
01693     {
01694         m_counter = KoParagCounter();
01695     }
01696     gNumbering->setButton( m_counter.numbering() );
01697     preview->setStyle( lay.style );
01698     preview->setCounter( m_counter );
01699     m_styleWidget->display( lay );
01700 }
01701 
01702 void KoParagCounterWidget::updatePreview() {
01703     preview->setCounter(m_counter);
01704     preview->repaint(true);
01705 }
01706 
01707 void KoParagCounterWidget::save( KoParagLayout & lay ) {
01708 /*    m_counter.setDepth(spnDepth->value());
01709     m_counter.setStartNumber(spnStart->value());
01710     m_counter.setPrefix(sPrefix->text());
01711     m_counter.setSuffix(sSuffix->text()); */
01712 
01713     if ( lay.counter )
01714         *lay.counter = m_counter;
01715     else
01716         lay.counter = new KoParagCounter( m_counter );
01717 }
01718 
01719 KoTabulatorsLineEdit::KoTabulatorsLineEdit( QWidget *parent, double lower, double upper, double step, double value /*= 0.0*/, KoUnit::Unit unit /*= KoUnit::U_PT*/, unsigned int precision /*= 2*/, const char *name /*= 0*/ )
01720     : KoUnitDoubleSpinBox ( parent, lower, upper, step, value, unit, precision, name )
01721 {
01722     setRange( 0, 9999, 1, false);
01723 }
01724 
01725 void KoTabulatorsLineEdit::keyPressEvent ( QKeyEvent *ke )
01726 {
01727     if( ke->key()  == QKeyEvent::Key_Return ||
01728         ke->key()  == QKeyEvent::Key_Enter )
01729     {
01730         emit keyReturnPressed();
01731         return;
01732     }
01733     KoUnitDoubleSpinBox::keyPressEvent (ke);
01734 }
01735 
01736 KoParagTabulatorsWidget::KoParagTabulatorsWidget( KoUnit::Unit unit, double frameWidth,QWidget * parent, const char * name )
01737     : KoParagLayoutWidget( KoParagDia::PD_TABS, parent, name ), m_unit(unit) {
01738     QString length;
01739     if(frameWidth==-1) {
01740         frameWidth=9999;
01741         m_toplimit=9999;
01742     } else {
01743         m_toplimit=frameWidth;
01744         length=i18n("Frame width: %1 %2")
01745         .arg(KoUnit::toUserStringValue(frameWidth,m_unit))
01746         .arg(KoUnit::unitName(m_unit));
01747         frameWidth=KoUnit::toUserValue(frameWidth,m_unit);
01748     }
01749     QVBoxLayout* Form1Layout = new QVBoxLayout( this );
01750     Form1Layout->setSpacing( KDialog::spacingHint() );
01751     Form1Layout->setMargin( KDialog::marginHint() );
01752 
01753     QHBoxLayout* Layout13 = new QHBoxLayout;
01754     Layout13->setSpacing( KDialog::spacingHint() );
01755     Layout13->setMargin( 0 ); //?
01756 
01757     lstTabs = new QListBox( this);
01758     lstTabs->insertItem( "mytabvalue" );
01759     lstTabs->setMaximumSize( QSize( 300, 32767 ) );
01760     Layout13->addWidget( lstTabs );
01761 
01762     editLayout = new QVBoxLayout;
01763     editLayout->setSpacing( KDialog::spacingHint() );
01764     editLayout->setMargin( 0 ); //?
01765 
01766     gPosition = new QGroupBox( this, "gPosition" );
01767     gPosition->setTitle( i18n( "Po&sition" ) );
01768     gPosition->setColumnLayout(0, Qt::Vertical );
01769     gPosition->layout()->setSpacing( 0 );
01770     gPosition->layout()->setMargin( 0 );
01771     QVBoxLayout* GroupBox2Layout = new QVBoxLayout( gPosition->layout() );
01772     GroupBox2Layout->setAlignment( Qt::AlignTop );
01773     GroupBox2Layout->setSpacing( KDialog::spacingHint() );
01774     GroupBox2Layout->setMargin( KDialog::marginHint() );
01775 
01776     QHBoxLayout* Layout5 = new QHBoxLayout;
01777     Layout5->setSpacing( KDialog::spacingHint() );
01778     Layout5->setMargin( 0 ); //?
01779 
01780     sTabPos = new KoTabulatorsLineEdit( gPosition, 0, 9999, 1, 0.0, m_unit );
01781     sTabPos->setRange( 0, 9999, 1 );
01782     sTabPos->setMaximumSize( QSize( 100, 32767 ) );
01783     Layout5->addWidget( sTabPos );
01784     QSpacerItem* spacer = new QSpacerItem( 20, 20, QSizePolicy::Expanding, QSizePolicy::Minimum );
01785     Layout5->addItem( spacer );
01786     GroupBox2Layout->addLayout( Layout5 );
01787     editLayout->addWidget( gPosition );
01788 
01789     QLabel* TextLabel1 = new QLabel( gPosition );
01790     QString unitDescription = KoUnit::unitDescription( m_unit );
01791     TextLabel1->setText( length );
01792     GroupBox2Layout->addWidget( TextLabel1 );
01793 
01794     bgAlign = new QButtonGroup( this );
01795     bgAlign->setTitle( i18n( "Alignment" ) );
01796     bgAlign->setColumnLayout(0, Qt::Vertical );
01797     bgAlign->layout()->setSpacing( 0 );
01798     bgAlign->layout()->setMargin( 0 );
01799     QVBoxLayout* ButtonGroup1Layout = new QVBoxLayout( bgAlign->layout() );
01800     ButtonGroup1Layout->setAlignment( Qt::AlignTop );
01801     ButtonGroup1Layout->setSpacing( KDialog::spacingHint() );
01802     ButtonGroup1Layout->setMargin( KDialog::marginHint() );
01803 
01804     rAlignLeft = new QRadioButton( bgAlign );
01805     rAlignLeft->setText( i18n( "&Left" ) );
01806     ButtonGroup1Layout->addWidget( rAlignLeft );
01807 
01808     rAlignCentre = new QRadioButton( bgAlign );
01809     rAlignCentre->setText( i18n( "C&enter" ) );
01810     ButtonGroup1Layout->addWidget( rAlignCentre );
01811 
01812     rAlignRight = new QRadioButton( bgAlign );
01813     rAlignRight->setText( i18n( "&Right" ) );
01814     ButtonGroup1Layout->addWidget( rAlignRight );
01815 
01816     QHBoxLayout* Layout8 = new QHBoxLayout;
01817     Layout8->setSpacing( KDialog::spacingHint() );
01818     Layout8->setMargin( 0 );
01819 
01820     rAlignVar = new QRadioButton( bgAlign );
01821     rAlignVar->setText( i18n( "On followin&g character: " ) );
01822     Layout8->addWidget( rAlignVar );
01823 
01824     sAlignChar = new QLineEdit( bgAlign);
01825     sAlignChar->setMaximumSize( QSize( 60, 32767 ) );
01826     sAlignChar->setText(QString(KGlobal::locale()->decimalSymbol()[0]));
01827     Layout8->addWidget( sAlignChar );
01828     QSpacerItem* spacer_2 = new QSpacerItem( 20, 20, QSizePolicy::Expanding, QSizePolicy::Minimum );
01829     Layout8->addItem( spacer_2 );
01830     ButtonGroup1Layout->addLayout( Layout8 );
01831     editLayout->addWidget( bgAlign );
01832 
01833     gTabLeader = new QGroupBox( this, "gTabLeader" );
01834     gTabLeader->setTitle( i18n( "Tab Leader" ) );
01835     QVBoxLayout* GroupBox5Layout = new QVBoxLayout( gTabLeader );
01836     GroupBox5Layout->setAlignment( Qt::AlignTop );
01837     GroupBox5Layout->setSpacing( KDialog::spacingHint() );
01838     GroupBox5Layout->setMargin( KDialog::marginHint() );
01839     GroupBox5Layout->addSpacing( fontMetrics().height() / 2 ); // groupbox title
01840 
01841     QLabel* TextLabel1_2 = new QLabel( gTabLeader );
01842     TextLabel1_2->setText( i18n( "The space a tab uses can be filled with a pattern." ) );
01843     GroupBox5Layout->addWidget( TextLabel1_2 );
01844 
01845     QGridLayout *fillingGrid = new QGridLayout( 0L, 2, 2, 0, KDialog::spacingHint() );
01846 
01847     QLabel* TextLabel2 = new QLabel( gTabLeader);
01848     TextLabel2->setText( i18n( "&Filling:" ) );
01849     TextLabel2->setAlignment( AlignRight );
01850     fillingGrid->addWidget( TextLabel2, 0, 0 );
01851 
01852     cFilling = new QComboBox( FALSE, gTabLeader);
01853     cFilling->insertItem( i18n( "Blank" ) );
01854     cFilling->insertItem( "_ _ _ _ _ _"); // DOT
01855     cFilling->insertItem( "_________");   // SOLID
01856     cFilling->insertItem( "___ ___ __");  // DASH
01857     cFilling->insertItem( "___ _ ___ _"); // DASH_DOT
01858     cFilling->insertItem( "___ _ _ ___"); // DASH_DOT_DOT
01859     TextLabel2->setBuddy( cFilling );
01860     fillingGrid->addWidget( cFilling, 0, 1 );
01861 
01862     QLabel * TextLabel3 = new QLabel( i18n("&Width:"), gTabLeader );
01863     TextLabel3->setAlignment( AlignRight );
01864     fillingGrid->addWidget( TextLabel3, 1, 0 );
01865 
01866     eWidth = new KoUnitDoubleSpinBox( gTabLeader );
01867     eWidth->setMinValue(0.01);
01868     eWidth->setUnit( m_unit );
01869     TextLabel3->setBuddy( eWidth );
01870     fillingGrid->addWidget( eWidth, 1, 1 );
01871 
01872     GroupBox5Layout->addLayout( fillingGrid );
01873     editLayout->addWidget( gTabLeader );
01874     QSpacerItem* spacer_4 = new QSpacerItem( 20, 20, QSizePolicy::Minimum, QSizePolicy::Expanding );
01875     editLayout->addItem( spacer_4 );
01876     Layout13->addLayout( editLayout );
01877     Form1Layout->addLayout( Layout13 );
01878 
01879     QHBoxLayout* Layout4 = new QHBoxLayout;
01880     Layout4->setSpacing( KDialog::spacingHint() );
01881     Layout4->setMargin( 0 );
01882 
01883     bNew = new QPushButton( this);
01884     bNew->setText( i18n( "&New" ) );
01885     Layout4->addWidget( bNew );
01886 
01887     bDelete = new QPushButton( this);
01888     bDelete->setText( i18n( "&Delete" ) );
01889     Layout4->addWidget( bDelete );
01890 
01891     bDeleteAll = new QPushButton( this);
01892     bDeleteAll->setText( i18n( "Delete All" ) );
01893     Layout4->addWidget( bDeleteAll );
01894 
01895     QSpacerItem* spacer_5 = new QSpacerItem( 20, 20, QSizePolicy::Expanding, QSizePolicy::Minimum );
01896     Layout4->addItem( spacer_5 );
01897     Form1Layout->addLayout( Layout4 );
01898 
01899     //signal valueChanged passes value which the user see (unlike the value() function)
01900     //so fromUserValue has to be used in slotTabValueChanged
01901     connect(sTabPos,SIGNAL(valueChanged(double)), this, SLOT(slotTabValueChanged(double )));
01902     connect(sTabPos,SIGNAL( keyReturnPressed()),this,SLOT(newClicked()));
01903     connect(sAlignChar,SIGNAL(textChanged( const QString & )), this, SLOT(slotAlignCharChanged( const QString & )));
01904     connect(bNew,SIGNAL(clicked ()),this,SLOT(newClicked()));
01905     connect(bDelete,SIGNAL(clicked ()),this,SLOT(deleteClicked()));
01906     connect(bDeleteAll,SIGNAL(clicked ()),this,SLOT(deleteAllClicked()));
01907     connect(bgAlign,SIGNAL(clicked (int)),this,SLOT(updateAlign(int)));
01908     connect(cFilling,SIGNAL(activated (int)),this,SLOT(updateFilling(int)));
01909     connect(eWidth,SIGNAL(valueChangedPt( double ) ),this,SLOT(updateWidth()));
01910     connect(lstTabs,SIGNAL(highlighted (int)),this,SLOT(setActiveItem(int)));
01911     noSignals=false;
01912 }
01913 
01914 void KoParagTabulatorsWidget::slotTabValueChanged( double val ) {
01915     if(noSignals) return;
01916     noSignals=true;
01917     //see comment where this slot is connected
01918     m_tabList[lstTabs->currentItem()].ptPos = KoUnit::fromUserValue( val, m_unit );
01919 
01920     lstTabs->changeItem(tabToString(m_tabList[lstTabs->currentItem()]), lstTabs->currentItem());
01921 
01922     sortLists();
01923     noSignals=false;
01924 }
01925 
01926 void KoParagTabulatorsWidget::slotAlignCharChanged( const QString &/*_text*/ ) {
01927     // select align 3 and update data structures.
01928     bgAlign->setButton(3);
01929     m_tabList[lstTabs->currentItem()].alignChar=sAlignChar->text()[0];
01930     m_tabList[lstTabs->currentItem()].type=T_DEC_PNT;
01931 }
01932 
01933 void KoParagTabulatorsWidget::newClicked() {
01934     int selected=lstTabs->currentItem();
01935     KoTabulator newTab;
01936     if(selected < 0) {
01937         newTab.ptPos=0;
01938         newTab.type=T_LEFT;
01939         newTab.filling=TF_BLANK;
01940         newTab.ptWidth=0.5;
01941         m_tabList.append(newTab);
01942         lstTabs->insertItem(tabToString(newTab));
01943         lstTabs->setCurrentItem(0);
01944     } else {
01945         double pos = m_tabList[selected].ptPos;
01946         double add=1.0;
01947         if(m_unit==KoUnit::U_INCH) // inches are 25 times as big as mm, take it easy with adding..
01948             add=0.1;
01949 
01950         pos=pos + KoUnit::fromUserValue( add, m_unit );
01951         if(pos<m_toplimit)
01952         {
01953             newTab.ptPos=pos + KoUnit::fromUserValue( add, m_unit );
01954             newTab.type=m_tabList[selected].type;
01955             newTab.filling=m_tabList[selected].filling;
01956             newTab.ptWidth=m_tabList[selected].ptWidth;
01957             m_tabList.insert(m_tabList.at(selected), newTab);
01958             lstTabs->insertItem( tabToString(newTab), selected);
01959             lstTabs->setCurrentItem(lstTabs->findItem(tabToString(newTab)));
01960             sortLists();
01961         }
01962     }
01963 }
01964 
01965 void KoParagTabulatorsWidget::deleteClicked() {
01966     int selected = lstTabs->currentItem();
01967     if (selected < 0) return;
01968     noSignals=true;
01969     sTabPos->changeValue(0.0);
01970     noSignals=false;
01971     lstTabs->removeItem(selected);
01972     m_tabList.remove(m_tabList[selected]);
01973     if(lstTabs->count() >0) {
01974         lstTabs->setCurrentItem(QMIN(static_cast<unsigned int>(selected), lstTabs->count()-1 ));
01975     } else {
01976         bDeleteAll->setEnabled(false);
01977         bDelete->setEnabled(false);
01978         gPosition->setEnabled(false);
01979         bgAlign->setEnabled(false);
01980         gTabLeader->setEnabled(false);
01981     }
01982 }
01983 
01984 void KoParagTabulatorsWidget::deleteAllClicked()
01985 {
01986     noSignals=true;
01987     sTabPos->changeValue(0.0);
01988     noSignals=false;
01989     lstTabs->clear();
01990     m_tabList.clear();
01991     bDeleteAll->setEnabled(false);
01992     bDelete->setEnabled(false);
01993     gPosition->setEnabled(false);
01994     bgAlign->setEnabled(false);
01995     gTabLeader->setEnabled(false);
01996 }
01997 
01998 void KoParagTabulatorsWidget::setActiveItem(int selected) {
01999     if(noSignals) return;
02000     if(selected < 0) return;
02001     noSignals=true;
02002     KoTabulator *selectedTab = &m_tabList[selected];
02003     switch( selectedTab->type) {
02004         case T_CENTER:
02005             bgAlign->setButton(1); break;
02006         case  T_RIGHT:
02007             bgAlign->setButton(2); break;
02008         case T_DEC_PNT:
02009             bgAlign->setButton(3);
02010         sAlignChar->setText(QString(selectedTab->alignChar));
02011         break;
02012         case T_LEFT:
02013         default:
02014             bgAlign->setButton(0);
02015     }
02016     switch( selectedTab->filling) {
02017         case TF_DOTS:
02018             cFilling->setCurrentItem(1); break;
02019         case TF_LINE:
02020             cFilling->setCurrentItem(2); break;
02021         case TF_DASH:
02022             cFilling->setCurrentItem(3); break;
02023         case TF_DASH_DOT:
02024             cFilling->setCurrentItem(4); break;
02025         case TF_DASH_DOT_DOT:
02026             cFilling->setCurrentItem(5); break;
02027         case TF_BLANK:
02028         default:
02029             cFilling->setCurrentItem(0);
02030     }
02031     eWidth->changeValue( selectedTab->ptWidth );
02032     sTabPos->setValue( KoUnit::toUserValue(selectedTab->ptPos, m_unit));
02033     bDelete->setEnabled(true);
02034     bDeleteAll->setEnabled(true);
02035     gPosition->setEnabled(true);
02036     bgAlign->setEnabled(true);
02037     gTabLeader->setEnabled(true);
02038     noSignals=false;
02039 }
02040 
02041 void KoParagTabulatorsWidget::setCurrentTab( double tabPos ) {
02042     KoTabulatorList::ConstIterator it = m_tabList.begin();
02043     for ( int i = 0; it != m_tabList.end(); ++it, ++i )
02044         if ( (*it).ptPos == tabPos ) {
02045             lstTabs->setCurrentItem(i);
02046             setActiveItem( i );
02047             return;
02048         }
02049     kdWarning() << "KoParagTabulatorsWidget::setCurrentTab: no tab found at pos=" << tabPos << endl;
02050 }
02051 
02052 QString KoParagTabulatorsWidget::tabToString(const KoTabulator &tab) {
02053     return KoUnit::toUserStringValue( tab.ptPos, m_unit);
02054 }
02055 
02056 void KoParagTabulatorsWidget::updateAlign(int selected) {
02057     KoTabulator *selectedTab = &m_tabList[lstTabs->currentItem()];
02058 
02059     switch( selected) {
02060         case 1:
02061             selectedTab->type=T_CENTER; break;
02062         case  2:
02063             selectedTab->type=T_RIGHT; break;
02064         case 3:
02065             selectedTab->type=T_DEC_PNT;
02066         selectedTab->alignChar=sAlignChar->text()[0];
02067         break;
02068         case 0:
02069         default:
02070             selectedTab->type=T_LEFT;
02071     }
02072 }
02073 
02074 void KoParagTabulatorsWidget::updateFilling(int selected) {
02075     KoTabulator *selectedTab = &m_tabList[lstTabs->currentItem()];
02076 
02077     switch( selected) {
02078         case 1:
02079             selectedTab->filling=TF_DOTS; break;
02080         case 2:
02081             selectedTab->filling=TF_LINE; break;
02082         case 3:
02083             selectedTab->filling=TF_DASH; break;
02084         case 4:
02085             selectedTab->filling=TF_DASH_DOT; break;
02086         case 5:
02087             selectedTab->filling=TF_DASH_DOT_DOT; break;
02088     case 0:
02089         default:
02090             selectedTab->filling=TF_BLANK;
02091     }
02092 }
02093 
02094 void KoParagTabulatorsWidget::updateWidth() {
02095     KoTabulator *selectedTab = &m_tabList[lstTabs->currentItem()];
02096     selectedTab->ptWidth = QMAX( 0, eWidth->value() );
02097 }
02098 
02099 void KoParagTabulatorsWidget::sortLists() {
02100 
02101     noSignals=true;
02102     qHeapSort( m_tabList );
02103 
02104     // we could just sort the listView, but to make sure we never have any problems with
02105     // inconsistent lists, just re-add..
02106     QString curValue=lstTabs->currentText();
02107     lstTabs->clear();
02108     KoTabulatorList::ConstIterator it = m_tabList.begin();
02109     for ( ; it != m_tabList.end(); ++it )
02110         lstTabs->insertItem( KoUnit::toUserStringValue( (*it).ptPos, m_unit ) );
02111 
02112     lstTabs->setCurrentItem(lstTabs->findItem(curValue));
02113     noSignals=false;
02114 }
02115 
02116 void KoParagTabulatorsWidget::display( const KoParagLayout &lay ) {
02117     m_tabList.clear();
02118     lstTabs->clear();
02119     m_tabList = lay.tabList();
02120     KoTabulatorList::ConstIterator it = m_tabList.begin();
02121     for ( ; it != m_tabList.end(); ++it )
02122         lstTabs->insertItem( KoUnit::toUserStringValue( (*it).ptPos, m_unit ) );
02123 
02124     if(lstTabs->count() > 0)
02125         lstTabs->setCurrentItem(0);
02126     else {
02127         bDelete->setEnabled(false);
02128         bDeleteAll->setEnabled(false);
02129         gPosition->setEnabled(false);
02130         bgAlign->setEnabled(false);
02131         gTabLeader->setEnabled(false);
02132     }
02133 }
02134 
02135 void KoParagTabulatorsWidget::save( KoParagLayout & lay ) {
02136     lay.setTabList( m_tabList );
02137 }
02138 
02139 QString KoParagTabulatorsWidget::tabName() {
02140     return i18n( "&Tabulators" );
02141 }
02142 
02143 /******************************************************************/
02144 /* Class: KoParagDia                                              */
02145 /******************************************************************/
02146 KoParagDia::KoParagDia( QWidget* parent, const char* name,
02147                         int flags, KoUnit::Unit unit, double _frameWidth, bool breakLine, bool disableAll )
02148     : KDialogBase(Tabbed, QString::null, Ok | Cancel | User1 | Apply, Ok, parent, name, true )
02149 {
02150     m_decorationsWidget = 0;
02151     m_flags = flags;
02152     setButtonText( KDialogBase::User1, i18n("Reset") );
02153 
02154     if ( m_flags & PD_SPACING )
02155     {
02156         QVBox * page = addVBoxPage( i18n( "Indent && S&pacing" ) );
02157         m_indentSpacingWidget = new KoIndentSpacingWidget( unit,_frameWidth,page, "indent-spacing" );
02158         m_indentSpacingWidget->layout()->setMargin(0);
02159     }
02160     if ( m_flags & PD_ALIGN )
02161     {
02162         QVBox * page = addVBoxPage( i18n( "General &Layout" ) );
02163         m_alignWidget = new KoParagAlignWidget( breakLine, page, "align" );
02164         m_alignWidget->layout()->setMargin(0);
02165     }
02166     if ( m_flags & PD_DECORATION )
02167     {
02168         QVBox * page = addVBoxPage( i18n( "D&ecorations" ) );
02169         m_decorationsWidget = new KoParagDecorationWidget( page, "decorations");
02170         m_decorationsWidget->layout()->setMargin(0);
02171     }
02172     if ( m_flags & PD_NUMBERING )
02173     {
02174         QVBox * page = addVBoxPage( i18n( "B&ullets/Numbers" ) );
02175         m_counterWidget = new KoParagCounterWidget( disableAll , page, "numbers" );
02176         m_counterWidget->layout()->setMargin(0);
02177     }
02178     if ( m_flags & PD_TABS )
02179     {
02180         QVBox * page = addVBoxPage( i18n( "&Tabulators" ) );
02181         m_tabulatorsWidget = new KoParagTabulatorsWidget( unit,_frameWidth, page, "tabs");
02182         m_tabulatorsWidget->layout()->setMargin(0);
02183     }
02184 
02185     connect( this, SIGNAL( user1Clicked() ), this, SLOT(slotReset()));
02186     setInitialSize( QSize(630, 500) );
02187 }
02188 
02189 KoParagDia::~KoParagDia()
02190 {
02191 }
02192 
02193 void KoParagDia::slotApply()
02194 {
02195     emit applyParagStyle();
02196 }
02197 
02198 void KoParagDia::slotOk()
02199 {
02200     slotApply();
02201     KDialogBase::slotOk();
02202 }
02203 
02204 void KoParagDia::setCurrentPage( int page )
02205 {
02206     switch( page )
02207     {
02208     case PD_SPACING:
02209         showPage( pageIndex( m_indentSpacingWidget->parentWidget() ) );
02210         break;
02211     case PD_ALIGN:
02212         showPage( pageIndex( m_alignWidget->parentWidget() ) );
02213         break;
02214     case PD_DECORATION:
02215         showPage( pageIndex( m_decorationsWidget->parentWidget() ) );
02216         break;
02217     case PD_NUMBERING:
02218         showPage( pageIndex( m_counterWidget->parentWidget() ) );
02219         break;
02220     case PD_TABS:
02221         showPage( pageIndex( m_tabulatorsWidget->parentWidget() ) );
02222         break;
02223     default:
02224         break;
02225     }
02226 }
02227 
02228 void KoParagDia::setParagLayout( const KoParagLayout & lay )
02229 {
02230     m_indentSpacingWidget->display( lay );
02231     m_alignWidget->display( lay );
02232     m_decorationsWidget->display( lay );
02233     m_counterWidget->display( lay );
02234     m_tabulatorsWidget->display( lay );
02235     oldLayout = lay;
02236 }
02237 
02238 void KoParagDia::slotReset()
02239 {
02240     if( m_indentSpacingWidget )
02241         m_indentSpacingWidget->display( oldLayout );
02242     if( m_alignWidget )
02243         m_alignWidget->display( oldLayout );
02244     if ( m_decorationsWidget )
02245         m_decorationsWidget->display( oldLayout );
02246     if( m_counterWidget )
02247         m_counterWidget->display( oldLayout );
02248     if( m_tabulatorsWidget )
02249         m_tabulatorsWidget->display( oldLayout );
02250 }
02251 
02252 bool KoParagDia::isCounterChanged() const
02253 {
02254     if ( oldLayout.counter ) // We had a counter
02255         return ! ( *oldLayout.counter == counter() );
02256     else // We had no counter -> changed if we have one now
02257         return counter().numbering() != KoParagCounter::NUM_NONE;
02258 }
02259 
02260 int KoParagDia::changedFlags() const
02261 {
02262     return paragLayout().compare( oldLayout );
02263 }
02264 
02265 KoParagLayout KoParagDia::paragLayout() const
02266 {
02267     KoParagLayout newLayout;
02268     newLayout.setLineSpacingValue( lineSpacing() );
02269     newLayout.lineSpacingType = lineSpacingType();
02270     newLayout.setTabList( tabListTabulator() );
02271     newLayout.alignment = align();
02272     newLayout.margins[QStyleSheetItem::MarginFirstLine] = firstLineIndent();
02273     newLayout.margins[QStyleSheetItem::MarginLeft] = leftIndent();
02274     newLayout.margins[QStyleSheetItem::MarginRight] = rightIndent();
02275     newLayout.margins[QStyleSheetItem::MarginTop] = spaceBeforeParag();
02276     newLayout.margins[QStyleSheetItem::MarginBottom] = spaceAfterParag();
02277     newLayout.pageBreaking = pageBreaking();
02278     newLayout.leftBorder = leftBorder();
02279     newLayout.rightBorder = rightBorder();
02280     newLayout.topBorder = topBorder();
02281     newLayout.bottomBorder = bottomBorder();
02282     newLayout.joinBorder = joinBorder();
02283     newLayout.backgroundColor = backgroundColor();
02284     newLayout.counter = new KoParagCounter( counter() );
02285     return newLayout;
02286 }
02287 
02288 #include "KoParagDia.moc"
02289 #include "KoParagDia_p.moc"
KDE Home | KDE Accessibility Home | Description of Access Keys