[QScintilla] folding quirks
Phil Thompson
phil at riverbankcomputing.com
Wed Feb 17 12:22:54 GMT 2010
On Tue, 16 Feb 2010 03:50:22 -0500, Jared Sutton <jpsutton at gmail.com>
wrote:
> Hi All,
>
> For the last several years (spare time) I've been constructing a simple
> cross-platform code editor called QSciTE using Qt4 version of
Qscintilla2.
> You can find it here, in case you're interested:
>
> http://qscite.googlecode.com/
>
> First off, thanks very much for making this library available to the
public
> under the GPL. It has some wonderful functionality built-in.
>
> I've been having some issues with code folding recently, which I believe
to
> have stemmed from at least one bug in Qscintilla. I have a simple menu
> option to enable/disable code folding. Whenever I turn folding off, I
want
> any lines that are currently folded to be unfolded automatically, since
it
> doesn't make a whole lot of sense to have folded code that can't easily
be
> unfolded. Here's my toggleFolding() function which is directly connected
> to
> the menu option:
>
> void MainWindow::toggleFolding() {
> QsciteEditor * doc = getCurDoc();
> QsciteEditor::FoldStyle state =
> static_cast<QsciteEditor::FoldStyle>((!doc->folding()) * 5);
>
> if (!state) {
> // unfold all code before turning off folding
> doc->foldAll(false);
> }
>
> doc->setFolding(state);
> }
>
> The QsciteEditor class is a child-class of Qscintilla, because I needed
to
> expose several functions for use with QtScript, and because I needed to
> catch some key-presses that I needed to process specially. As you can
see,
> foldAll() is only getting called just before the folding is about to be
> turned off. The documentation for foldAll() states "If any lines are
> currently folded then they are all unfolded. Otherwise all lines are
> folded." Now, my implementation does not take into account the
possibility
> that no lines were folded between the time that the folding was enabled
and
> disabled (which I'll expand on below), meaning that if foldAll() works as
> documented, I should expect to see all lines get folded before the
folding
> is disabled. However, even when I fold one or more lines and then turn
off
> folding, I find that all lines are getting folded before folding gets
> disabled. This seems like it's a problem with the foldAll()
> implementation.
It depends...
foldAll() can only deal with what a particular lexer has set in the way of
fold flags. I've found that lexers don't always exhibit consistent
behaviour - some are just wrong.
Both Scite and QScintilla will call foldAll() (or the Scite equivalent)
when you shift-control-click in the fold margin. I would compare the result
of doing this in Scite with the same lexer set and the same file being
edited. If the result is different then it's probably a QScintilla bug. If
it's not then it's likely to be a Scintilla bug or feature (ie. in the
particular lexer itself).
> This also brings up a few questions:
> 1. Shouldn't setFolding() automatically unfold all lines that are
currently
> folded before the FoldStyle is set to NoFoldStyle? Does anyone expect to
> have lines folded after they disable folding?
> 2. If the person using QsciScintilla is expected to unfold all lines that
> were folded before turning folding off, how can he know what lines are
> folded? As far as I can tell, that information is private, as are the
> functions/signals/slots that are responsible for changing a line's fold
> state.
>
> So, I see these issues in the end:
> 1. There appears to be a bug in the QsciScintilla:foldAll(bool) function.
> It doesn't appear to function as documented.
> 2. In my opinion, QsciScintilla::setFolding() should either unfold
> everything when folding is turned off, or the appropriate member
> variables/functions/signals/slots should be changed from private to
> protected so that developers can deal with the situation without
resorting
> to hacking on Qscintilla directly.
How about an unfoldAll() method? (It's a shame that foldAll() was so badly
named.) That would allow it to be used separately from setFolding(), and
wouldn't change the behaviour of the latter for existing applications.
> For what it's worth, here's my development environment:
> Arch Linux
> KDEmod 4.4.0
> Qscintilla 2.4.2
> Qt 4.6.1
>
> Thanks for any insight you may have.
>
> Jared Sutton
Phil
More information about the QScintilla
mailing list