2010-03-10 17:05 UTC-0800 Pritpal Bedi (pritpal@vouchcac.com)

* contrib/hbqt/doc/en/class_hbqplaintextedit.txt
  * contrib/hbqt/hbqt_hbqplaintextedit.cpp
  * contrib/hbqt/hbqt_hbqplaintextedit.h
  * contrib/hbqt/qtgui/HBQPlainTextEdit.cpp
  * contrib/hbqt/qtgui/THBQPlainTextEdit.prg
  * contrib/hbqt/qth/HBQPlainTextEdit.qth

  * contrib/hbide/hbide.prg
  * contrib/hbide/ideeditor.prg
  * contrib/hbide/idefunctions.prg
  * contrib/hbide/ideobject.prg

    + Implemented "Code Completion" feature.
        How it works:
          1. Load prototype tags in "Projects Functions Lookup".
          2. Activate some editor tab.
          3. Start typing a function proto. 
          4. After 3 characters a popup will appear beneth the cursor.
          5. Select from the list, by mouse or use navigation keys.
          6. Prototype will be there in the editor exactly with 
             same cases your prototype is defined.

               Input is welcome.
This commit is contained in:
Pritpal Bedi
2010-03-11 01:10:36 +00:00
parent f804553c6c
commit 4788dd88da
11 changed files with 223 additions and 49 deletions

View File

@@ -17,6 +17,31 @@
past entries belonging to author(s): Viktor Szakats.
*/
2010-03-10 17:05 UTC-0800 Pritpal Bedi (pritpal@vouchcac.com)
* contrib/hbqt/doc/en/class_hbqplaintextedit.txt
* contrib/hbqt/hbqt_hbqplaintextedit.cpp
* contrib/hbqt/hbqt_hbqplaintextedit.h
* contrib/hbqt/qtgui/HBQPlainTextEdit.cpp
* contrib/hbqt/qtgui/THBQPlainTextEdit.prg
* contrib/hbqt/qth/HBQPlainTextEdit.qth
* contrib/hbide/hbide.prg
* contrib/hbide/ideeditor.prg
* contrib/hbide/idefunctions.prg
* contrib/hbide/ideobject.prg
+ Implemented "Code Completion" feature.
How it works:
1. Load prototype tags in "Projects Functions Lookup".
2. Activate some editor tab.
3. Start typing a function proto.
4. After 3 characters a popup will appear beneth the cursor.
5. Select from the list, by mouse or use navigation keys.
6. Prototype will be there in the editor exactly with
same cases your prototype is defined.
Input is welcome.
2010-03-10 21:42 UTC+0100 Viktor Szakats (harbour.01 syenar.hu)
* utils/hbmk2/hbmk2.prg
* config/dos/djgpp.mk

View File

@@ -177,6 +177,8 @@ CLASS HbIde
DATA qTBarPanels
DATA qTBarDocks
DATA qCompleter
DATA qCompModel
DATA qProtoList
ACCESS oCurEditor INLINE ::oEM:getEditorCurrent()
ACCESS qCurEdit INLINE ::oEM:getEditCurrent()

View File

@@ -198,10 +198,16 @@ METHOD IdeEditsManager:create( oIde )
aadd( ::aActions, { "" , oSub:addSeparator() } )
aadd( ::aActions, { "Close Split" , oSub:addAction( "Close Split Window" ) } )
::oIde:qProtoList := QStringList():new()
::oIde:qCompModel := QStringListModel():new()
::oIde:qCompleter := QCompleter():new()
::qCompModel:setStringList( ::qProtoList )
::qCompleter:setModel( ::qCompModel )
::qCompleter:setModelSorting( QCompleter_CaseInsensitivelySortedModel )
::qCompleter:setCaseSensitivity( Qt_CaseInsensitive )
::qCompleter:setCompletionMode( QCompleter_PopupCompletion )
::qCompleter:setWrapAround( .f. )
::connect( ::qCompleter, "activated(QString)", {|p| ::execEvent( qcompleter_activated, p ) } )
@@ -265,11 +271,13 @@ METHOD IdeEditsManager:addSourceInTree( cSourceFile )
/*----------------------------------------------------------------------*/
METHOD IdeEditsManager:execEvent( nMode, p )
HB_SYMBOL_UNUSED( p )
LOCAL oEdit
DO CASE
CASE nMode == qcompleter_activated
IF !empty( oEdit := ::getEditObjectCurrent() )
oEdit:completeCode( p )
ENDIF
ENDCASE
@@ -1398,6 +1406,7 @@ CLASS IdeEdit INHERIT IdeObject
METHOD resumePrototype()
METHOD showPrototype( cProto )
METHOD hidePrototype()
METHOD completeCode( p )
ENDCLASS
@@ -1432,6 +1441,8 @@ METHOD IdeEdit:create( oEditor, nMode )
::qEdit:hbHighlightCurrentLine( .t. ) /* Via user-setup */
::qEdit:hbSetSpaces( ::nTabSpaces )
::qEdit:hbSetCompleter( ::qCompleter )
::toggleLineNumbers()
::qHLayout := QHBoxLayout():new()
@@ -2222,6 +2233,23 @@ METHOD IdeEdit:hidePrototype()
/*----------------------------------------------------------------------*/
METHOD IdeEdit:completeCode( p )
LOCAL qCursor := QTextCursor():from( ::qEdit:textCursor() )
qCursor:movePosition( QTextCursor_Left )
qCursor:movePosition( QTextCursor_StartOfWord )
qCursor:movePosition( QTextCursor_EndOfWord, QTextCursor_KeepAnchor )
qCursor:insertText( p )
qCursor:movePosition( QTextCursor_Left )
qCursor:movePosition( QTextCursor_Right )
::qEdit:setTextCursor( qCursor )
RETURN Self
/*----------------------------------------------------------------------*/
METHOD IdeEdit:loadFuncHelp()
LOCAL qEdit, qCursor, qTextBlock, cText, cWord, nCol, cPro

View File

@@ -425,7 +425,7 @@ METHOD IdeFunctions:enableControls( lEnable )
::oUI:q_editFunction:setEnabled( lEnable )
::showApplicationCursor( iif( lEnable, NIL, Qt_BusyCursor ) )
::showApplicationCursor( iif( lEnable, NIL, Qt_WaitCursor ) )
RETURN Self
@@ -586,29 +586,56 @@ METHOD IdeFunctions:consolidateList()
/*----------------------------------------------------------------------*/
METHOD IdeFunctions:populateTable()
LOCAL oTbl, qItm, a_, n
LOCAL oTbl, qItm, a_, n, s, k_:={}
::clear( .t. )
::buildHeader()
::clear( .t. )
::buildHeader()
oTbl := ::oUI:q_tableFuncList
oTbl:setRowCount( len( ::aList ) )
oTbl := ::oUI:q_tableFuncList
oTbl:setRowCount( len( ::aList ) )
n := 0
FOR EACH a_ IN ::aList
qItm := QTableWidgetItem():new()
n := 0
FOR EACH a_ IN ::aList
qItm := QTableWidgetItem():new()
qItm:setText( a_[ 3 ] )
qItm:setTooltip( a_[ 2 ] )
oTbl:setItem( n, 0, qItm )
oTbl:setRowHeight( n, 16 )
qItm:setText( a_[ 3 ] )
qItm:setTooltip( a_[ 2 ] )
oTbl:setItem( n, 0, qItm )
oTbl:setRowHeight( n, 16 )
QApplication():processEvents()
QApplication():processEvents()
aadd( ::aItems, qItm )
n++
::oUI:q_labelEntries:setText( "Entries: " + hb_ntos( n ) )
NEXT
aadd( ::aItems, qItm )
n++
::oUI:q_labelEntries:setText( "Entries: " + hb_ntos( n ) )
NEXT
::qProtoList:clear()
FOR EACH a_ IN ::aList
s := a_[ 2 ]
IF ( n := at( "(", s ) ) == 0
IF ( n := at( " ", s ) ) > 0
aadd( k_, substr( s, 1, n - 1 ) )
ELSE
aadd( k_, trim( s ) )
ENDIF
ELSE
aadd( k_, substr( s, 1, n - 1 ) )
ENDIF
NEXT
asort( k_, , , {|e,f| lower( e ) < lower( f ) } )
aeval( k_, {|e| ::qProtoList:append( e ) } )
::qCompModel:setStringList( ::qProtoList )
::qCompleter:setModel( ::qCompModel )
::qCompleter:setModelSorting( QCompleter_CaseInsensitivelySortedModel )
::qCompleter:setCaseSensitivity( Qt_CaseInsensitive )
::qCompleter:setCompletionMode( QCompleter_PopupCompletion )
::qCompleter:setWrapAround( .f. )
QListView():from( ::qCompleter:popup() ):setAlternatingRowColors( .t. )
RETURN Self

View File

@@ -120,6 +120,8 @@ CLASS IdeObject
ACCESS qTBarPanels INLINE ::oIde:qTBarPanels
ACCESS qTBarDocks INLINE ::oIde:qTBarDocks
ACCESS qCompleter INLINE ::oIde:qCompleter
ACCESS qCompModel INLINE ::oIde:qCompModel
ACCESS qProtoList INLINE ::oIde:qProtoList
ACCESS cWrkProject INLINE ::oIde:cWrkProject
ACCESS cWrkTheme INLINE ::oIde:cWrkTheme

View File

@@ -1,20 +1,25 @@
/*
* hbQTgen v1.0 - Harbour Callable Wrappers Generator for Qt v4.5.3+
* hbQTgen v1.0 - Harbour Callable Wrappers Generator for QT v4.5+
*
* Please do not modify this document as it is subject to change in future.
*
* Pritpal Bedi <bedipritpal@hotmail.com>
*
* 03/10/10 - 14:17:24
*
*/
/* $DOC$
$TEMPLATE$
Class
$NAME$
HBQPlainTextEdit()
$CATEGORY$
Harbour Bindings for Qt
Harbour Bindings for Qt 4.5.3+
$SUBCATEGORY$
GUI
$EXTERNALLINK$
http://doc.trolltech.com/4.5/hbqplaintextedit.html
$ONELINER$
Creates a new HBQPlainTextEdit object.
$INHERITS$
@@ -60,7 +65,9 @@
:hbMoveLine( nIDirection ) -> NIL
:hbHighlightSelectedColumns( lYes ) -> NIL
:hbGetSelectedText() -> cQString
:hbTextUnderCursor() -> cQString
:hbShowPrototype( cTip ) -> NIL
:hbSetCompleter( pCompleter ) -> NIL
$DESCRIPTION$
@@ -81,6 +88,6 @@
C++ Wrappers : contrib/hbqt/qtgui/HBQPlainTextEdit.cpp
Library : hbqtgui
$SEEALSO$
QPlainTextEdit
QPlainTextEdit, http://doc.trolltech.com/4.5/hbqplaintextedit.html
$END$
*/

View File

@@ -170,6 +170,75 @@ bool HBQPlainTextEdit::event( QEvent *event )
return QPlainTextEdit::event( event );
}
void HBQPlainTextEdit::keyPressEvent( QKeyEvent * event )
{
if( c && c->popup()->isVisible() )
{
// The following keys are forwarded by the completer to the widget
switch( event->key() )
{
case Qt::Key_Enter:
case Qt::Key_Return:
case Qt::Key_Escape:
case Qt::Key_Tab:
case Qt::Key_Backtab:
event->ignore();
return; // let the completer do default behavior
default:
break;
}
}
QPlainTextEdit::keyPressEvent( event );
const bool ctrlOrShift = event->modifiers() & (Qt::ControlModifier | Qt::ShiftModifier);
if( !c || ( ctrlOrShift && event->text().isEmpty() ) )
return;
static QString eow( "~!@#$%^&*()+{}|:\"<>?,./;'[]\\-=" ); /* end of word */
bool hasModifier = ( event->modifiers() != Qt::NoModifier ) && !ctrlOrShift;
QString completionPrefix = hbTextUnderCursor();
if( ( hasModifier || event->text().isEmpty() || completionPrefix.length() < 3
|| eow.contains( event->text().right( 1 ) ) ) )
{
c->popup()->hide();
return;
}
if( completionPrefix != c->completionPrefix() )
{
c->setCompletionPrefix( completionPrefix );
c->popup()->setCurrentIndex( c->completionModel()->index( 0, 0 ) );
}
QRect cr = cursorRect();
cr.setWidth( c->popup()->sizeHintForColumn( 0 ) + c->popup()->verticalScrollBar()->sizeHint().width() );
c->complete( cr ); // popup it up!
}
QString HBQPlainTextEdit::hbTextUnderCursor()
{
QTextCursor tc = textCursor();
tc.select( QTextCursor::WordUnderCursor );
return tc.selectedText();
}
void HBQPlainTextEdit::resizeEvent( QResizeEvent *e )
{
QPlainTextEdit::resizeEvent( e );
QRect cr = contentsRect();
lineNumberArea->setGeometry( QRect( cr.left(), cr.top(), hbLineNumberAreaWidth(), cr.height() ) );
}
void HBQPlainTextEdit::focusInEvent( QFocusEvent * event )
{
if( c )
c->setWidget( this );
QPlainTextEdit::focusInEvent( event );
}
void HBQPlainTextEdit::mouseDoubleClickEvent( QMouseEvent *event )
{
HB_TRACE( HB_TR_ALWAYS, ( "void HBQPlainTextEdit::mouseDblClickEvent( QMouseEvent * %p )", event ) );
@@ -256,24 +325,6 @@ void HBQPlainTextEdit::lineNumberAreaPaintEvent( QPaintEvent *event )
}
}
#if 0
void HBQPlainTextEdit::contextMenuEvent( QContextMenuEvent *event )
{
QWidget::contextMenuEvent( event );
}
void HBQPlainTextEdit::keyPressEvent( QKeyEvent *event )
{
QPlainTextEdit::keyPressEvent( event );
}
#endif
void HBQPlainTextEdit::resizeEvent( QResizeEvent *e )
{
QPlainTextEdit::resizeEvent( e );
QRect cr = contentsRect();
lineNumberArea->setGeometry( QRect( cr.left(), cr.top(), hbLineNumberAreaWidth(), cr.height() ) );
}
void HBQPlainTextEdit::hbBookmarks( int block )

View File

@@ -63,6 +63,9 @@
#include <QTextBlock>
#include <QPainter>
#include <QMessageBox>
#include <QCompleter>
#include <QAbstractItemView>
#include <QScrollBar>
#include <QToolTip>
#include "hbqt_hbqsyntaxhighlighter.h"
@@ -123,15 +126,14 @@ private:
int columnEnds;
bool isColumnSelectionEnabled;
bool isTipActive;
QCompleter * c;
protected:
bool event( QEvent * event );
void resizeEvent( QResizeEvent * event );
void mouseDoubleClickEvent( QMouseEvent * event );
#if 0
void contextMenuEvent( QContextMenuEvent * event );
void focusInEvent( QFocusEvent * event );
void keyPressEvent( QKeyEvent * event );
#endif
public slots:
void hbUpdateLineNumberAreaWidth( int newBlockCount );
@@ -153,9 +155,11 @@ public slots:
void hbInsertTab( int mode );
void hbHighlightSelectedColumns( bool yes );
QString hbGetSelectedText();
QString hbTextUnderCursor();
void hbNumberBlockVisible( bool b );
bool hbNumberBlockVisible();
void hbShowPrototype( const QString & tip );
void hbSetCompleter( QCompleter * completer ) { c = completer; };
private slots:
void hbSlotCursorPositionChanged();

View File

@@ -410,6 +410,14 @@ HB_FUNC( QT_HBQPLAINTEXTEDIT_HBGETSELECTEDTEXT )
hb_retc( hbqt_par_HBQPlainTextEdit( 1 )->hbGetSelectedText().toAscii().data() );
}
/*
* QString hbTextUnderCursor()
*/
HB_FUNC( QT_HBQPLAINTEXTEDIT_HBTEXTUNDERCURSOR )
{
hb_retc( hbqt_par_HBQPlainTextEdit( 1 )->hbTextUnderCursor().toAscii().data() );
}
/*
* void hbShowPrototype( const QString & tip )
*/
@@ -418,6 +426,14 @@ HB_FUNC( QT_HBQPLAINTEXTEDIT_HBSHOWPROTOTYPE )
hbqt_par_HBQPlainTextEdit( 1 )->hbShowPrototype( HBQPlainTextEdit::tr( hb_parc( 2 ) ) );
}
/*
* void hbSetCompleter( QCompleter * completer )
*/
HB_FUNC( QT_HBQPLAINTEXTEDIT_HBSETCOMPLETER )
{
hbqt_par_HBQPlainTextEdit( 1 )->hbSetCompleter( hbqt_par_QCompleter( 2 ) );
}
/*----------------------------------------------------------------------*/
#endif /* #if QT_VERSION >= 0x040500 */

View File

@@ -99,7 +99,9 @@ CREATE CLASS HBQPlainTextEdit INHERIT HbQtObjectHandler, QPlainTextEdit
METHOD hbMoveLine( nIDirection )
METHOD hbHighlightSelectedColumns( lYes )
METHOD hbGetSelectedText()
METHOD hbTextUnderCursor()
METHOD hbShowPrototype( cTip )
METHOD hbSetCompleter( pCompleter )
ENDCLASS
@@ -241,6 +243,14 @@ METHOD HBQPlainTextEdit:hbGetSelectedText()
RETURN Qt_HBQPlainTextEdit_hbGetSelectedText( ::pPtr )
METHOD HBQPlainTextEdit:hbTextUnderCursor()
RETURN Qt_HBQPlainTextEdit_hbTextUnderCursor( ::pPtr )
METHOD HBQPlainTextEdit:hbShowPrototype( cTip )
RETURN Qt_HBQPlainTextEdit_hbShowPrototype( ::pPtr, cTip )
METHOD HBQPlainTextEdit:hbSetCompleter( pCompleter )
RETURN Qt_HBQPlainTextEdit_hbSetCompleter( ::pPtr, hbqt_ptr( pCompleter ) )

View File

@@ -55,9 +55,9 @@
;
<CLASS>
QObject =
QObject =
Inherits = QPlainTextEdit
Type =
Type =
New =
</CLASS>
@@ -106,7 +106,7 @@ HB_FUNC( QT_HBQPLAINTEXTEDIT )
void hbGotoBookmark(int block)
void hbNumberBlockVisible(bool b)
bool hbNumberBlockVisible()
void hbHighlightCurrentLine(bool b)
void hbHighlightCurrentLine(bool b)
bool hbHighlightCurrentLine()
void hbSetEventBlock( PHB_ITEM block )
</PROTOS>
@@ -130,7 +130,9 @@ HB_FUNC( QT_HBQPLAINTEXTEDIT )
void hbMoveLine( int iDirection )
void hbHighlightSelectedColumns( bool yes )
QString hbGetSelectedText()
QString hbTextUnderCursor()
void hbShowPrototype( const QString & tip )
void hbSetCompleter( QCompleter * completer )
</SLOTS>
<SIGNALS>