texteditor.cpp
author insilmaril
Tue Apr 11 14:34:14 2006 +0000 (2006-04-11)
changeset 295 f6fecd518011
parent 189 ca30b203fb73
child 315 866f79dfa6d7
permissions -rw-r--r--
added basic history window
     1 #include "texteditor.h"
     2 
     3 #include <qcanvas.h>
     4 #include <qstatusbar.h>
     5 #include <qmessagebox.h>
     6 #include <qaction.h>
     7 #include <qapplication.h>
     8 #include <qpainter.h>
     9 #include <qprinter.h>
    10 #include <qfile.h>
    11 #include <qfiledialog.h>
    12 #include <qtoolbar.h>
    13 #include <qpopupmenu.h>
    14 #include <qmenubar.h>
    15 #include <qtextedit.h>
    16 #include <qaccel.h>
    17 #include <qtextstream.h>
    18 #include <qpaintdevicemetrics.h>
    19 #include <qsettings.h>
    20 #include <qfontdialog.h>
    21 #include <qmessagebox.h>
    22 #include <qcolordialog.h>
    23 #include <qregexp.h>
    24 #include <qlineedit.h>
    25 #include <qsimplerichtext.h>
    26 
    27 #include <iostream>
    28 #include <cstdlib>
    29 #include <typeinfo>
    30 
    31 #include "noteobj.h"
    32 #include "version.h"
    33 
    34 extern QCanvas* actCanvas;
    35 extern int statusbarTime;
    36 extern QSettings settings;
    37 
    38 extern QAction *actionViewToggleNoteEditor;
    39 
    40 extern QString iconPath;
    41 
    42 using namespace std;
    43 
    44 
    45 ///////////////////////////////////////////////////////////////////////
    46 ///////////////////////////////////////////////////////////////////////
    47 
    48 
    49 TextEditor::TextEditor()
    50 {
    51     printer = new QPrinter( QPrinter::HighResolution );
    52 	printer->setPrinterName (settings.readEntry("/vym/mainwindow/printerName",printer->printerName()));
    53 
    54 	// Editor (use MyTextEdit to wrap verticalAlignmentChanged to 
    55 	//         int argument. see header file)
    56     e = new MyTextEdit( this, "editor" );
    57     e->setFocus();
    58 	e->setTextFormat(RichText);		// default
    59 	e->setTabStopWidth (20);		// unit is pixel
    60 	e->setColor (black);
    61 	connect (e, SIGNAL( textChanged() ), this, SLOT( editorChanged() ) );
    62     setCentralWidget( e );
    63     statusBar()->message( "Ready", statusbarTime);
    64 	setCaption(__VYM " - " +tr ("Note Editor"));
    65 
    66 	// Toolbars
    67 	setupFileActions();
    68 	setupEditActions();
    69 	setupFormatActions();
    70 	setupSettingsActions();
    71 	
    72 	// Various states
    73 	emptyPaper   = QBrush(gray);
    74 	filledPaper  = QBrush(white);
    75 	inactivePaper= QBrush(black);
    76 	setInactive();
    77 
    78 	// Load Settings
    79 	resize (settings.readNumEntry( "/vym/noteeditor/geometry/width", 450),
    80 	        settings.readNumEntry( "/vym/noteeditor/geometry/height",600));
    81 	move   (settings.readNumEntry( "/vym/noteeditor/geometry/posX", 150),
    82 	        settings.readNumEntry( "/vym/noteeditor/geometry/posY",  50));
    83 	
    84 	if (settings.readEntry( "/vym/noteeditor/showWithMain","yes") =="yes")
    85 		setShowWithMain(true);
    86 	else	
    87 		setShowWithMain(false);
    88 
    89 	varFont.fromString( settings.readEntry 
    90 		("/vym/noteeditor/fonts/varFont",
    91 		"Nimbus Sans l,14,-1,5,48,0,0,0,0,0") 
    92 	);
    93 	fixedFont.fromString (settings.readEntry (
    94 		"/vym/noteeditor/fonts/fixedFont",
    95 		"Courier,14,-1,5,48,0,0,0,1,0") 
    96 	);
    97 	QString s=settings.readEntry ("/vym/noteeditor/fonts/fonthintDefault","variable");
    98 	if (s == "fixed")
    99 	{	
   100 		actionSettingsFonthintDefault->setOn (true);
   101 		e->setCurrentFont (fixedFont);
   102 	} else	
   103 	{
   104 		actionSettingsFonthintDefault->setOn (false);
   105 		e->setCurrentFont (varFont);
   106 	}	
   107 	filenameHint="";
   108 
   109 	// Save settings in vymrc
   110 	settings.writeEntry("/vym/mainwindow/printerName",printer->printerName());
   111 }
   112 
   113 
   114 TextEditor::~TextEditor()
   115 {
   116     if (printer) delete printer;
   117 	// Save Settings
   118 	settings.writeEntry( "/vym/noteeditor/geometry/width", width() );
   119 	settings.writeEntry( "/vym/noteeditor/geometry/height", height() );
   120 	settings.writeEntry( "/vym/noteeditor/geometry/posX", pos().x() );
   121 	settings.writeEntry( "/vym/noteeditor/geometry/posY", pos().y() );
   122 	
   123 	if (showWithMain())
   124 		settings.writeEntry( "/vym/noteeditor/showWithMain","yes");
   125 	else	
   126 		settings.writeEntry( "/vym/noteeditor/showWithMain","no");
   127 
   128 	QString s;
   129 	if (actionSettingsFonthintDefault->isOn() )
   130 		s="fixed";
   131 	else	
   132 		s="variable";
   133 	settings.writeEntry( "/vym/noteeditor/fonts/fonthintDefault",s );
   134 	settings.writeEntry ("/vym/noteeditor/fonts/varFont",
   135 		varFont.toString() );
   136 	settings.writeEntry ("/vym/noteeditor/fonts/fixedFont",
   137 		fixedFont.toString() );
   138 }
   139 
   140 bool TextEditor::isEmpty()
   141 {
   142 	if (e->text().length())
   143 		return false;
   144 	else
   145 		return true;
   146 }
   147 
   148 void TextEditor::setShowWithMain(bool v)
   149 {
   150 	showwithmain=v;
   151 }
   152 
   153 bool TextEditor::showWithMain()
   154 {
   155 	return showwithmain;
   156 }
   157 
   158 void TextEditor::setFontHint (const QString &fh)
   159 {
   160 	if (fh=="fixed")
   161 		actionFormatUseFixedFont->setOn (true);
   162 	else
   163 		actionFormatUseFixedFont->setOn (false);
   164 }
   165 
   166 
   167 QString TextEditor::getFontHint()
   168 {
   169 	if (actionFormatUseFixedFont->isOn())
   170 		return "fixed";
   171 	else	
   172 		return "var";
   173 }
   174 
   175 QString TextEditor::getFontHintDefault()
   176 {
   177 	if (actionSettingsFonthintDefault->isOn())
   178 		return "fixed";
   179 	else	
   180 		return "var";
   181 }
   182 
   183 void TextEditor::setFilename(const QString &fn)
   184 {
   185 	if (state==filledEditor)
   186 		if (fn.isEmpty() )
   187 		{
   188 			filename="";
   189 			statusBar()->message( "No filename available for this note.", statusbarTime );
   190 		}	
   191 		else
   192 		{
   193 			filename=fn;
   194 			statusBar()->message( QString( "Current filename is %1" ).arg( filename ), statusbarTime );
   195 		}	
   196 }
   197 
   198 QString TextEditor::getFilename()
   199 {
   200 	return filename;
   201 }
   202 
   203 void TextEditor::setFilenameHint(const QString &fnh)
   204 {
   205 	filenameHint=fnh;
   206 }
   207 
   208 QString TextEditor::getFilenameHint()
   209 {
   210 	return filenameHint;
   211 }
   212 
   213 bool TextEditor::findText(const QString &t, const bool &cs)
   214 {
   215 	bool wo=false;	// word matches
   216 	if (e->find (t, cs, wo, true, 0, 0 ))
   217 		return true;
   218 	else	
   219 		return false;
   220 }
   221 
   222 void TextEditor::setupFileActions()
   223 {
   224     QToolBar *tb = new QToolBar( this );
   225     tb->setLabel( "File Actions" );
   226     QPopupMenu *menu = new QPopupMenu( this );
   227     menuBar()->insertItem( tr( "&File" ), menu );
   228 
   229     QAction *a;
   230     a = new QAction( tr( "Import" ), QPixmap( iconPath+"fileopen.png"), tr( "&Import..." ), CTRL + Key_O, this, "fileImport" );
   231     connect( a, SIGNAL( activated() ), this, SLOT( textLoad() ) );
   232 	a->setEnabled(false);
   233     a->addTo( tb );
   234     a->addTo( menu );
   235 	actionFileLoad=a;
   236 
   237     menu->insertSeparator();
   238     a = new QAction( tr( "Export Note (HTML)" ), QPixmap(iconPath+"filesave.png" ), tr( "&Export..." ), CTRL + Key_S, this, "fileSave" );
   239     connect( a, SIGNAL( activated() ), this, SLOT( textSave() ) );
   240     a->addTo( tb );
   241     a->addTo( menu );
   242 	actionFileSave=a;
   243 	
   244     a = new QAction( tr( "Export Note As (HTML) " ), QPixmap(), tr( "Export &As... (HTML)" ), 0, this, "exportHTML" );
   245     connect( a, SIGNAL( activated() ), this, SLOT( textSaveAs() ) );
   246     a->addTo( menu );
   247 	actionFileSaveAs=a;
   248 
   249     a = new QAction( tr( "Export Note As (ASCII) " ), QPixmap(), tr( "Export &As...(ASCII)" ), ALT + Key_X, this, "exportASCII" );
   250     connect( a, SIGNAL( activated() ), this, SLOT( textExportAsASCII() ) );
   251     a->addTo( menu );
   252 	actionFileSaveAs=a;
   253 
   254     menu->insertSeparator();
   255     a = new QAction( tr( "Print Note" ), QPixmap(iconPath+"fileprint.png" ), tr( "&Print..." ), CTRL + Key_P, this, "filePrint" );
   256     connect( a, SIGNAL( activated() ), this, SLOT( textPrint() ) );
   257     a->addTo( tb );
   258     a->addTo( menu );
   259 	actionFilePrint=a;
   260 }
   261 
   262 void TextEditor::setupEditActions()
   263 {
   264     QToolBar *tb = new QToolBar( this );
   265     tb->setLabel( "Edit Actions" );
   266     QPopupMenu *menu = new QPopupMenu( this );
   267     menuBar()->insertItem( tr( "&Edit" ), menu );
   268 
   269     QAction *a;
   270     a = new QAction( tr( "Undo" ), QPixmap(iconPath+"undo.png"), tr( "&Undo" ), CTRL + Key_Z, this, "undoEvent" );
   271     connect( a, SIGNAL( activated() ), e, SLOT( undo() ) );
   272     a->addTo( menu );
   273     a->addTo( tb);
   274 	actionEditUndo=a;
   275 	
   276     a = new QAction( tr( "Redo" ), QPixmap(iconPath+"redo.png" ), tr( "&Redo" ), CTRL + Key_Y, this, "editRedo" ); 
   277     connect( a, SIGNAL( activated() ), e, SLOT( redo() ) );
   278     a->addTo( tb );
   279     a->addTo( menu );
   280 	actionEditRedo=a;
   281 
   282     menu->insertSeparator();
   283     a = new QAction( tr( "Select and copy all" ), QPixmap(), tr( "Select and copy &all" ), CTRL + Key_A, this, "editcopyall" ); 
   284     connect( a, SIGNAL( activated() ), this, SLOT( editCopyAll() ) );
   285     a->addTo( menu );
   286 
   287     menu->insertSeparator();
   288     a = new QAction( tr( "Copy" ), QPixmap(iconPath+"editcopy.png" ), tr( "&Copy" ), CTRL + Key_C, this, "editCopy" );
   289     connect( a, SIGNAL( activated() ), e, SLOT( copy() ) );
   290     a->addTo( tb );
   291     a->addTo( menu );
   292 	actionEditCopy=a;
   293 	
   294     a = new QAction( tr( "Cut" ), QPixmap(iconPath+"editcut.png" ), tr( "Cu&t" ), CTRL + Key_X, this, "editCut" );
   295     connect( a, SIGNAL( activated() ), e, SLOT( cut() ) );
   296     a->addTo( tb );
   297     a->addTo( menu );
   298 	actionEditCut=a;
   299 
   300     a = new QAction( tr( "Paste" ), QPixmap(iconPath+"editpaste.png" ), tr( "&Paste" ), CTRL + Key_V, this, "editPaste" );
   301     connect( a, SIGNAL( activated() ), e, SLOT( paste() ) );
   302     a->addTo( tb );
   303     a->addTo( menu );
   304 	actionEditPaste=a;
   305 	
   306     a = new QAction( tr( "Delete all" ), QPixmap( iconPath+"edittrash.png"), tr( "&Delete All" ), 0, this, "editDeleteAll" );
   307     connect( a, SIGNAL( activated() ), e, SLOT( clear() ) );
   308     a->addTo( tb );
   309     a->addTo( menu );
   310 	actionEditDeleteAll=a;
   311 
   312 	a = new QAction( tr( "Convert paragraphs to linebreaks" ), QPixmap(), tr( "&Convert Paragraphs" ), ALT + Key_P, this, "editConvertPar" );
   313     connect( a, SIGNAL( activated() ), this, SLOT( textConvertPar() ) );
   314     a->addTo( menu );
   315 	actionEditConvertPar=a;
   316 
   317 	a = new QAction( tr( "Join all lines of a paragraph" ), QPixmap(), tr( "&Join lines" ), ALT + Key_J, this, "editJoinLines" );
   318     connect( a, SIGNAL( activated() ), this, SLOT( textJoinLines() ) );
   319     a->addTo( menu );
   320 	actionEditJoinLines=a;
   321 }
   322 
   323 void TextEditor::setupFormatActions()
   324 {
   325     QToolBar *tb = new QToolBar( this );
   326     tb->setLabel( "Format Actions" );
   327     QPopupMenu *menu = new QPopupMenu( this );
   328     menuBar()->insertItem( tr( "&Format" ), menu );
   329 
   330     QAction *a;
   331 
   332     a = new QAction( tr( "Toggle font hint for the whole text" ), QPixmap(iconPath+"formatfixedfont.png"), tr( "&Font hint" ), ALT + Key_I, this, "fontHint" );
   333 	a->setToggleAction (true);
   334 	a->setOn (settings.readBoolEntry ("/vym/noteeditor/fonts/useFixedByDefault",false) );
   335     connect( a, SIGNAL( activated() ), this, SLOT( toggleFonthint() ) );
   336     a->addTo( menu );
   337     a->addTo( tb );
   338 	actionFormatUseFixedFont=a;
   339 
   340 	menu->insertSeparator();
   341 
   342     comboFont = new QComboBox( true, tb );
   343     QFontDatabase db;
   344     comboFont->insertStringList( db.families() );
   345     connect( comboFont, SIGNAL( activated( const QString & ) ),
   346 	     this, SLOT( textFamily( const QString & ) ) );
   347     comboFont->lineEdit()->setText( QApplication::font().family() );
   348 
   349     comboSize = new QComboBox( true, tb );
   350     QValueList<int> sizes = db.standardSizes();
   351     QValueList<int>::Iterator it = sizes.begin();
   352     for ( ; it != sizes.end(); ++it )
   353 	comboSize->insertItem( QString::number( *it ) );
   354     connect( comboSize, SIGNAL( activated( const QString & ) ),
   355 	     this, SLOT( textSize( const QString & ) ) );
   356     comboSize->lineEdit()->setText( QString::number( QApplication::font().pointSize() ) );
   357 
   358     menu->insertSeparator();
   359 
   360     QPixmap pix( 16, 16 );
   361     pix.fill( e->color());
   362     actionTextColor = new QAction( pix, tr( "&Color..." ), 0, this, "textColor" );
   363     connect( actionTextColor, SIGNAL( activated() ), this, SLOT( textColor() ) );
   364     actionTextColor->addTo( tb );
   365     actionTextColor->addTo( menu );
   366 
   367     actionTextBold = new QAction( QPixmap (iconPath+"text_bold.png"), tr( "&Bold" ), CTRL + Key_B, this, "textBold" );
   368     connect( actionTextBold, SIGNAL( activated() ), this, SLOT( textBold() ) );
   369     actionTextBold->addTo( tb );
   370     actionTextBold->addTo( menu );
   371     actionTextBold->setToggleAction( true );
   372     actionTextItalic = new QAction( QPixmap(iconPath+"text_italic.png"), tr( "&Italic" ), CTRL + Key_I, this, "textItalic" );
   373     connect( actionTextItalic, SIGNAL( activated() ), this, SLOT( textItalic() ) );
   374     actionTextItalic->addTo( tb );
   375     actionTextItalic->addTo( menu );
   376     actionTextItalic->setToggleAction( true );
   377     actionTextUnderline = new QAction( QPixmap (iconPath+"text_italic.png"), tr( "&Underline" ), CTRL + Key_U, this, "textUnderline" );
   378     connect( actionTextUnderline, SIGNAL( activated() ), this, SLOT( textUnderline() ) );
   379     actionTextUnderline->addTo( tb );
   380     actionTextUnderline->addTo( menu );
   381     actionTextUnderline->setToggleAction( true );
   382     menu->insertSeparator();
   383 
   384     QActionGroup *grp = new QActionGroup( this );
   385     connect( grp, SIGNAL( selected( QAction* ) ), this, SLOT( textAlign( QAction* ) ) );
   386 
   387     actionAlignLeft = new QAction( QPixmap (iconPath+"text_left.png"), tr( "&Left" ), CTRL + Key_L, grp, "textLeft" );
   388     actionAlignLeft->setToggleAction( true );
   389     actionAlignCenter = new QAction( QPixmap (iconPath+"text_center.png"), tr( "C&enter" ), CTRL + Key_E, grp, "textCenter" );
   390     actionAlignCenter->setToggleAction( true );
   391     actionAlignRight = new QAction( QPixmap (iconPath+"text_right.png" ), tr( "&Right" ), CTRL + Key_R, grp, "textRight" );
   392     actionAlignRight->setToggleAction( true );
   393     actionAlignJustify = new QAction( QPixmap ( iconPath+"text_block.png"), tr( "&Justify" ), CTRL + Key_J, grp, "textjustify" );
   394     actionAlignJustify->setToggleAction( true );
   395 
   396     grp->addTo( tb );
   397     grp->addTo( menu );
   398 
   399     QActionGroup *grp2 = new QActionGroup( this );
   400     grp2->setExclusive(false);
   401     actionAlignSubScript = new QAction( QPixmap (iconPath+"text_sub.png"), tr( "Subs&cript" ), CTRL + SHIFT + Key_B, grp2, "textSubscript" );
   402 
   403     actionAlignSubScript->setToggleAction( true );
   404     connect(actionAlignSubScript, SIGNAL(activated()), this, SLOT(textVAlign()));
   405 
   406     actionAlignSuperScript = new QAction( QPixmap (iconPath+"text_super.png"), tr( "Su&perscript" ), CTRL + SHIFT + Key_P, grp2, "textSuperscript" );
   407 
   408     actionAlignSuperScript->setToggleAction( true );
   409     connect(actionAlignSuperScript, SIGNAL(activated()), this, SLOT(textVAlign()));
   410 
   411     menu->insertSeparator();
   412     
   413     grp2->addTo(tb);
   414     grp2->addTo(menu);
   415 
   416     connect( e, SIGNAL( currentFontChanged( const QFont & ) ),
   417 	     this, SLOT( fontChanged( const QFont & ) ) );
   418     connect( e, SIGNAL( currentColorChanged( const QColor & ) ),
   419 	     this, SLOT( colorChanged( const QColor & ) ) );
   420     connect( e, SIGNAL( currentAlignmentChanged( int ) ),
   421 	     this, SLOT( alignmentChanged( int ) ) );
   422     connect( e, SIGNAL( currentVerticalAlignmentChanged(int)),
   423 	     this, SLOT( verticalAlignmentChanged(int)));
   424 
   425 }
   426 
   427 void TextEditor::setupSettingsActions()
   428 {
   429     QPopupMenu *menu = new QPopupMenu( this );
   430     menuBar()->insertItem( tr( "&Settings" ), menu );
   431 
   432     QAction *a;
   433     a = new QAction( tr( "Set fixed font" ), QPixmap(), tr( "Set &fixed font" ), 0, this, "setFixedFont" );
   434     connect( a, SIGNAL( activated() ), this, SLOT( setFixedFont() ) );
   435     a->addTo( menu );
   436 	actionSettingsFixedFont=a;
   437 
   438     a = new QAction( tr( "Set variable font" ), QPixmap(), tr( "Set &variable font" ), 0, this, "setvariableFont" );
   439     connect( a, SIGNAL( activated() ), this, SLOT( setVarFont() ) );
   440     a->addTo( menu );
   441 	actionSettingsVarFont=a;
   442 
   443     a = new QAction( tr( "Used fixed font by default" ), QPixmap(), tr( "&fixed font is default" ), 0, this, "fonthintDefault" );
   444 	a->setToggleAction (true);
   445 	// set state later in constructor...
   446     a->addTo( menu );
   447 	actionSettingsFonthintDefault=a;
   448 }
   449 
   450 void TextEditor::textLoad()
   451 {
   452 	if (state!=inactiveEditor)
   453 	{
   454 		if (e->length()) 
   455 		{
   456 			QMessageBox mb( __VYM " - " +tr("Note Editor"),
   457 				"Loading will overwrite the existing note",
   458 				QMessageBox::Warning,
   459 				QMessageBox::Yes | QMessageBox::Default,
   460 				QMessageBox::Cancel,
   461 				0 );
   462 			mb.setButtonText( QMessageBox::Yes, "Load note" );
   463 			switch( mb.exec() ) {
   464 				case QMessageBox::Cancel:
   465 					return;
   466 					break;
   467 			}
   468 		} 
   469 		// Load note
   470 		QFileDialog *fd=new QFileDialog( this);
   471 		fd->addFilter ("ASCII texts (*.txt)");
   472 		fd->addFilter ("VYM notes (*.html)");
   473 		fd->show();
   474 		QString fn;
   475 		if ( fd->exec() == QDialog::Accepted )
   476 			fn = fd->selectedFile();
   477 
   478 		if ( !fn.isEmpty() )
   479 		{
   480 			QFile f( fn );
   481 			if ( !f.open( IO_ReadOnly ) )
   482 			return;
   483 
   484 			QTextStream ts( &f );
   485 			setText( ts.read() );
   486 			editorChanged();
   487 		}
   488 	}
   489 }
   490 
   491 void TextEditor::closeEvent( QCloseEvent* ce )
   492 {
   493     ce->accept();	// TextEditor can be reopened with show()
   494     actionViewToggleNoteEditor->setOn (false);
   495     showwithmain=false;
   496     return;
   497 }
   498 
   499 QString TextEditor::getText()
   500 {
   501 	return e->text();
   502 }
   503 
   504 void TextEditor::editorChanged()
   505 {
   506 	if (isEmpty())
   507 		state=emptyEditor;
   508 	else
   509 		state=filledEditor;
   510 
   511 		if (state==emptyEditor)
   512 			e->setPaper (emptyPaper);
   513 		else
   514 			e->setPaper (filledPaper);
   515 	// SLOT is LinkableMapObj, which will update systemFlag
   516 	emit (textHasChanged() );
   517 }
   518 
   519 
   520 void TextEditor::setText(QString t)
   521 {
   522 	if ( !QStyleSheet::mightBeRichText( t ) )
   523 		t = QStyleSheet::convertFromPlainText( t, QStyleSheetItem::WhiteSpaceNormal );
   524 	e->setReadOnly(false);
   525 	e->setText(t);
   526 //	editorChanged();	//not called automagically  FIXME or is it?
   527 
   528 	enableActions();
   529 }
   530 
   531 void TextEditor::setInactive()
   532 {
   533 	state=inactiveEditor;
   534 	setText("");
   535 	e->setPaper (inactivePaper);
   536 	e->setReadOnly (true);
   537 
   538 	disableActions();
   539 }
   540 
   541 void TextEditor::editCopyAll()
   542 {
   543 	e->selectAll();
   544 	e->copy();
   545 }
   546 
   547 void TextEditor::textSaveAs()
   548 {
   549     QString fn = QFileDialog::getSaveFileName( QString::null, "VYM Note (HTML) (*.html);;All files (*)",
   550 					       this,"export note dialog",tr("Export Note to single file") );
   551 
   552     if ( !fn.isEmpty() ) 
   553 	{
   554 		QFile file (fn);
   555 		if (file.exists())
   556 		{
   557 			QMessageBox mb( __VYM,
   558 				tr("The file ") + fn + 
   559 				tr(" exists already. "
   560 				"Do you want to overwrite it?"),
   561 			QMessageBox::Warning,
   562 			QMessageBox::Yes | QMessageBox::Default,
   563 			QMessageBox::Cancel | QMessageBox::Escape,
   564 			QMessageBox::NoButton );
   565 			mb.setButtonText( QMessageBox::Yes, tr("Overwrite") );
   566 			mb.setButtonText( QMessageBox::No, tr("Cancel"));
   567 			switch( mb.exec() ) {
   568 				case QMessageBox::Yes:
   569 					// save 
   570 					filename = fn;
   571 					textSave();
   572 					return;
   573 				case QMessageBox::Cancel:
   574 					// do nothing
   575 					break;
   576 			}
   577 		} else
   578 		{
   579 			filename = fn;
   580 			textSave();
   581 			return;
   582 		}			
   583     }
   584 	statusBar()->message(tr( "Couldn't export note ") + fn, statusbarTime );
   585 }
   586 
   587 
   588 void TextEditor::textSave()
   589 {
   590     if ( filename.isEmpty() ) 
   591 	{
   592 		textSaveAs();
   593 		return;
   594     }
   595 
   596     QString text = e->text();
   597     QFile f( filename );
   598     if ( !f.open( IO_WriteOnly ) ) 
   599 	{
   600 		statusBar()->message( QString("Could not write to %1").arg(filename),
   601 					  statusbarTime );
   602 		return;
   603     }
   604 
   605     QTextStream t( &f );
   606     t << text;
   607     f.close();
   608 
   609     e->setModified( FALSE );
   610 
   611     statusBar()->message( QString( "Note exported as %1" ).arg( filename ), statusbarTime );
   612 }
   613 
   614 void TextEditor::textConvertPar()
   615 {
   616 	// In X11 a copy&paste generates paragraphs, 
   617 	// which is not always wanted
   618 	// This function replaces paragraphs by linebreaks.
   619 	int parFrom, parTo, indFrom, indTo;
   620 	e->getSelection (&parFrom,&indFrom,&parTo,&indTo);
   621 	QString t;
   622 	if (parFrom>-1)
   623 		t=e->selectedText();
   624 	else
   625 		t=e->text();
   626 
   627 	QRegExp re("<p.*>");
   628 	re.setMinimal(true);
   629 	t.replace (re,"");
   630 	t.replace ("</p>","<br />");
   631 	if (parFrom>-1)
   632 	{
   633 		e->setCursorPosition (parFrom,indFrom);
   634 		e->cut();
   635 		// Tried to simply insert the changed text with
   636 		// e->insert (t,(uint)(QTextEdit::RemoveSelected));
   637 		// but then the html would be quoted. So I use the ugly
   638 		// way: insert a marker, replace it in whole text of QTextEdit
   639 		QString marker="R3PlAcEMeL4teR!";
   640 		e->insert (marker);
   641 		e->setText (e->text().replace(marker,t));
   642 	} else
   643 		e->setText(t);
   644 }
   645 
   646 void TextEditor::textJoinLines()
   647 {
   648 	int parFrom, parTo, indFrom, indTo;
   649 	e->getSelection (&parFrom,&indFrom,&parTo,&indTo);
   650 	QString t;
   651 	if (parFrom>-1)
   652 		t=e->selectedText();
   653 	else
   654 		t=e->text();
   655 	// In addition to textConvertPar it is sometimes
   656 	// useful to join all lines of a paragraph
   657 	QRegExp re("</p>\n+<p>(?!</p>)");
   658 	re.setMinimal(true);
   659 	t.replace (re," ");
   660 
   661 	// Above we may have introduced new " " at beginning of a
   662 	// paragraph - remove it.
   663 	re.setPattern("<p> ");
   664 	t.replace (re,"<p>");
   665 	if (parFrom>-1)
   666 	{
   667 		e->setCursorPosition (parFrom,indFrom);
   668 		e->cut();
   669 		// Tried to simply insert the changed text with
   670 		// e->insert (t,(uint)(QTextEdit::RemoveSelected));
   671 		// but then the html would be quoted. So I use the ugly
   672 		// way: insert a marker, replace it in whole text of QTextEdit
   673 		QString marker="R3PlAcEMeL4teR!";
   674 		e->insert (marker);
   675 		e->setText (e->text().replace(marker,t));
   676 	} else
   677 		e->setText(t);
   678 }
   679 
   680 void TextEditor::textExportAsASCII()
   681 {
   682 	QString text = NoteObj (e->text()).getNoteASCII();
   683 	QString fn,s;
   684 	if (!filenameHint.isEmpty())
   685 	{
   686 		if (!filenameHint.contains (".txt"))
   687 			s=filenameHint+".txt";
   688 		else	
   689 			s=filenameHint;
   690 	} else	
   691 		s=QString::null;
   692 	fn = QFileDialog::getSaveFileName( s, "VYM Note (ASCII) (*.txt);;All files (*)", this,"export note dialog",tr("Export Note to single file (ASCII)") );
   693 	int ret=-1;
   694 
   695     if ( !fn.isEmpty() ) 
   696 	{
   697 		QFile file (fn);
   698 		if (file.exists())
   699 		{
   700 			QMessageBox mb( "VYM",
   701 				tr("The file ") + fn + 
   702 				tr(" exists already. "
   703 				"Do you want to overwrite it?"),
   704 			QMessageBox::Warning,
   705 			QMessageBox::Yes | QMessageBox::Default,
   706 			QMessageBox::Cancel | QMessageBox::Escape,
   707 			QMessageBox::NoButton );
   708 			mb.setButtonText( QMessageBox::Yes, tr("Overwrite") );
   709 			mb.setButtonText( QMessageBox::No, tr("Cancel"));
   710 			ret=mb.exec();
   711 		}	
   712 		if (ret==QMessageBox::Cancel)
   713 			return;
   714 			
   715 		// save 
   716 		if ( !file.open( IO_WriteOnly ) ) 
   717 			statusBar()->message( QString("Could not write to %1").arg(filename),
   718 						  statusbarTime );
   719 		else
   720 		{
   721 			QTextStream t( &file );
   722 			t << text;
   723 			file.close();
   724 
   725 			statusBar()->message( QString( "Note exported as %1" ).arg( fn ), statusbarTime );
   726 		}
   727     }
   728 }
   729 
   730 
   731 void TextEditor::textPrint()
   732 {
   733     printer->setFullPage(TRUE);
   734     if ( printer->setup( this ) ) 
   735 	{
   736 		QPainter p( printer );
   737 		// Check that there is a valid device to print to.
   738 		if ( !p.device() ) return;
   739 		QPaintDeviceMetrics metrics( p.device() );
   740 		int dpiy = metrics.logicalDpiY();
   741 		int margin = (int) ( (2/2.54)*dpiy ); // 2 cm margins
   742 		QRect body( margin, margin, metrics.width() - 2*margin, metrics.height() - 2*margin );
   743 		QFont font( e->currentFont() );
   744 		font.setPointSize( 10 ); // we define 10pt to be a nice base size for printing
   745 
   746 		QSimpleRichText richText( e->text(), font,
   747 					  e->context(),
   748 					  e->styleSheet(),
   749 					  e->mimeSourceFactory(),
   750 					  body.height() );
   751 		richText.setWidth( &p, body.width() );
   752 		QRect view( body );
   753 		int page = 1;
   754 		do 
   755 		{
   756 			richText.draw( &p, body.left(), body.top(), view, colorGroup() );
   757 			view.moveBy( 0, body.height() );
   758 			p.translate( 0 , -body.height() );
   759 			p.setFont( font );
   760 			p.drawText( view.right() - p.fontMetrics().width( QString::number( page ) ),
   761 				view.bottom() + p.fontMetrics().ascent() + 5, QString::number( page ) );
   762 			if ( view.top()  >= richText.height() )
   763 			break;
   764 			printer->newPage();
   765 			page++;
   766 		} while (TRUE);
   767     }
   768 }
   769 
   770 void TextEditor::textEditUndo()
   771 {
   772 }
   773 
   774 void TextEditor::toggleFonthint()
   775 {
   776 	setUpdatesEnabled (false);
   777 	e->selectAll (true);
   778 	if (!actionFormatUseFixedFont->isOn() ) 
   779 		e->setCurrentFont (varFont);
   780 	else	
   781 		e->setCurrentFont (fixedFont);
   782 	e->selectAll (false);
   783 	setUpdatesEnabled (true);
   784 	repaint();
   785 }
   786 
   787 void TextEditor::setFixedFont()
   788 {
   789 	bool ok;
   790 	QFont font =QFontDialog::getFont(
   791                     &ok, fixedFont, this );
   792     if ( ok ) 
   793         // font is set to the font the user selected
   794 		fixedFont=font;
   795 }
   796 
   797 void TextEditor::setVarFont()
   798 {
   799 	bool ok;
   800 	QFont font =QFontDialog::getFont(
   801                     &ok, varFont, this );
   802     if ( ok ) 
   803         // font is set to the font the user selected
   804 		varFont=font;
   805 }
   806 
   807 void TextEditor::textBold()
   808 {
   809     e->setBold( actionTextBold->isOn() );
   810 }
   811 
   812 void TextEditor::textUnderline()
   813 {
   814     e->setUnderline( actionTextUnderline->isOn() );
   815 }
   816 
   817 void TextEditor::textItalic()
   818 {
   819     e->setItalic( actionTextItalic->isOn() );
   820 }
   821 
   822 void TextEditor::textFamily( const QString &f )
   823 {
   824     e->setFamily( f );
   825 }
   826 
   827 void TextEditor::textSize( const QString &p )
   828 {
   829     e->setPointSize( p.toInt() );
   830 }
   831 
   832 
   833 void TextEditor::textColor()
   834 {
   835     QColor col = QColorDialog::getColor( e->color(), this );
   836     if ( !col.isValid() )
   837 	return;
   838     e->setColor( col );
   839     QPixmap pix( 16, 16 );
   840     pix.fill( black );
   841     actionTextColor->setIconSet( pix );
   842 }
   843 
   844 void TextEditor::textAlign( QAction *a )
   845 {
   846     if ( a == actionAlignLeft )
   847 	e->setAlignment( AlignLeft );
   848     else if ( a == actionAlignCenter )
   849 	e->setAlignment( AlignHCenter );
   850     else if ( a == actionAlignRight )
   851 	e->setAlignment( AlignRight );
   852     else if ( a == actionAlignJustify )
   853 	e->setAlignment( AlignJustify );
   854 }
   855 
   856 void TextEditor::textVAlign()
   857 {
   858     if ( sender() == actionAlignSuperScript && actionAlignSuperScript->isOn()) {
   859 	e->setVerticalAlignment( QTextEdit::AlignSuperScript);
   860     } else if (sender() == actionAlignSubScript && actionAlignSubScript->isOn()) {
   861 	e->setVerticalAlignment( QTextEdit::AlignSubScript);
   862     } else {
   863 	e->setVerticalAlignment( QTextEdit::AlignNormal);
   864     }
   865 }
   866 
   867 
   868 void TextEditor::fontChanged( const QFont &f )
   869 {
   870     comboFont->lineEdit()->setText( f.family() );
   871     comboSize->lineEdit()->setText( QString::number( f.pointSize() ) );
   872     actionTextBold->setOn( f.bold() );
   873     actionTextItalic->setOn( f.italic() );
   874     actionTextUnderline->setOn( f.underline() );
   875 }
   876 
   877 void TextEditor::colorChanged( const QColor &c )
   878 {
   879     QPixmap pix( 16, 16 );
   880     pix.fill( c );
   881     actionTextColor->setIconSet( pix );
   882 }
   883 
   884 void TextEditor::alignmentChanged( int a )
   885 {
   886     if ( ( a == AlignAuto ) || ( a & AlignLeft ))
   887 	actionAlignLeft->setOn( true );
   888     else if ( ( a & AlignHCenter ) )
   889 	actionAlignCenter->setOn( true );
   890     else if ( ( a & AlignRight ) )
   891 	actionAlignRight->setOn( true );
   892     else if ( ( a & AlignJustify ) )
   893 	actionAlignJustify->setOn( true );
   894 }
   895 
   896 void TextEditor::verticalAlignmentChanged(int a) 
   897 {
   898     if (a == QTextEdit::AlignSuperScript ) {
   899 	actionAlignSuperScript->setOn(true);
   900 	actionAlignSubScript->setOn(false);
   901     } else if (a == QTextEdit::AlignSubScript ) {
   902 	actionAlignSuperScript->setOn(false);
   903 	actionAlignSubScript->setOn(true);
   904     } else {
   905 	actionAlignSuperScript->setOn(false);
   906 	actionAlignSubScript->setOn(false);
   907     }
   908 }
   909 
   910 
   911 
   912 void TextEditor::enableActions()
   913 {
   914 	actionFileLoad->setEnabled(true);
   915 	actionFileSave->setEnabled(true);
   916 	actionFileSaveAs->setEnabled(true);
   917 	actionFilePrint->setEnabled(true);
   918 	actionEditUndo->setEnabled(true);
   919 	actionEditRedo->setEnabled(true);
   920 	actionEditCopy->setEnabled(true);
   921 	actionEditCut->setEnabled(true);
   922 	actionEditPaste->setEnabled(true);
   923 	actionEditDeleteAll->setEnabled(true);
   924 	actionEditConvertPar->setEnabled(true);
   925 	actionEditJoinLines->setEnabled(true);
   926 	actionFormatUseFixedFont->setEnabled(true);
   927 }
   928 
   929 void TextEditor::disableActions()
   930 {
   931 	actionFileLoad->setEnabled(false);
   932 	actionFileSave->setEnabled(false);
   933 	actionFileSaveAs->setEnabled(false);
   934 	actionFilePrint->setEnabled(false);
   935 	actionEditUndo->setEnabled(false);
   936 	actionEditRedo->setEnabled(false);
   937 	actionEditCopy->setEnabled(false);
   938 	actionEditCut->setEnabled(false);
   939 	actionEditPaste->setEnabled(false);
   940 	actionEditDeleteAll->setEnabled(false);
   941 	actionEditConvertPar->setEnabled(false);
   942 	actionEditJoinLines->setEnabled(false);
   943 	actionFormatUseFixedFont->setEnabled(false);
   944 }
   945 
   946