From 052cbfee3562d05f6041d802aec737e0f5f0756e Mon Sep 17 00:00:00 2001 From: Vadim Zeitlin Date: Sat, 5 Jun 1999 01:03:54 +0000 Subject: [PATCH] latest changes: added word-wise movement (buggy, esp. backwards), more minor fixes, big problems (scrolling/selection) still remain under MSW git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@2673 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775 --- user/wxLayout/wxllist.cpp | 75 ++++++++++++++++++++++++++++++++++++- user/wxLayout/wxllist.h | 9 ++++- user/wxLayout/wxlwindow.cpp | 38 +++++++++++-------- user/wxLayout/wxlwindow.h | 4 -- 4 files changed, 104 insertions(+), 22 deletions(-) diff --git a/user/wxLayout/wxllist.cpp b/user/wxLayout/wxllist.cpp index f0e15342f6..4596fc7205 100644 --- a/user/wxLayout/wxllist.cpp +++ b/user/wxLayout/wxllist.cpp @@ -937,7 +937,8 @@ wxLayoutLine::DeleteWord(CoordType xpos) return true; } } - wxASSERT(0); // we should never arrive here + + wxFAIL_MSG("unreachable"); } wxLayoutLine * @@ -1671,6 +1672,78 @@ wxLayoutList::MoveCursorHorizontally(int n) return n == 0; } +bool +wxLayoutList::MoveCursorWord(int n) +{ + wxCHECK_MSG( m_CursorLine, false, "no current line" ); + wxCHECK_MSG( n == -1 || n == +1, false, "not implemented yet" ); + + CoordType moveDistance = 0; + CoordType offset; + for ( wxLOiterator i = m_CursorLine->FindObject(m_CursorPos.x, &offset); + n != 0; + n > 0 ? i++ : i-- ) + { + if ( i == NULLIT ) + return false; + + wxLayoutObject *obj = *i; + if( obj->GetType() != WXLO_TYPE_TEXT ) + { + // any non text objects count as one word + n > 0 ? n-- : n++; + + moveDistance += obj->GetLength(); + } + else + { + // text object + wxLayoutObjectText *tobj = (wxLayoutObjectText *)obj; + + if ( offset == tobj->GetLength() ) + { + // at end of object + n > 0 ? n-- : n++; + } + else + { + const char *start = tobj->GetText().c_str(); + const char *p = start + offset; + + // to the beginning/end of the next/prev word + while ( isspace(*p) ) + { + n > 0 ? p++ : p--; + } + + // go to the end/beginning of the word (in a broad sense...) + while ( p >= start && !isspace(*p) ) + { + n > 0 ? p++ : p--; + } + + if ( n > 0 ) + { + // now advance to the beginning of the next word + while ( isspace(*p) ) + p++; + } + + n > 0 ? n-- : n++; + + moveDistance = p - start - offset; + } + } + + // except for the first iteration, offset is 0 + offset = 0; + } + + MoveCursorHorizontally(moveDistance); + + return true; +} + bool wxLayoutList::Insert(wxString const &text) { diff --git a/user/wxLayout/wxllist.h b/user/wxLayout/wxllist.h index c354b2ffb3..05e4498652 100644 --- a/user/wxLayout/wxllist.h +++ b/user/wxLayout/wxllist.h @@ -761,10 +761,15 @@ public: */ bool MoveCursorVertically(int n); /** Move cursor left or right. - @param n + @param n = number of positions to move @return bool if it could be moved */ bool MoveCursorHorizontally(int n); + /** Move cursor to the left or right counting in words + @param n = number of positions in words + @return bool if it could be moved + */ + bool MoveCursorWord(int n); /// Move cursor to end of line. void MoveCursorToEndOfLine(void) @@ -847,7 +852,7 @@ public: /** Finds text in this list. @param needle the text to find @param cpos the position where to start the search - @return the cursoor coord where it was found or (-1,-1) + @return the cursor coord where it was found or (-1,-1) */ wxPoint FindText(const wxString &needle, const wxPoint &cpos = wxPoint(0,0)) const; diff --git a/user/wxLayout/wxlwindow.cpp b/user/wxLayout/wxlwindow.cpp index 0cd45c2c93..7f0bbbdfe1 100644 --- a/user/wxLayout/wxlwindow.cpp +++ b/user/wxLayout/wxlwindow.cpp @@ -75,7 +75,9 @@ END_EVENT_TABLE() wxLayoutWindow::wxLayoutWindow(wxWindow *parent) : wxScrolledWindow(parent, -1, wxDefaultPosition, wxDefaultSize, - wxHSCROLL | wxVSCROLL | wxBORDER) + wxHSCROLL | wxVSCROLL | + wxBORDER | + wxWANTS_CHARS) { SetStatusBar(NULL); // don't use statusbar @@ -138,15 +140,6 @@ wxLayoutWindow::Clear(int family, DoPaint((wxRect *)NULL); } -#ifdef __WXMSW__ -long -wxLayoutWindow::MSWGetDlgCode() -{ - // if we don't return this, we won't get OnChar() events for TABs and ENTER - return DLGC_WANTCHARS | DLGC_WANTARROWS | DLGC_WANTMESSAGE; -} -#endif //MSW - void wxLayoutWindow::OnMouse(int eventId, wxMouseEvent& event) { @@ -308,13 +301,20 @@ wxLayoutWindow::OnChar(wxKeyEvent& event) cursor, etc. It's default will process all keycodes causing modifications to the buffer, but only if editing is allowed. */ + bool ctrlDown = event.ControlDown(); switch(keyCode) { case WXK_RIGHT: - m_llist->MoveCursorHorizontally(1); + if ( ctrlDown ) + m_llist->MoveCursorWord(1); + else + m_llist->MoveCursorHorizontally(1); break; case WXK_LEFT: - m_llist->MoveCursorHorizontally(-1); + if ( ctrlDown ) + m_llist->MoveCursorWord(-1); + else + m_llist->MoveCursorHorizontally(-1); break; case WXK_UP: m_llist->MoveCursorVertically(-1); @@ -329,18 +329,26 @@ wxLayoutWindow::OnChar(wxKeyEvent& event) m_llist->MoveCursorVertically(20); break; case WXK_HOME: - m_llist->MoveCursorToBeginOfLine(); + if ( ctrlDown ) + m_llist->MoveCursorTo(wxPoint(0, 0)); + else + m_llist->MoveCursorToBeginOfLine(); break; case WXK_END: + if ( ctrlDown ) + { + // TODO VZ: how to move the cursor to the last line of the text? + m_llist->MoveCursorVertically(1000); + } m_llist->MoveCursorToEndOfLine(); break; default: - if(keyCode == 'c' && event.ControlDown()) + if(keyCode == 'c' && ctrlDown) { // this should work even in read-only mode Copy(); } - if( IsEditable() ) + else if( IsEditable() ) { /* First, handle control keys */ if(event.ControlDown() && ! event.AltDown()) diff --git a/user/wxLayout/wxlwindow.h b/user/wxLayout/wxlwindow.h index 080ff000ee..c857b1572c 100644 --- a/user/wxLayout/wxlwindow.h +++ b/user/wxLayout/wxlwindow.h @@ -116,10 +116,6 @@ public: */ void DoPaint(const wxRect *updateRect = NULL); -#ifdef __WXMSW__ - virtual long MSWGetDlgCode(); -#endif //MSW - /// if exact == false, assume 50% extra size for the future void ResizeScrollbars(bool exact = false); // don't change this to true! -- 2.47.2