00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #include "katebookmarks.h"
00021 #include "katebookmarks.moc"
00022
00023 #include "katedocument.h"
00024 #include "kateview.h"
00025
00026 #include <klocale.h>
00027 #include <kaction.h>
00028 #include <kpopupmenu.h>
00029 #include <kstringhandler.h>
00030 #include <kxmlguiclient.h>
00031 #include <kxmlguifactory.h>
00032
00033 #include <qregexp.h>
00034 #include <qmemarray.h>
00035 #include <qevent.h>
00036
00044 static void ssort( QMemArray<uint> &a, int max )
00045 {
00046 uint tmp, j, maxpos;
00047 for ( uint h = max; h >= 1; h-- )
00048 {
00049 maxpos = 0;
00050 for ( j = 0; j <= h; j++ )
00051 maxpos = a[j] > a[maxpos] ? j : maxpos;
00052 tmp = a[maxpos];
00053 a[maxpos] = a[h];
00054 a[h] = tmp;
00055 }
00056 }
00057
00058
00059
00060 KateBookmarks::KateBookmarks( KateView* view, Sorting sort )
00061 : QObject( view, "kate bookmarks" )
00062 , m_view( view )
00063 , m_sorting( sort )
00064 {
00065 connect (view->getDoc(), SIGNAL(marksChanged()), this, SLOT(marksChanged()));
00066 _tries=0;
00067 m_bookmarksMenu = 0L;
00068 }
00069
00070 KateBookmarks::~KateBookmarks()
00071 {
00072 }
00073
00074 void KateBookmarks::createActions( KActionCollection* ac )
00075 {
00076 m_bookmarkToggle = new KToggleAction(
00077 i18n("Set &Bookmark"), "bookmark", CTRL+Key_B,
00078 this, SLOT(toggleBookmark()),
00079 ac, "bookmarks_toggle" );
00080 m_bookmarkToggle->setWhatsThis(i18n("If a line has no bookmark then add one, otherwise remove it."));
00081 m_bookmarkToggle->setCheckedState( i18n("Clear &Bookmark") );
00082
00083 m_bookmarkClear = new KAction(
00084 i18n("Clear &All Bookmarks"), 0,
00085 this, SLOT(clearBookmarks()),
00086 ac, "bookmarks_clear");
00087 m_bookmarkClear->setWhatsThis(i18n("Remove all bookmarks of the current document."));
00088
00089 m_goNext = new KAction(
00090 i18n("Next Bookmark"), "next", ALT + Key_PageDown,
00091 this, SLOT(goNext()),
00092 ac, "bookmarks_next");
00093 m_goNext->setWhatsThis(i18n("Go to the next bookmark."));
00094
00095 m_goPrevious = new KAction(
00096 i18n("Previous Bookmark"), "previous", ALT + Key_PageUp,
00097 this, SLOT(goPrevious()),
00098 ac, "bookmarks_previous");
00099 m_goPrevious->setWhatsThis(i18n("Go to the previous bookmark."));
00100
00101 m_bookmarksMenu = (new KActionMenu(i18n("&Bookmarks"), ac, "bookmarks"))->popupMenu();
00102
00103
00104
00105 connect( m_bookmarksMenu, SIGNAL(aboutToShow()), this, SLOT(bookmarkMenuAboutToShow()));
00106 connect( m_bookmarksMenu, SIGNAL(aboutToHide()), this, SLOT(bookmarkMenuAboutToHide()) );
00107
00108 marksChanged ();
00109 bookmarkMenuAboutToHide();
00110
00111 connect( m_view, SIGNAL( gotFocus( Kate::View * ) ), this, SLOT( slotViewGotFocus( Kate::View * ) ) );
00112 connect( m_view, SIGNAL( lostFocus( Kate::View * ) ), this, SLOT( slotViewLostFocus( Kate::View * ) ) );
00113 }
00114
00115 void KateBookmarks::toggleBookmark ()
00116 {
00117 uint mark = m_view->getDoc()->mark( m_view->cursorLine() );
00118 if( mark & KTextEditor::MarkInterface::markType01 )
00119 m_view->getDoc()->removeMark( m_view->cursorLine(),
00120 KTextEditor::MarkInterface::markType01 );
00121 else
00122 m_view->getDoc()->addMark( m_view->cursorLine(),
00123 KTextEditor::MarkInterface::markType01 );
00124 }
00125
00126 void KateBookmarks::clearBookmarks ()
00127 {
00128
00129 QPtrList<KTextEditor::Mark> m = m_view->getDoc()->marks();
00130 for (uint i=0; i < m.count(); i++)
00131 m_view->getDoc()->removeMark( m.at(i)->line, KTextEditor::MarkInterface::markType01 );
00132
00133
00134 marksChanged ();
00135 }
00136
00137 void KateBookmarks::slotViewGotFocus( Kate::View *v )
00138 {
00139 if ( v == (Kate::View*)m_view )
00140 bookmarkMenuAboutToHide();
00141 }
00142
00143 void KateBookmarks::slotViewLostFocus( Kate::View *v )
00144 {
00145 if ( v == (Kate::View*)m_view )
00146 m_bookmarksMenu->clear();
00147 }
00148
00149 void KateBookmarks::insertBookmarks( QPopupMenu& menu )
00150 {
00151 uint line = m_view->cursorLine();
00152 const QRegExp re("&(?!&)");
00153 int idx( -1 );
00154 int old_menu_count = menu.count();
00155 KTextEditor::Mark *next = 0;
00156 KTextEditor::Mark *prev = 0;
00157
00158 QPtrList<KTextEditor::Mark> m = m_view->getDoc()->marks();
00159 QMemArray<uint> sortArray( m.count() );
00160 QPtrListIterator<KTextEditor::Mark> it( m );
00161
00162 if ( it.count() > 0 )
00163 menu.insertSeparator();
00164
00165 for( int i = 0; *it; ++it, ++i )
00166 {
00167 if( (*it)->type & KTextEditor::MarkInterface::markType01 )
00168 {
00169 QString bText = KStringHandler::rEmSqueeze
00170 ( m_view->getDoc()->textLine( (*it)->line ),
00171 menu.fontMetrics(), 32 );
00172 bText.replace(re, "&&");
00173 bText.replace('\t', ' ');
00174
00175 if ( m_sorting == Position )
00176 {
00177 sortArray[i] = (*it)->line;
00178 ssort( sortArray, i );
00179 idx = sortArray.find( (*it)->line ) + 3;
00180 }
00181
00182 menu.insertItem(
00183 QString("%1 - \"%2\"").arg( (*it)->line+1 ).arg( bText ),
00184 m_view, SLOT(gotoLineNumber(int)), 0, (*it)->line, idx );
00185
00186 if ( (*it)->line < line )
00187 {
00188 if ( ! prev || prev->line < (*it)->line )
00189 prev = (*it);
00190 }
00191
00192 else if ( (*it)->line > line )
00193 {
00194 if ( ! next || next->line > (*it)->line )
00195 next = (*it);
00196 }
00197 }
00198 }
00199
00200 idx = ++old_menu_count;
00201 if ( next )
00202 {
00203 m_goNext->setText( i18n("&Next: %1 - \"%2\"").arg( next->line + 1 )
00204 .arg( KStringHandler::rsqueeze( m_view->getDoc()->textLine( next->line ), 24 ) ) );
00205 m_goNext->plug( &menu, idx );
00206 idx++;
00207 }
00208 if ( prev )
00209 {
00210 m_goPrevious->setText( i18n("&Previous: %1 - \"%2\"").arg(prev->line + 1 )
00211 .arg( KStringHandler::rsqueeze( m_view->getDoc()->textLine( prev->line ), 24 ) ) );
00212 m_goPrevious->plug( &menu, idx );
00213 idx++;
00214 }
00215 if ( next || prev )
00216 menu.insertSeparator( idx );
00217
00218 }
00219
00220 void KateBookmarks::bookmarkMenuAboutToShow()
00221 {
00222
00223 QPtrList<KTextEditor::Mark> m = m_view->getDoc()->marks();
00224
00225 m_bookmarksMenu->clear();
00226 m_bookmarkToggle->setChecked( m_view->getDoc()->mark( m_view->cursorLine() )
00227 & KTextEditor::MarkInterface::markType01 );
00228 m_bookmarkToggle->plug( m_bookmarksMenu );
00229 m_bookmarkClear->plug( m_bookmarksMenu );
00230
00231
00232 insertBookmarks(*m_bookmarksMenu);
00233 }
00234
00235
00236
00237
00238 void KateBookmarks::bookmarkMenuAboutToHide()
00239 {
00240 m_bookmarkToggle->plug( m_bookmarksMenu );
00241 m_bookmarkClear->plug( m_bookmarksMenu );
00242 m_goNext->setText( i18n("Next Bookmark") );
00243 m_goNext->plug( m_bookmarksMenu );
00244 m_goPrevious->setText( i18n("Previous Bookmark") );
00245 m_goPrevious->plug( m_bookmarksMenu );
00246 }
00247
00248 void KateBookmarks::goNext()
00249 {
00250 QPtrList<KTextEditor::Mark> m = m_view->getDoc()->marks();
00251 if (m.isEmpty())
00252 return;
00253
00254 uint line = m_view->cursorLine();
00255 int found = -1;
00256
00257 for (uint z=0; z < m.count(); z++)
00258 if ( (m.at(z)->line > line) && ((found == -1) || (uint(found) > m.at(z)->line)) )
00259 found = m.at(z)->line;
00260
00261 if (found != -1)
00262 m_view->gotoLineNumber ( found );
00263 }
00264
00265 void KateBookmarks::goPrevious()
00266 {
00267 QPtrList<KTextEditor::Mark> m = m_view->getDoc()->marks();
00268 if (m.isEmpty())
00269 return;
00270
00271 uint line = m_view->cursorLine();
00272 int found = -1;
00273
00274 for (uint z=0; z < m.count(); z++)
00275 if ((m.at(z)->line < line) && ((found == -1) || (uint(found) < m.at(z)->line)))
00276 found = m.at(z)->line;
00277
00278 if (found != -1)
00279 m_view->gotoLineNumber ( found );
00280 }
00281
00282 void KateBookmarks::marksChanged ()
00283 {
00284 m_bookmarkClear->setEnabled( !m_view->getDoc()->marks().isEmpty() );
00285 }
00286
00287