Selection and positionning within a text
by Andrey B. Yastrebov
Many commands need to deal with a position inside text. How this
position may be represented? There are many ways. Look at your
location on the Earth. You may be located with your geographical
coordinates, but you may be located also with your street address.
Moreover, last years, phone number or e-mail address will locate
you even better. The same happens with the position inside text.
You may define the location inside the text in a number of ways.
Which one is better or worse?
Look at the standard Windows Edit control. It defines location
inside the text with its offset from the beginning of the buffer.
Why? Just because it stores the text in a single buffer and this
way is the most natural for it. It even
doesn't need to find the location - programmer gives it the
location ready to use. Such a way of locating position within
a text is the most handy.
LEdit manages texts differently. Let's suppose Ledit had the
text stored in one large memory buffer. The text may be several
magabytes. Imagine that you moves to the beginning of the text,
and you
press key 'A'. Now the control needs to reflect changes. It
needs to insert your 'A'. What happens? Several megabytes of
memory have to be scrolled one position down. You may be waiting
for several seconds until the letter appears on the screen.
Not so good way to keep large texts. That's probably why
standard Edit control keeps having 64K limit even in Windows 95.
What to do with it? How to avoid such a difficulty? The
memory should be organized differently.
That's why LEdit doesn't store
all the text as a single buffer. It stores the text as a
list of lines. This way, change in one line (e.g. typing 'A')
will result in no delay. All will be fast.
But what happens with the way of locating position inside
text? It changes. Edit's way to locate position isn't
handy any more. To find the text at some offset, LEdit needs
to scan all lines before that offset for their lengths and
sum them up. It may take much time.
A better way to locate position is to tell a number of
the line and an offset of symbol within that line.
That way, LEdit will work much
faster than in case of preserving old method. That's why
positionning within the text becomes quite different -
LEdit stores location in two numbers - a number of line and
a number of symbol inside line. It's very natural to LEdit
as well as the offset inside buffer is natural to standard Edit.
If you use LEdit you have to switch to the new way unless
you're going to kill LEdit's efectiveness.
Which way is better? I think the way LEdit locates
positions is far more natural to human being (and to programmers
too, because I suppose they are human beings).
Let's see - when you need to locate some place in a book you
say: "open n-th page, see at m-th line k-th word". You
don't say: "open the book at i-th word". You do this just
because books are organized that way. This way is natural with
books. It is natural with LEdit too.
If you have ever selected the text in editor you probably
noticed that this process ends up with the text from
some position to some other position being highlighted
(and ready for some operation). So, to define where selection
is, we need to know two positions - start of the selection and
end of the selection. Please note, that start of the selection
may be below its end if you selected the text upwards. The caret
always lives at the end of the selection.
So, to represent a position of the current selection,
LEdit needs
four different things, which it stores in four numbers:
StartLine
- number of the line where the selection begins
StartPosition
- number of the symbol at which the selection begins within StartLine
EndLine
- number of the line where the selection ends
EndPosition
- Number of the symbol at which the selection ends within EndLine
When selection collapses and we see only the caret on the screen,
StartLine becomes equal to EndLine and StartPosition becomes
equal to EndPosition.
Besides being very effective with LEdit, this method of
positionning may be very useful for programmer. For example,
you'll probably want to tell user caret position inside the
text. With LEdit you get it directly.
However, this method has some disadvantages. For example,
it becomes less effective to calculate a size of the selection,
because LEdit needs to sum up the lengths of all the lines
within the selection.
Be LEdit's method of positionning good or bad, it's
the solely method you may use with LEdit because it's the
most effective and most natural method with LEdit.
|