From d5fc2361c40b48ec9586d26033504d50106f9175 Mon Sep 17 00:00:00 2001 From: Helge Deller Date: Sun, 4 Nov 2001 00:47:59 +0000 Subject: [PATCH] =?UTF-8?q?-=20hotkey-support=20(Ctrl-E)=20to=20switch=20b?= =?UTF-8?q?etween=20configured=20font=20and=20a=20fixed=20width=20font,=20?= =?UTF-8?q?-=20fixed=20a=20few=20minor=20buglets,=20-=20some=20tuning=20in?= =?UTF-8?q?=20in=20the=20mail-rendering=20engine=20(quotedHTML()),=20-=20r?= =?UTF-8?q?emoved=20unneeded=20mSavedEditorFont=20variable,=20-=20Thanks?= =?UTF-8?q?=20to=20Michael=20H=C3=A4ckel=20for=20reviewing?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit svn path=/trunk/kdenetwork/kmail/; revision=120657 --- kmcomposerui.rc | 4 +- kmcomposewin.cpp | 20 +++++-- kmcomposewin.h | 11 +++- kmmainwin.cpp | 50 ++++++++++++---- kmmainwin.h | 4 +- kmmessage.cpp | 11 +++- kmmessage.h | 3 +- kmreaderwin.cpp | 150 ++++++++++++++++++++++++----------------------- kmreaderwin.h | 8 ++- 9 files changed, 163 insertions(+), 98 deletions(-) diff --git a/kmcomposerui.rc b/kmcomposerui.rc index 431569200..4008aff43 100644 --- a/kmcomposerui.rc +++ b/kmcomposerui.rc @@ -1,4 +1,4 @@ - + &Message @@ -45,6 +45,8 @@ + + &Attach diff --git a/kmcomposewin.cpp b/kmcomposewin.cpp index 7946b3aea..e1787af8d 100644 --- a/kmcomposewin.cpp +++ b/kmcomposewin.cpp @@ -20,6 +20,7 @@ #include "kmtransport.h" #include +#include #include #include #include @@ -62,7 +63,7 @@ #include "kmcomposewin.moc" //----------------------------------------------------------------------------- -KMComposeWin::KMComposeWin(KMMessage *aMsg, QString id ) +KMComposeWin::KMComposeWin(KMMessage *aMsg, QString id) : KMTopLevelWidget (), MailComposerIface(), mId( id ) @@ -105,6 +106,7 @@ KMComposeWin::KMComposeWin(KMMessage *aMsg, QString id ) mAutoDeleteMsg = FALSE; mFolder = NULL; mEditor = new KMEdit(mMainWidget, this); + mEditor->setTextFormat(Qt::PlainText); disableBreaking = false; QString tip = i18n("Select email address(es)"); QToolTip::add( mBtnTo, tip ); @@ -172,9 +174,6 @@ KMComposeWin::KMComposeWin(KMMessage *aMsg, QString id ) mEditor->setExternalEditorPath(mExtEditor); } - // As family may change with charset, we must save original settings - mSavedEditorFont=mEditor->font(); - mMsg = NULL; if (aMsg) setMsg(aMsg); @@ -792,6 +791,9 @@ void KMComposeWin::setupActions(void) (void) new KAction (i18n("Cl&ean Spaces"), 0, this, SLOT(slotCleanSpace()), actionCollection(), "clean_spaces"); + (void) new KToggleAction( i18n("Fixed font widths"), DEFAULT_FIXEDFONTS_KEY, this, + SLOT(slotToggleFixedFont()), actionCollection(), "toggle_fixedfont" ); + //these are checkable!!! urgentAction = new KToggleAction (i18n("&Urgent"), 0, actionCollection(), @@ -983,6 +985,8 @@ void KMComposeWin::setupEditor(void) menu->insertSeparator(); menu->insertItem(i18n("Find..."), this, SLOT(slotFind())); menu->insertItem(i18n("Replace..."), this, SLOT(slotReplace())); + menu->insertSeparator(); + menu->insertItem(i18n("Fixed font widths"), this, SLOT(slotToggleFixedFont())); mEditor->installRBPopup(menu); updateCursorPosition(); connect(mEditor,SIGNAL(CursorPositionChanged()),SLOT(updateCursorPosition())); @@ -1960,6 +1964,14 @@ void KMComposeWin::slotReplace() mEditor->replace(); } +//----------------------------------------------------------------------------- +void KMComposeWin::slotToggleFixedFont() +{ + if (!mEditor) return; + + QFont fixedfont = KGlobalSettings::fixedFont(); + mEditor->setFont( (mEditor->font() == fixedfont) ? mBodyFont : fixedfont ); +} //----------------------------------------------------------------------------- void KMComposeWin::slotUndo() diff --git a/kmcomposewin.h b/kmcomposewin.h index 0172562d9..5442ed346 100644 --- a/kmcomposewin.h +++ b/kmcomposewin.h @@ -55,6 +55,8 @@ class KURL; typedef QPtrList KMMsgPartList; +/* default key to toggle between fixed width font and default font */ +#define DEFAULT_FIXEDFONTS_KEY (CTRL+Key_E) //----------------------------------------------------------------------------- #define KMEditInherited KEdit @@ -157,7 +159,7 @@ class KMComposeWin : public KMTopLevelWidget, virtual public MailComposerIface friend class KMHeaders; // needed for the digest forward public: - KMComposeWin(KMMessage* msg=0L, QString id = "unknown" ); + KMComposeWin(KMMessage* msg=0L, QString id = "unknown"); ~KMComposeWin(); /** @@ -261,6 +263,12 @@ public slots: void slotCopy(); void slotPaste(); void slotMarkAll(); + + /** + * toggle fixed width font. + */ + void slotToggleFixedFont(); + /** * Open addressbook editor dialog. */ @@ -528,7 +536,6 @@ protected: QCString mCharset; QCString mDefCharset; - QFont mSavedEditorFont; QStringList mFolderNames; QValueList > mFolderList; diff --git a/kmmainwin.cpp b/kmmainwin.cpp index 91d83d7ef..833f69a84 100644 --- a/kmmainwin.cpp +++ b/kmmainwin.cpp @@ -1082,10 +1082,17 @@ void KMMainWin::slotShowMsgSrc() if (!cset.isEmpty()) codec = KMMsgBase::codecForName(cset); } - msg->viewSource(i18n("Message as Plain Text"), codec); + msg->viewSource(i18n("Message as Plain Text"), codec, + mMsgView->isfixedFont()); } } +//----------------------------------------------------------------------------- +void KMMainWin::slotToggleFixedFont() +{ + mMsgView->slotToggleFixedFont(); +} + //----------------------------------------------------------------------------- void KMMainWin::slotMoveMsg() @@ -1168,17 +1175,20 @@ void KMMainWin::slotViewChange() //----------------------------------------------------------------------------- void KMMainWin::slotSetHeaderStyle(int id) { - if(id <= 5) + if (id >= KMReaderWin::HdrBrief && id <= KMReaderWin::HdrAll) { mViewMenu->setItemChecked((int)mMsgView->headerStyle(), FALSE); mMsgView->setHeaderStyle((KMReaderWin::HeaderStyle)id); mViewMenu->setItemChecked(id, TRUE); + return; } - else + + if (id >= 5+KMReaderWin::IconicAttmnt && id <= 5+KMReaderWin::InlineAttmnt) { mViewMenu->setItemChecked((int)mMsgView->attachmentStyle()+5, FALSE); mViewMenu->setItemChecked(id, TRUE); mMsgView->setAttachmentStyle(id-5); + return; } } @@ -1474,11 +1484,11 @@ void KMMainWin::slotUrlClicked(const KURL &aUrl, int) // It is correct to convert to latin1() as URL should not contain // anything except ascii. msg->setBody( KURL::decode_string(queryPart.mid(6)).latin1() ); - else if (queryPart.left(6) == "?cc=") + else if (queryPart.left(4) == "?cc=") msg->setCc( KURL::decode_string(queryPart.mid(4)) ); } - win = new KMComposeWin(msg,id); + win = new KMComposeWin(msg, id); win->setCharset("", TRUE); win->show(); } @@ -1516,7 +1526,7 @@ void KMMainWin::slotMailtoCompose() msg->setCharset("utf-8"); msg->setTo(mUrlCurrent.path()); - win = new KMComposeWin(msg,id); + win = new KMComposeWin(msg, id); win->setCharset("", TRUE); win->show(); } @@ -1536,7 +1546,7 @@ void KMMainWin::slotMailtoReply() rmsg = msg->createReply(FALSE, FALSE, mMsgView->copyText()); rmsg->setTo(mUrlCurrent.path()); - win = new KMComposeWin(rmsg,id); + win = new KMComposeWin(rmsg, id); win->setCharset(msg->codec()->name(), TRUE); win->setReplyFocus(); win->show(); @@ -1660,6 +1670,10 @@ void KMMainWin::slotMsgPopup(const KURL &aUrl, const QPoint& aPoint) moveActionMenu->plug( menu ); copyActionMenu->plug( menu ); + menu->insertSeparator(); + toggleFixFontAction->plug(menu); + viewSourceAction->plug(menu); + menu->insertSeparator(); printAction->plug(menu); saveAsAction->plug(menu); @@ -1688,7 +1702,8 @@ void KMMainWin::getAccountMenu() void KMMainWin::setupMenuBar() { //----- File Menu - (void) new KAction( i18n("&New Mail Client..."), "window_new", 0, this, SLOT(slotNewMailReader()), + (void) new KAction( i18n("&New Mail Client..."), "window_new", 0, + this, SLOT(slotNewMailReader()), actionCollection(), "new_mail_client" ); saveAsAction = new KAction( i18n("Save &As..."), "filesave", @@ -1822,7 +1837,8 @@ void KMMainWin::setupMenuBar() SLOT(slotResendMsg()), actionCollection(), "send_again" ); //----- Message-Encoding Submenu - mEncoding = new KSelectAction( i18n( "Set &Encoding" ), "charset", 0, this, SLOT( slotSetEncoding() ), actionCollection(), "encoding" ); + mEncoding = new KSelectAction( i18n( "Set &Encoding" ), "charset", 0, this, + SLOT( slotSetEncoding() ), actionCollection(), "encoding" ); QStringList encodings = KMMsgBase::supportedEncodings(FALSE); encodings.prepend( i18n( "Auto" ) ); mEncoding->setItems( encodings ); @@ -1912,13 +1928,14 @@ void KMMainWin::setupMenuBar() (void) new KAction( i18n("Apply filters"), "filter", CTRL+Key_J, this, SLOT(slotApplyFilters()), actionCollection(), "apply_filters" ); - - (void) new KAction( i18n("View Source..."), 0, this, + + viewSourceAction = new KAction( i18n("View Source..."), Key_V, this, SLOT(slotShowMsgSrc()), actionCollection(), "view_source" ); + //----- View Menu KActionMenu *viewMenuAction = new - KActionMenu( i18n("things to show", "&View"), actionCollection(), "view" ); + KActionMenu( i18n("&View"), actionCollection(), "view" ); mViewMenu = viewMenuAction->popupMenu(); mViewMenu->setCheckable(TRUE); @@ -1937,6 +1954,13 @@ void KMMainWin::setupMenuBar() KMReaderWin::HdrAll + KMReaderWin::InlineAttmnt); mViewMenu->setItemChecked((int)mMsgView->headerStyle(), TRUE); mViewMenu->setItemChecked((int)mMsgView->attachmentStyle()+5, TRUE); + + mViewMenu->insertSeparator(); + toggleFixFontAction = new KToggleAction( i18n("Fixed font widths"), + DEFAULT_FIXEDFONTS_KEY, this, SLOT(slotToggleFixedFont()), + actionCollection(), "toggle_fixedfont" ); + viewMenuAction->insert( toggleFixFontAction ); + //----- Settings Menu toolbarAction = KStdAction::showToolbar(this, SLOT(slotToggleToolBar()), @@ -2184,7 +2208,7 @@ void KMMainWin::updateMessageActions() sendAgainAction->setEnabled( single_actions ); printAction->setEnabled( single_actions ); saveAsAction->setEnabled( mass_actions ); - action( "view_source" )->setEnabled( single_actions ); + viewSourceAction->setEnabled( single_actions ); if ( count == 1 ) { KMMessage *msg; diff --git a/kmmainwin.h b/kmmainwin.h index 111449a9e..19fb74362 100644 --- a/kmmainwin.h +++ b/kmmainwin.h @@ -79,7 +79,8 @@ public: KAction *replyAction, *noQuoteReplyAction, *replyAllAction, *replyListAction, *forwardAction, *forwardAttachedAction, *redirectAction, *deleteAction, *saveAsAction, *bounceAction, *editAction, - *printAction, *sendAgainAction; + *viewSourceAction, *printAction, *sendAgainAction; + KToggleAction *toggleFixFontAction; KActionMenu *filterMenu, *statusMenu, *moveActionMenu, *copyActionMenu; void folderSelected(KMFolder*, bool jumpToUnread); @@ -174,6 +175,7 @@ protected slots: void slotSetMsgStatusSent(); void slotSetMsgStatusFlag(); void slotShowMsgSrc(); + void slotToggleFixedFont(); void slotSetHeaderStyle(int); void slotSetEncoding(); void slotSendQueued(); diff --git a/kmmessage.cpp b/kmmessage.cpp index 29bc9e4d3..e31241d7e 100644 --- a/kmmessage.cpp +++ b/kmmessage.cpp @@ -16,6 +16,7 @@ #include "kmidentity.h" #include +#include #include // we need access to the protected member DwBody::DeleteBodyParts()... @@ -2075,19 +2076,23 @@ void KMMessage::addBodyPart(const KMMessagePart* aPart) //----------------------------------------------------------------------------- -void KMMessage::viewSource(const QString& aCaption, QTextCodec *codec) +void KMMessage::viewSource(const QString& aCaption, QTextCodec *codec, bool fixedfont) { QString str = (codec) ? codec->toUnicode(asString()) : asString(); #if ALLOW_GUI - QMultiLineEdit* edt; + QMultiLineEdit *edt; edt = new QMultiLineEdit; KWin::setIcons(edt->winId(), kapp->icon(), kapp->miniIcon()); if (!aCaption.isEmpty()) edt->setCaption(aCaption); - edt->insertLine(str); + edt->setTextFormat(Qt::PlainText); + edt->setText(str); + if (fixedfont) + edt->setFont(KGlobalSettings::fixedFont()); edt->setReadOnly(TRUE); + edt->resize(KApplication::desktop()->width()/2, 2*KApplication::desktop()->height()/3); edt->setCursorPosition(0, 0); edt->show(); diff --git a/kmmessage.h b/kmmessage.h index c0f124250..6b07a93c9 100644 --- a/kmmessage.h +++ b/kmmessage.h @@ -281,7 +281,8 @@ public: virtual void deleteBodyParts(void); /** Open a window containing the complete, unparsed, message. */ - virtual void viewSource(const QString& windowCaption, QTextCodec *codec); + virtual void viewSource(const QString& windowCaption, QTextCodec *codec, + bool fixedfont); /** Set "Status" and "X-Status" fields of the message from the * internal message status. */ diff --git a/kmreaderwin.cpp b/kmreaderwin.cpp index 027c92ff5..46d9f8bbf 100644 --- a/kmreaderwin.cpp +++ b/kmreaderwin.cpp @@ -78,6 +78,7 @@ KMReaderWin::KMReaderWin(QWidget *aParent, const char *aName, int aFlags) initHtmlWidget(); readConfig(); mHtmlOverride = false; + mUseFixedFont = false; connect( &updateReaderWinTimer, SIGNAL(timeout()), this, SLOT(updateReaderWin()) ); @@ -278,7 +279,7 @@ QString KMReaderWin::quoteFontTag( int quoteLevel ) } } - QString str = QString("").arg( color.name() ); + QString str = QString("").arg( color.name() ); if( font.italic() ) { str += ""; } if( font.bold() ) { str += ""; } return( str ); @@ -430,6 +431,7 @@ void KMReaderWin::displayAboutPage() "
  • DIGEST-MD5 authentication
  • \n" "
  • Identity based sent-mail folders
  • \n" "
  • Expiry of old messages
  • \n" + "
  • Hotkey to temporary switch to fixed width fonts
  • \n" "\n"); if( kernel->firstStart() ) { info += i18n("

    Please take a moment to fill in the KMail configuration panel at " @@ -896,94 +898,90 @@ void KMReaderWin::writeBodyStr(const QCString aStr, QTextCodec *aCodec) QString KMReaderWin::quotedHTML(const QString& s) { - QString htmlStr, line, tmpStr, normalStartTag, normalEndTag; - QChar ch; + QString htmlStr, line, normalStartTag, normalEndTag; + QString quoteEnd(""); - bool atStartOfLine; - int pos, beg; + unsigned int pos, beg; + unsigned int length = s.length(); - int currQuoteLevel = -1; - int prevQuoteLevel = -1; - int newlineCount = 0; if (mBodyFont.bold()) { normalStartTag += ""; normalEndTag += ""; } if (mBodyFont.italic()) { normalStartTag += ""; normalEndTag += ""; } - tmpStr = "

    " + normalStartTag; //work around KHTML slowness // skip leading empty lines - for( pos = 0; pos < (int)s.length() && s[pos] <= ' '; pos++ ); + for( pos = 0; pos < length && s[pos] <= ' '; pos++ ); while (pos > 0 && (s[pos-1] == ' ' || s[pos-1] == '\t')) pos--; beg = pos; - atStartOfLine = TRUE; - while( pos < (int)s.length() ) + htmlStr = normalStartTag; + if (mUseFixedFont) + htmlStr.append("
    ");
    +
    +  int currQuoteLevel = -1;
    +  
    +  while (beg= 0 )
    -      {
    -	if( currQuoteLevel != prevQuoteLevel )
    -	{
    -	  line.prepend( mQuoteFontTag[currQuoteLevel%3] );
    -	  if( prevQuoteLevel >= 0 )
    -	  {
    -	    line.prepend( "" );
    -	  } else line.prepend( normalEndTag );
    +    /* search next occurance of '\n' */
    +    pos = s.find('\n', beg, FALSE);
    +    if (pos == (unsigned int)(-1))
    +	pos = length;
    +
    +    line = s.mid(beg,pos-beg);
    +    beg = pos+1;
    +
    +    /* calculate line's current quoting depth */
    +    int p, actQuoteLevel = -1;
    +    bool finish = FALSE;
    +    for (p=0; p':
    +	    case '|':	actQuoteLevel++;
    +			break;
    +	    case ' ':
    +	    case '\t':	break;
    +	    default:	finish = TRUE;
    +			break;
     	}
    -	prevQuoteLevel = currQuoteLevel;
    -      }
    -      else if( prevQuoteLevel >= 0 )
    -      {
    -        line.prepend( normalStartTag );
    -	line.prepend( "" );
    -	prevQuoteLevel = -1;
    -      }
    -
    -      tmpStr += line + "
    "; - if( (newlineCount % 100) == 0 ) - { - htmlStr += tmpStr; - if (currQuoteLevel >= 0) - htmlStr += ""; - else htmlStr += normalEndTag; - htmlStr += "
    "; //work around KHTML slowness - if (currQuoteLevel >= 0) - htmlStr += mQuoteFontTag[currQuoteLevel%3]; - else htmlStr += normalStartTag; - tmpStr.truncate(0); - } + } /* for() */ - beg = pos + 1; - atStartOfLine = TRUE; - currQuoteLevel = -1; + line = strToHtml(line, TRUE); + p = line.length(); + line.append("
    \n"); - } - else if( ch > ' ' ) - { - if( atStartOfLine == TRUE && (ch=='>' || /*ch==':' ||*/ ch=='|') ) - { - if( mRecyleQouteColors == true || currQuoteLevel < 2 ) - { - currQuoteLevel += 1; - } - } - else - { - atStartOfLine = FALSE; - } + /* continue with current quotelevel if it didn't changed */ + if (actQuoteLevel == currQuoteLevel || p == 0) { + htmlStr.append(line); + continue; } - pos++; - } + /* finish last quotelevel */ + if (mUseFixedFont) + htmlStr.append(""); + if (currQuoteLevel == -1) + htmlStr.append( normalEndTag ); + else + htmlStr.append( quoteEnd ); - if (prevQuoteLevel >= 0) - tmpStr += ""; + /* start new quotelevel */ + currQuoteLevel = actQuoteLevel; + if (actQuoteLevel == -1) + line.prepend(normalStartTag); + else + line.prepend( mQuoteFontTag[currQuoteLevel%3] ); + if (mUseFixedFont) + line.prepend("
    ");
    +
    +    htmlStr.append(line);
    +  } /* while() */
    +
    +  /* really finish the last quotelevel */
    +  if (mUseFixedFont)
    +     htmlStr.append("
    "); + if (currQuoteLevel == -1) + htmlStr.append( normalEndTag ); + else + htmlStr.append( quoteEnd ); - htmlStr += tmpStr; - htmlStr += "
    "; //work around KHTML slowness return htmlStr; } @@ -1335,6 +1333,14 @@ void KMReaderWin::slotFind() act->activate(); } + +//----------------------------------------------------------------------------- +void KMReaderWin::slotToggleFixedFont() +{ + mUseFixedFont = !mUseFixedFont; + update(true); +} + //----------------------------------------------------------------------------- void KMReaderWin::atmViewMsg(KMMessagePart* aMsgPart) { diff --git a/kmreaderwin.h b/kmreaderwin.h index 8c50789aa..5bcb6cd56 100644 --- a/kmreaderwin.h +++ b/kmreaderwin.h @@ -50,7 +50,7 @@ public: virtual void setInlineAttach(int maxLines); /** Style of the message header. */ - enum HeaderStyle { HdrFancy=1, HdrBrief=2, HdrStandard=3, HdrLong=4, + enum HeaderStyle { HdrBrief=1, HdrFancy=2, HdrStandard=3, HdrLong=4, HdrAll=5 }; /** Style of attachments. */ enum AttachmentStyle {IconicAttmnt=1, SmartAttmnt =2, InlineAttmnt = 3}; @@ -118,6 +118,8 @@ public: bool atBottom() const; + bool isfixedFont() { return mUseFixedFont; } + signals: /** Emitted to show a text on the status line. */ void statusMsg(const QString& text); @@ -164,6 +166,9 @@ public slots: /** The user selected "Find" from the menu. */ void slotFind(); + /** The user toggled the "Fixed Font" flag from the view menu. */ + void slotToggleFixedFont(); + protected slots: /** Some attachment operations. */ void slotAtmOpen(); @@ -250,6 +255,7 @@ protected: bool mMsgDisplay; int fntSize; + bool mUseFixedFont; QString mBodyFamily; QColor c1, c2, c3, c4; QString mQuoteFontTag[3];