Virtual Pen Project History résumé
(08/09/2002) 
23 December 2002
- The memory consumption seems almost stable now...
- Tried to draw something with Virtual Pen. The missing functions such as
duplicate, mirror, rotate, etc. would be very useful even for simple
drawings.
- Stumbled on a bug (not identified yet) with the undo/redo chain. When
doing a PurgeUndo, VP crashes mysteriously.
And when doing/undoing/doing/PurgeRedo, I
get tons of asserts (because of the fork ?).
22 December 2002
- Searching the reason of the wasted MB of RAM...
- Found a first culprit : VP::Render::GdiFigRegion
was not being cleaned up. It was therefore leaking GDI+ regions and paths
every time an object was drawn.
21 December 2002
- Fixed small alignment problem when dragging figures by their outline or by
their surface when a magnetic grid is active.
- The Bézier curve edition and creation classes now support the different
constrain modes (symmetry, locked angle, free).
- Simply moving the mouse around some time eats MB of memory. Why ?
20 December 2002
- Fixed VP.FrontEnd.Controllers.DocView to
avoid handling of ghost button release events. These events are generated
when the user dismisses a menu by clicking outside of it. The button press
event is consumed by the menu, but not the release event.
- Fixed problem in Magic library, used for the pop-up menus... Method InternalTrackPopup
of class VP.Magic.Menus.PopupMenu did
not propagate the WM_MOUSELEAVE event, and
this caused a lot of trouble with the MouseLeave/MouseEnter
.NET events, especially for the document view, which thought it was active
all the time...
- After a pop-up is displayed and dismissed, the click is sent to the
correct window, but since no mouse move event was sent before it, the
position of the click is wrong. This required the generation of a dummy
mouse move event.
- These little annoyances took about 10 hours to be fixed.
- Ready to add the sink commands into Bézier curve plug-in.
19 December 2002
- Working on the Bézier creator.
- Added commands to query the points while an object is being created.
- Added commands TestObjectIsClosedFigure and
QueryPointPos needed by the Bézier curve
creator and editor front end classes.
- Cleaned-up old references to A-ClosePath.
- The Bézier curve is now functional. It is not yet possible to change the
constrain mode of the primary grips, but otherwise, everything seems OK.
- Started work on a contextual menu which would be displayed whenever the
user right-clicks on a grip. What seemed simple is going to be tricky, since
I have observed strange behaviours with the mouse cursor...
18 December 2002
- Method VP::Render::Context::DrawHairLine
accepts an alpha value (to display the tangent control segments of the
Bezier curve).
- Updated the document object multiple point creator in order
to work with the Bézier curve too.
- Updated the Bézier core plug-in and fixed a few details.
- Fixed VP::Render::Context::TestPointInText
which did not properly calculate the position of the cursor in ligatures.
The current implementation is better, but still not perfect, since it
assumes that the ligature is composed of n equally wide sub-glyphs.
- Added information about raw cursor position in the cursor
event class, which is required by the text tool.
- Added a hint in the main tool cursor class, which specifies
whether a ghost cursor is allowed or not. Having a ghost cursor with the
text tool is rather annoying !
- Fixed figure/grip detection when using grid.
- The BelowCursorFinder class now properly
handles out-of-view events.
- Working on the Bézier creator.
17 December 2002
- Implemented the settings dialog for the grid.
- Worked on the Bezier curve implementation. This required work on other
classes in the front end.
16 December 2002
- Bugs never end... this could be last week's moto. While fixing the problem
found late yesterday evening, I stumbled on several other problems. And I
guess that the first beta testers will also find lots of bugs elsewhere. My,
my...
- Fixed VP::DocText::Meta::CollapseFontState
which did not remove the correct number of bytes when a font reset tag
cancelled another tag. Also cleanup any dangling format tags.
- Made class VP::DocText::Meta methods ClearBreakTags,
OptimiseBreakTags and GenerateBreaks
independent of the cursor's order.
- Added better debugging output in VP::DocText::Meta::DebugDump.
- Switched to the front-end... and added support for a new kind of plug-ins,
called a manager, which has no user interface, but needs to
communicate with the document view.
- In the document view controller, the cursor position used for detection is
always the raw one, not the filtered one.
- Added support for paint event registration and exported a few properties
needed by the Grid plug-in in class VP.FrontEnd.Controllers.DocView.
- Implemented a magnetic grid (no user interface yet, however).
15 December 2002 (Sunday)
- More bug hunting...
- Fixed bug in cursor backward movement (character by character). This was
the same problem as the one fixed the day before for the forward movement.
- Fixed VP::DocText::Meta::MoveBackwardsInText
which did not move consistenly across the tags, depending on the position of
the cursor in a skip tag.
- Fixed small bug in VP::DocText::Meta::CreateTempCursorB,
which caused VP to raise a fatal error in some cases (trying to skip past
the terminal fence tag).
- Improved method VP::TextLib::Scribe::GlyphLine::GetCaret
so that the caller can provide its own version of the font record. This is
needed, since only the text flow has enough information to know if the caret
should be displayed slanted, if the cursor lies between an empty <I></I>
sequence (no information is stored in the scribe for empty runs).
- Fixed cursor maintainance done by VP::DocText::Meta::NotifyCollapse
(if the cursor was pointing into the first skip tag of a collapsing tags
collection, then its skip tag offset was not reset).
- Fixed VP::DocText::Meta::CollapseFontState
to work in multiple line paragraphs and if the document is completely empty.
- When a selection gets erased, the active cursor is now systematically
placed inside the selection before doing any text removal (see right example
in image below, where after deletion of the word "how", the typed
text should be formatted in italic too).
- Improved ligature suppression : this is now only done in justified
paragraphs.
- The I-beam tool handles the ESC key : when it is pressed, the main
window is activated first, then the selection is discarded.
- Added support for font and paragraph attribute resetting : clicking
on an already active button in the tool palette's text tab can be used to
apply/reset the corresponding attribute. This works only when a selection is
active.
- Fixed a bug related to the use of VP::DocText::Meta::CollapseFontState,
which did not properly update the text flow after a change in the tags
stream, which could lead to line nodes pointing at the wrong place in the
text.
- Selections, even spanning several paragraphs, can now be changed with the ApplyFontState
command. This had far reaching ramifications...
- There is still a little omission in the CollapseFontState
method, which does not remove the trailing formatting tags of a paragraph,
but I am too tired to fix it this evening.
14 December 2002 (Saturday)
- Removed the Cursor::xxxAutoSync
mechanisms.
- Bug hunting.
- Added the CollapseTextState command, to
explicitely force the removal of useless formatting tags.
- Fixed bug in cursor advance (character by character), when reaching the
end of a line.
- There can be trouble when calling some methods of VP::DocText::Meta,
which rely on a correctly fitted text (tags with the TAG_SKIP_BREAK_ACTIVE
bit set) to detect the line boundaries. By swapping two method calls in
command InsertText, this problem could be
avoided. But there might be other cases !
- Improved VP::DocText::State::Serialiser::SerialiseState
in order to replace tags which would simply return to the style's default
state with their FORMAT_FontResetTag tags.
This is used by VP::DocText::Meta::InsertFontState.
- Fixed logic of VP::DocText::Meta::CollapseFontState.
- Fixed logic of VP::DocText::Meta::RemoveText,
in order to keep the font formatting tags. This avoids any problems in
following cases (deletion of italic style begin; inconsistent deletion of
italic style begin or end) :
|
 |
|
13 December 2002
- Improving the font format tag handling.
- When using text insertion commands or cursor movement commands, the
affected paragraph will be analysed and all duplicate/useless formatting
tags will be removed.
- Modified VP::DocText::Meta::MoveToLineBeginInText
to provide an easy means of finding the real beginning of a line in the tags
stream too.
- Added VP::DocText::Meta::NotifySkipTagChange for use by
VP::DocText::Meta::OptimiseSkipTags and
SplitSkipTag, which allows to work on the
text and tags streams without ever desynchronising the cursor records. This
paves the way to the removal of the Cursor::xxxAutoSync
mechanisms.
- Implemented VP::DocText::Meta::CollapseFontState
to remove the duplicate/useless formatting tags.
12 December 2002
- Fixed baseline alignment for the characters. The call to ExtTextOut
uses the mode specified by SetTextAlign
to position its output. TA_BASELINE does
what we need.
- Fixed highlighting gaps in the text. Because of some
rounding errors, white hairlines could show up between adjacent highlighted
characters (in VP::TextLib::Scribe::LineStore::PaintLine).
- Fixed H1/H2 adjustment happening when a line has not enough
vertical room on the first fitter iteration.
- The caller to VP::TextLib::Fitter::Context::ExtractWord can
now specify if he wants the method to consider the state changes, or not.
The state changes must be ignored if the caller is just interested in the
words, but not the geometry.
- Added command QueryTextSelectionLength.
- The I-beam cursor tool recognises if the activated flow had a selection by
executing the QueryTextSelectionLength
command.
- Spent a lot of time trying to debug the UxTheme wrapper DLL on
Windows 98.
- Fixed the fitter for the cases where the line fit got restarted. Several
local variables were not reinitialised, which caused the fitter to misbehave
with respect to end of lines.
11 December 2002
- Continuing work on text style edition.
- When a paragraph break is inserted in the middle of a paragraph, VP
creates a new paragraph with exactly the same settings as the previous
paragraph. This copies both the paragraph style and all the modified
paragraph formatting tags.
- The ApplyParaState command is now applied
to the whole selection.
- Added a new FormatDef tag, FORMAT_FontResetTag,
which can be used to reset a tag's value to its default value.
- Fixed VP::DocText::State::StreamParser::ExtractFormatText,
which did not properly extract the text if used in the non embedded
mode.
- Added command ApplyFontState.
- Implemented VP::DocText::Meta::InsertFontState,
which changes the font formatting locally. This caused a few display
problems to become visible (regular and bold fonts, for instance, do not
share the same baseline).
- Fixed the text fitter in order to properly handle font
format changes in words (the font change was considered as a text end in the
word extraction code).
- Some work for Crésus Gestion PE today, too.
10 December 2002
- Working for Crésus Gestion PE today.
9 December 2002
- Continuing work on text style edition.
- In class VP.Forms.Cmd.Sink.MessageFilter,
added an event which is fired whenever the number of keyboard consumers
changes, so we can disable the blinking text caret when the user is typing
into a text box or combo box...
- When clicking in a text flow, update the associated text styles.
- Fixed icon update on font style changes.
- First draft implementation of command ApplyParaState.
- Fixed bug in VP::DocText::Accessor::Synchronise
which moved to the wrong place.
- Added command QueryStateInText which is
used to determine the exact state at the specified cursor position in the
text stream.
- Class VP.FrontEnd.GUI.PaletteTabText now
uses the real paragraph state, not just the state defined by the active
style (it queries the exact state with the QueryStateInText
command).
- Fixed the forward/backward navigation in the text stream. Don't ever get
stuck between the paragraph style format tag (FORMAT_ParaStyle)
and other paragraph formatting tags (FORMAT_...
belonging to the FORMAT_CAT_PARAGRAPH
category).
- The reflection in .NET is great to build methods such as VP.FrontEnd.Logic.TextState.Delta.
It does all its calculations without knowning anything about the fields
represented in the text state, just by peeking and poking through the class
public methods.
7-8 December 2002
- Week-end. Some work for Cresus PE. No work on VP.
6 December 2002
- Implemented and tested command CreateTextFlow.
The current implementation of the text fitter does not support multiple
flows. This implies that I have to rework the fitter... and maybe the scribe
too.
After surprisingly few changes, VP now supports several text flows without
any trouble.
- Fixed a hyphenation problem in VP::DocText::Meta::AnalyseTextBreaks
with the last word in a text stream.
- Improved VP.FrontEnd.Logic.MainToolCursorIBeam
to create the text flow as required when attaching to an object which has no
text yet.
5 December 2002
- Added new text manipulation commands : QueryTextLength,
CreateTextFlow, DeleteTextFlow,
AttachFrameTextFlow, DetachFrameTextFlow,
QueryFrameTextFlow.
- Renamed DeleteText into RemoveTextBackwards.
- The bug hunting was successful :
- Added tests to the text style manipulation commands to avoid having them
crash VP if there is no active style.
- The caret won't be displayed if it is not active.
- The selected object will be actively displayed even if the text tab is
shown in the palette.
- Fixed hyphenated line width calculation : the hyphenated line length
did not take in account the hyphenated word, which caused VP to choose quite
bad hyphenation points.
- Fixed identifcal node optimisation : two nodes which point at the
same place in the text stream are considered to be identical only if they
will graphically appear at the same position.
- The break points displayed by command DebugBreakTags will be properly
displayed even if the window has been scrolled.
4 December 2002
- Continuing work on text formatting GUI logic.
- Fixed several minor bugs caused by abusive cyclic events in the text
formatting GUI.
- Added support for the optical names in the text formatting GUI (this is
fully transparent to the user).
- Improved blinking caret : when text is being displayed, the VP wastes
much less CPU cycles.
- Fixed cursor movement bug when a line ended with spaces : moving
forwards would detect the end-of-line when reaching the first space, which
is correct, but the MoveTextCursor
command expected that by skipping a single character, the cursor would reach
the next line. This is not the case.
- EPSITEC meeting this afternoon.
- Bug hunting.
3 December 2002
- Working on text formatting. The PaletteTabText
class is approaching an almost usable status.
- The font name analysis stumbled on some fonts where the base name included
the "Light" suffix, just as it would normally include an optical
suffix (such as "Display"). I added a list of exceptions. Maybe I
should do it the other way : define the optical suffixes and only
recognise those.
- Added a mode field to the text style, which allows to mark some styles as non
delete-able.
- The text state serialiser accepts a prefix of the fields to be serialised.
- Fixed the QueryFamilyStyles and FindFamilyStylesByName
commands.
- Made the tool panel by default transparent, which produces much nicer
looking icon bars in the palette.
2 December 2002
- Added command for font enumeration (doc.QueryFontList).
This command required a few changes in TextLib's
font information classes, the most important being the support for the optical
name of a font.
- Added a font information class in the front end : VP.FrontEnd.Logic.FontInfo.
This class can extract all pertinent information from the font information
provided by the core and organise it into family name, style name
and optical name (for instance "Warnock Pro",
"Regular", "Display").
- Improved class VP.Forms.ComboBox in order
to be able to generate events when the highlighted line in the dropped down
list changes. This could be useful to build a preview of the selected font.
- Improved VP.Unit.Value parsing and pretty
printing.
- Class VP.FrontEnd.Logic.TextState can
serialise its state to a string builder.
- Changed the font leading into a paragraph leading, which is
not as intuitive (the leading applies to the font height, but in fact it is
a property set for a whole paragraph).
1 December 2002
- Improved core event notification in the text related commands.
- Added preliminary support for the text state representation in the front
end (class VP.FrontEnd.Logic.TextState).
- Added a lot of widgets into the text tab. They do not do anything
yet.
30 November 2002
- Implemented text style usage counter and text style naming. The usage
counter is maintained automatically by class VP::DocText::Meta
when insertions and deletions are done in the text and tags streams.
- Implemented a set of commands used to manipulate styles and text styles,
which are needed by the front end in order to build the text GUI. Also added
new commands to list named styles in given families.
- Improved the text support in class VP::DocObj::Label.
Maybe we should switch to UTF-8
encoding ?
- Introduced new core events (Text_TextChanged
and Text_StyleChanged).
- Working on text GUI.
29 November 2002
- No real work on Virtual Pen today.
28 November 2002
- Improved and finished serialisation and deserialisation code for the
textual representation of the state record in VP::DocText::State.
- EPSITEC meeting.
26-27 November 2002
- Microsoft DevDays 2002 at Zurich Oerlikon. I did some refactoring
while travelling and during the most annoying conferences :
- Command parser accepts quoted strings.
- Added FORMAT_TextStyle and appropriate
handling in VP::DocText::State.
- Improved the serialisation and deserialisation code in VP::DocText::State
(it supports both the tags stream and a textual representation).
25 November 2002
- Fixed several small repainting bugs caused by the tool palette
refactoring.
- Added a splash screen.
- Started refactoring of the VP::DocText::State
class, in order to generalise the state serialisation and state
deserialisation code; we need to be able to exchange the internal state
representation with the higher level .NET front-end...
23-24 November 2002
22 November 2002
- Implementing the text user interface.
- Refactored the VP.FrontEnd.GUI.SamplePalette
class into a VP.FrontEnd.GUI.Palette class.
Extracted the attribute specific code to class VP.FrontEnd.GUI.PaletteTabFigure.
- Started implementation of the VP.FrontEnd.GUI.PaletteTabText
class.
21 Novembre 2002
- Design for the text user interface.
20 November 2002
- Still not feeling 100% fit.
- Added the doc.DebugTextBreaks command,
which shows all possible text breaks in a text flow. This is very useful to
understand how the paragraph fitter decides to break its lines. Should have
added this much sooner...
- Fixed left aligned lines which did not get compressed when displayed.
- Fixed glyph ligature stretching : when a line gets stretched, the
fitter no longer replaces glyphs with their matching ligature.
19 November 2002
- Sick today...
- SQL and SQL meeting at David's with Pascal Zweilin, Alex Maillefer, Daniel
Roux, Denis Dumoulin, Michael Walz, Yves Raboud and David Besuchet.
18 November 2002
- Sick today...
- Tested InstallShield software, which could be used to build an installer
for Virtual Pen. However, this product seems to be too rich for my needs
(and too expensive, too).
- Tested the PreInstaller (which is freeware), but it is only
available in German.
- Finally, worked on Microsoft's sample bootstrapper and got a
working installer, which sets up .NET before starting the installation, if
needed.
9 -17 November 2002
- No work. I had a break thanks to the Swiss Army...
8 November 2002
- Today is a special day : "Fête des 25 ans
d'EPSITEC"
...
- Added text deselection through Escape key.
- Added zoom in and zoom out buttons and menu commands.
- Added new attribute : VP::DocAttr::ImageFrame
is the equivalent to TextFrame for images.
- Added new tool to add images into arbitrary figures (VP.FrontEnd.Logic.MainToolCursorImage);
this tool creates an a.imageframe attribute
block which describes the image (the block contains a Label
object for the file name).
- Implemented a cache for the image frame, in order to speed up the display.
We should probably cache the stretched image to further improve the
performance.
7 November 2002
- Cleaning up the internal setup of the text frame attribute, in order to
make it a real attribute object. For now, this was just a collection of
hacks used to test VP's text rendering.
- Found a strange behaviour in the font rendering. The blackness of the
characters is not constant. Some text frames have very dark output, some
medium and some still lighter. This must be related to anti-aliasing, but I
do not know where to search. Here is a sample (from dark to light) :
|

|
|
- Associated more information to a text flow frame, in order to quickly find
the flow for a given object.
- Fixed bug in VP::TextLib::Fitter::ParaStore::FitLine
which prevented text to flow into multiple text frames.
- The FlowManager is now associated with the
document rather than the rendering context.
- The hit testing for text frames now restricts its search to the matching
frame rather than stopping at the first possible hit.
- Finally found the bug with the non constant character blackness. This was
the result of painting several times the same text at the same place... Now,
VP::TextLib::Scribe::LineStore::PaintLines
only paints the lines which belong to a specified flow/frame.
- Fixed text and caret/selection update details.
- Avoid painting the caret multiple times (same problem as for the text
output).
- Improved slanted caret positioning.
- Fixed small problem in VP::TextLib::Scribe::LineStore::CacheLine
which caused lines with ligatures to lose their trailing punctuation
marks.
- Written tons of OpenType structures and definitions in order to read the
ligature information in the fonts. This requires walking through the GSUB
(glyph substitution) table, looking for the 'liga',
'dlig' and 'rlig'
features, which in turn give access to lookup tables, which contain the real
information...
- I have working ligatures (23h55) !
6 November 2002
- Fixed font height calculation. What I called H1
in my terminology is represented by the font ascent and the font line
gap (taken from OUTLINETEXTMETRIC).
Using just the ascent produced text lines which were too condensed, the
caret was too short and the highlighting did not reach down to the bottom of
the chacters. Windows seems to be adding the gap before the line.
- Added support for displaying selected text. This is all handled by classes
in VP::TextLib::Scribe and class VP::TextLib::Flow.
- Implemented text selection with the cursor keys. Erasing the selected text
works, too.
- Implemented text selection with the mouse.
- Fixed a lot of small problems related to the caret and to its refreshing.
- Implemented double-click for word selection, triple-click for line
selection, quadruple-click for paragraph selection and ...yes...
quintuple-click for full text selection.
- Modified class VP::DocText::Style to make
it compatible with the other VP attributes. This was not the case, which
meant that a style containing a T.style object crashed the rendering engine
when it tried to analyse the style's attributes.
- Fixed document setup code.
5 November 2002
- Fixed yesterday's fix on keyboard filtering : the I-beam cursor
wasn't consuming any more events.
- Working on keyboard navigation in text flow. Implemented following cursor
movements :
- Move to begin/end of text flow.
- Move to next/previous paragraph end/begin.
- Move to next/previous line, moving vertically in the text. This is the
most complicated of all moves, since it requires geometric knowledge about
the text.
- Move to next/previous word. This was not as easy as expected because of a
lot of special conditions which must be taken in account.
- Fixed stream data insertion, which generated empty objects when
inserting/removing a pair of cursors.
4 November 2002
- Checking in yesterday evening fixes.
- UNICODE defines a lot of accented characters to be AI_AmbiguousAlphabeticOrIdeographic,
which does not make sense to me. These must be mapped internally to AL_OrdinaryAlphabeticAndSymbol,
or else the line breaking algorithm will behave badly.
- Added support for spying WM_CHAR,
WM_DEADCHAR and others in VP.Forms.Cmd.Sink.
- Fixed cursor record access in the document store (split
cursor records were not skipped properly).
- Fixed offset bug in caret position calculation, caused by
the possible clipping region.
- Added support for DELETE and BACKSPACE keys when editing
text.
- Fixed bug in VP::DocText::Stream::InsertData,
when overflowing into next object.
- Fixed bug in VP::DocText::Meta::GenerateBreaks
which caused the temporary cursor to fall within UTF-8 sequences.
- Fixed UnicodeHelper::AnalyseBreaks
to accept line breaks at the very beginning of lines. And also modified the
handling of trailing spaces in runs. This is no longer 100% Unicode standard
conformant when considering the extremities of a run.
- Fixed cursor handling in empty lines (line with just a line
break in it) in VP::TextLib::Scribe.
- Fixed badness calculation for zero-length lines.
- Naïve floating point comparisons caused VP::TextLib::Scribe
to store lots of runs instead of merging them.
- Improved cursor position detection.
- Added support for the HOME and END keys when editing text.
And again a few bugs surfaced in the text stream management. It was not as
simple as expected to locate a begin or an end of line in the text flow,
because nobody was setting the TAG_SKIP_BREAK_ACTIVE
flag after fitting a paragraph... This has been addressed.
- Fixed caret display if multiple spaces hang outside of the
right margin.
- Fixed the debugging tool so that its text box gets the
keystrokes which are intended for it.
3 November 2002
- Continuing work on text interaction.
- The shortcut message filter was consuming characters which were not meant
for it (for instance, pressing the DEL key whould delete the selected
object, even if the user was typing text in a text box). Class VP.Forms.Cmd.Sink
now has the basic mechanisms needed to disable part of this filtering when a
text consuming control has the focus.
- The active visual style of the main window and the palette was not
behaving as it did in other applications (such as Word, Photoshop and other
prominent applications). Clicking into a palette would deactivate the main
window, which was bad. And clicking in the main window would deactivate the
palette, which was bad too. I had to design a new GUI.TopLevelForm
class from which both the main window and the palettes derive, which does
some tricky event juggling in its WndProc
method.
Without the help of an article
adressing a similar problem in VB, I would still be trying to guess how to
get things right.
- Hunted bugs while trying to type text in a text flow...
2 Novembre 2002
- Continuing work on text interaction.
- Fixed clicking after a paragraph end : the position is now correct (Unicode::BK_MandatoryBreak
character is now set to STRETCH_Invisible).
This is also the case when clicking before the line begin.
- Added support for distinction between two same positions in
the text flow, which are displayed at different positions on the screen (end
of line before hyphen, start of line after hyphen).
- Implemented support for slanted cursor when italic fonts
are used.
- Implemented centered and right-aligned layout.
- Implemented the paragraph hyphenation settings in VP::DocText::StateRecord.
This required VP to be able to determine if a letter is a CAPITAL
LETTER or not (to avoid hyphenating capitalised words). This
information is now provided by the UnicodeHelper
class.
- Implemented text "compression" which packs the
glyphs as tight as possible to fit a line into less space than theoretically
required.
- Removed class VP::TextLib::Scribe::Renderer
(all its methods could be moved to LineStore)
and finished the cleanup of class VP::TextLib::Scribe::LineStore.
1 November 2002
- Working on text interaction.
- Finally got a blinking cursor...
- Added polygon hit detection (method VP::TextLib::PolygonTools::Contains).
- Added support for text detection : given a pair of [x,y] coordinates,
find which flow/line/character is affected.
- Fixed a nasty bug which was introduced on 28 August, as a side effect of
the thin line hack implemented by scaling the pen width by 100 (and
scaling by 0.01 when rendering the path). This caused the bounding box
computation to assume that the outline of the figures was very, very thick.
Therefore, most figures became unselectable by the rectangular selection
tool.
- Spaces and unbreakable spaces are both flexible; this makes much more
sense than Microsoft's choice in Word.
- Finished hit detection : automatically update the cursor position on
successful hit detection. But there are still a lot of small details which
must be taken care of :
- VP does not distinguish the position after the last character of a
hyphenated line and the first character of the next line; the cursor always
shows up at the beginning of the next line.
- VP does not properly handle the paragraph end control character embedded
in the text : clicking after the end of a paragraph's last line moves
the cursor to the next line, not to the end of the paragraph.
31 October 2002
- Integrating the low-level work done on the text management with the
front-end.
- Added an AttributeBlock.Find method to
search for a specific attribute in an object (the attribute is specified by
its UCID).
- Added support for named image definitions (the front-end can send bits to
the back-end, which remembers them as a GDI+ bitmap, for use by some objects
or by the view to display icons).
- The I-beam tool detects when it is over a non-textual object and provides
a visual feed-back.
- Delegated more decision to the tool plug-ins :
- The tools are notified of their future activation (OnAboutToActivate).
- The tools can specify a custom cursor to be used as the standard
cursor (GetCustomCursor).
- The tools can specify a special candidate hilite mode and filter the
candidates which should not be hilited (CandidateFilterDiscard).
30 Octobre 2002
- Continuing work on text layout.
- Added Freeze operation to the NodeStore
and ParaStore, which release the huge
virtual memory range they acquired through the turbo heap (see OPaC::Tools::TurboHeap::Freeze).
- Cleaned up the text frame attribute : consolidated the painting code.
- Fixed an old bug which caused VP to crash on document loading. The problem
was that nobody ever called the LoadPostProcessing
method of the management classes after a Load.
29 October 2002
- Partially cleaned up the sources written hastily yesterday.
- Fixed VP::TextLib::Fitter::ParaStore::Fit
and FitLine to properly handle truncated
paragraphs (if there are no more frames available).
- Improved text flowing when the containing polygon geometry is not ideal
(not wide enough at certain places to display the shortest word element).
- Extracted the experimental text rendering code into a dedicated GlyphRunManager
class.
- Implemented the real justification algorithm. For now, we do not
cache the results of the justification, but when the document will become
larger, our current, naïve, approach won't be fast enough.
- Enabled anti-aliasing of the displayed fonts.
28 October 2002
- Fixed small problem with active node deactivation.
- Replaced sub-optimal code in VP::TextLib::Fitter::ParaStore::CreateNode.
- Refactored the fitter classes; class ParaStore
is now much simpler to understand and the dedicated Scribe
namespace has been added to contain the justification code.
- The node now remembers the hyphenation point.
- Method VP::TextLib::Fitter::Context::ExtractWord
recognizes a text fence and rewinds the text and tags streams accordingly
when the fence is reached.
- Added Scribe::StretchDef which replaces
the simple boolean for the space/non-space character identification (this
will allow future support for kashidas and stretchable dashes).
- Cleaned up TextFlow.cpp source file.
Removed the outdated version of the fitter algorithm.
- Reorganised the internal font representation.
- The VP::DocText::State class now provides
direct access to the active font instance.
- First sample text displayed this evening... and printed too, after a few
adjustments. GDI+ and GDI do not change their coordinate systems the same
way, which caused a bit of head scratching.
|
 |
|
27 October 2002
- Working on the line justification algorithm. I made a first attempt at a
justification algorithm which would be executed while the fitter is doing
its job, in order to avoid having to reparse the text twice, but this
appears to be a poor choice; so I ended the day with no progress at all...
26 October 2002
25 October 2002
- Fixed a memory deallocation problem in the TurboHeap
code (the call to VirtualFree requires a
zero length when releasing memory).
- Method VP::DocText::Fitter::NodeStore::CreateNode
now recycles previous nodes and thus dramatically recudes the number of
active nodes in the defavorable cases.
- Reorganised the source file Fitter.cpp
into three distinct files : Fitter, FitterNodeStore
and FitterParaStore. Cleaned up and added
comments.
- Fixed a bug in VP::TextLib::Fitter::ParaStore::RewindToCount.
- Working on the paragraph/line justification algorithm.
24 October 2002
- The paragraph fitter did its first 100% bug-free fit at 16:00 (local time
;-) !
- Method VP::DocText::State::Setup still
contained a few problems. This is now fixed.
- Fixed a lot of details in the fitter code itself :
- VP::TextLib::Fitter::NodeStore::FreeDiscardedNodes :
don't get stuck in a loop.
- VP::TextLib::Fitter::ParaStore::DeactivateAndMoveToNextActiveNode :
accept active nodes, but also accept output nodes.
- VP::TextLib::Fitter::ParaStore::SelectBestOutputNode :
update the output node index after discarding those which are no longer
needed.
- VP::TextLib::Fitter::ParaStore::ExtractWord
and others now return the offset in the text with respect to the context's
text/tags stream positions.
- Added support for following features in the fitter :
- Quality setting for the fit (progressive quality degradation).
- EndOfText and ErrorNeedMoreFrames
event handling.
- Implemented the missing VP::TextLib::Fitter::ParaStore::CreateNode
method.
23 October 2002
- Testing and debugging the paragraph fitter.
- While testing the paragraph fitter code, I stumbled over a few bugs hidden
in already tested code :
- Fixed VP::DocText::Meta::SynthesizeBreakTags :
when UTF-8 characters used more than one byte, then the resulting break tags
would become desynchronised.
- Fixed VP::DocText::Accessor::Synchronise :
moving backwards could cause accesses outside of the stream, since the
recorded original offset was sometimes wrong.
- Fixed VP::DocText::State::Setup which did
not properly reinitialise the internal parsing parameters and caused re-runs
of the same text to become desynchronised with respect to the tags stream.
22 October 2002
- Continuing work on the paragraph fitter. Adding real OpenType
measurements.
21 October 2002
- Worked on OpenType integration.
17 October 2002
- Continuing work on the paragraph fitter. 90% of the fitter is in place,
but there are still a lot of places where functions still need to be fully
implemented.
16 October 2002
- Resuming work on the paragraph fitter.
12-15 October 2002
- Week-end and two days off duty, reading a very interesting article on what
typographers expected from Adobe's K2 project (which turned out to be
InDesign).
11 October 2002
- Continuing implementation of the new paragraph fitter.
10 October 2002
- End of design of the paragraph fitter. I am happy with the result.
- Started implementation of the new paragraph fitter. This will take a few
days !
- Implemented a TurboHeap class which can be
used to allocate memory as a contiguous array very quickly, without
committing memory before it is really needed. This is based on virtual
memory allocation (the default is to reserve a chunk of 16 MB in
virtual memory and grow it as needed), which guarantees that the logical
addresses of the allocations will be contiguous.
7-9 October 2002
- I stopped working on the paragraph fitter. More design is needed before I
can start coding something useful and extensible. I hope to have all ideas
put down on paper tomorrow (10 Oct.).
5-6 October 2002
- Continuing work on paragraph fitter.
- Cleaned up code and structures used by the fitter.
- Added a FitGlyphRange structure used to
store the glyphs and the associated width information, which will be used to
cache the text to speed up the calls to ExtTextOut.
4 October 2002
- Working on the paragraph fitter (added a few text fitter related
structures).
- Fixed a few problems with VP::DocText::Accessor.
- Implemented a DebugDump method in VP::DocText::Meta,
which helped me find several bugs :
- The file Document.cpp contained invalid
testing code which broke the text stream and tags stream integrity, causing
some strange bugs in the fitter...
- The file Document.cpp initialised the
text formatting style too late, which caused some paragraphs to have invalid
paragraph style IDs, breaking once more the fitter.
- The VP::DocText::Meta::RemoveText method
was off-by-one in the tags stream (in the cases where the starting position
pointed into a skip tag range), which caused an incorrect number of tags to
be removed and brought the streams out of sync.
3 October 2002
- Hacked a bit in the code to make things progress faster, and help me find
some additional bugs. The a.textframe uses a
manually created text flow and meta text block to allow for some simple
experimentation.
2 October 2002
- Added support for text and tags generation IDs in VP::DocText::Meta,
which can be used to find out whether a specific pointer into the text is
still valid or not.
- Added flow management classes in VP::TextLib.
- Added support for a special kind of unit (i24)
which encodes a raw 24-bit unsigned integer, used to store indexes into
objects, such as a.textframe.
- Updated the flags defined by VP::Render::Context,
and their use in the different document management classes. This cleanup was
the consequence of trying to understand how they worked... and failing.
- Working on the Text Frame attribute (a.textframe),
which calculates the geometry of a text frame, based on a path definition
provided by any kind of object. Added interaction with the Text Flow.
1 October 2002
- Rewritten VP::DocText::Meta::InsertText to
handle the paragraph style format tags.
- Read the Guide du typographe romand.
30 September 2002
- Continuing work on state and format processing.
- Rewritten the text deletion method (VP::DocText::Meta::RemoveText)
to properly handle format tags. The old implementation relied on the user to
provide a number of characters to remove, which would not take in account
the complex logic behind cursor movement (which ensures that the cursor
never points to an invalid position, e.g. between a paragraph end
character and a paragraph style tag).
- Fixed VP::DocText::Meta::MoveBackwards,
which could get stuck in an infinite loop.
- Updated VP::DocText::Meta navigation
methods to handle the FORMAT_ParaStyle
formatting tag.
- Added a first version of VP::DocText::State::SerialiseState.
- Working on VP::DocText::Meta::InsertText
to properly handle the paragraph separation marks, which require the
insertion of special format tags (FORMAT_ParaStyle).
- Added paragraph style accessing code to VP::DocText::Meta
and VP::DocText::Format.
28-29 September 2002
27 September 2002
- Working on the text state and format tag processing :
- Added VP::DocText::State class to manage
state computation based on a position in the tags/text streams.
- Added VP::DocText::StateRecord structure
to store the information about the active state.
- Added VP::DocText::Style to store the
text style information (this is in fact a tags stream, but it is
guaranteed to contain contiguous data; there will never be a linked list of
text style objects).
- This is a day with a lot of new code :-)
26 September 2002
- Refining the format description for paragraphs, characters and text in
general. Originally, I planned to use a format stream to store
additional information on the formatting, but this is not a good idea. Put
all the formatting information directly into the tags stream and only
longer arguments (such as font names) into the format stream.
- Implemented access to format data in VP::DocText::Meta,
based on a cache. This can be used to find, allocate, store and remove
pieces of format data identified by a 16-bit format ID. It is also possible
to make sure that two pieces of data with the same content won't get
duplicated by searching first for a matching format data record.
- Re-refactored the font listing mechanism used by VP, in order to classify
the fonts in families (based on their preferred family as specified
by OpenType, not as provided by brain-dead Windows API). Now fonts such as Warnock
Pro Light and Warnock Pro Semibold belong to the same family as Warnock
Pro Regular.
25 September 2002
- Started implementation of paragraph splitting.
- Nice Adobe fonts with typographic finesse :
- I had to redesign the font management code in Virtual Pen to avoid GDI+
completely, since the OpenType fonts from Adobe did not show up in the list.
This took me about 5 hours to try to figure out where I had done something
wrong, and 1 hour to rewrite my code to use plain old GDI.
- Defined a format record, which contains cache-able information (amongst
which a pointer to a VP::TextLib::FontRecord
object).
24 September 2002
- Working on paragraph splitting. I am going to use a modified version of
Knuth's algorithm, which is the best to date, to my knowledge...
- Found an article on direction and language specification related to
HTML : http://www.w3.org/TR/REC-html40/struct/dirlang.html.
- The UTF-8 specification is part of RFC2279.
- Unicode characters in the range U+E000 up to U+F8FF included are defined
as private area. This is split into an end user zone and a corporate
user zone (U+F000-U+F8FF). Some vendors such as Apple (U+F800-U+F8FF,
Apple Logo U+F8FF), Microsoft (U+F000-U+F0FF), Adobe (U+F600-U+F7FF),
Linux (still evolving in the CUS, Klingon
starting at U+F8D0) use this for characters not found in the standard
Unicode range (e.g. partial glyphs from the Symbol font). And some
would like to standardise
the use of the private are for fictional character sets. Some Commodore fans
would like to use part of the CUS for PETSCII.
How should these characters be handled by Virtual Pen ?
What character codes may I select for Virtual Pen's internal use ?
It is better not to use any private area codes, if possible. For now,
I will stick to characters 02 (ASCII SOT) and 03 (ASCII EOT) as markers
for begin and end of text inclusions (such as foot notes or URL targets).
- Lots of thinking, no coding...
23 September 2002
- Integrated Daniel's hyphenator with VP::DocText::Meta.
- Split the large VP::TextLib::Meta::GenerateBreaks
method into a main method and four sub-methods, which implement following
funcitonality :
- Find start of zone and create temporary cursor A.
- Find end of zone and create temporary cursor B.
- Break according to Unicode rules and hyphenate the alphabetic text.
- Update the skip tags and insert break tags as needed.
- Added a text distance measurement method to VP::TextLib::Cursor
class.
- Debugged thoroughly (at least I hope so) the break tag generation and
management.
22 September 2002
- Working on line splitting at the text tags stream level.
- Fixed a bug in VP::DocText::Accessor::Read/Write,
which caused navigation problems.
- Fixed a bug in the hyphenator initialisation, which caused the the default
hyphenator to be deleted without notice (and caused mysterious crashes in
method VP::TextLib::Meta::GenerateBreaks).
- Fixed a bug in VP::DocText::Cursor::Find,
which caused cursor deletions to remove the wrong cursor record.
- The line breaking algorithm is now working with a byte provider rather
than a string, which allows a better implementation of the break analysis
(the source must no longer be copied into a temporary buffer before it can
be used).
- The tags used to mark breaking positions in the text were not sufficient
(formerly, I had just the break here and break option flags).
The following information needs to be encoded into the break tags :
- No break can happen here.
- A break must always happen here.
- A break might happen here if needed (word boundary).
- A hyphenation and a break might happen here if needed (hyphenation within
a word).
It would be nice to also be able to record the quality of the hyphenation
(poor, good, best).
- With the current layout, a break is done here (active break).
- This information needs more than just 2 bits to be properly encoded. The
first 4 states (6, counting the hyphenation quality) fit into a 2-bit
(3-bit) field. The last information is a flag (break or no break). I finally
selected following layout :
TAG_SKIP 0b xxx nnn
TAG_SKIP_BREAK_ACTIVE -b --- ---
TAG_SKIP_BREAK_STATUS -- xxx ---
TAG_SKIP_VALUE -- --- nnn
- This reduces the range which can be encoded with TAG_SKIP
to 1..7. It would be possible to encode a
wider range with the 3 bits (e.g. 1, 2, 4, 8, 16, 32, 64), building the
intermediate values by summing up skip tags. This does not make sense,
however, since most words are less than 8 characters, or can be hyphenated
into short character sequences.
21 September 2002
- Continuing work on font management and line geometry measurement. Mostly
worked on OpenType interface.
20 September 2002
- Added break handling for embedded objects (Unicode character 00FFFC),
through interface IObjectBreakInfoProvider.
- Implemented Unicode-character-class based line breaking algorithm. This is
based on the Unicode
Standard Annex #14 and on file LineBreak.txt
provided by the Unicode Consortium.
Here are a few related articles :
- Working on the hyphenator, which meant restructuring part of the Unicode
related code in TextLib.
- Working on the font management.
19 September 2002
- Tried to find an elegant work-around for the cursor update bug, but
getting the updates right is very difficult and quite inefficient. To
simplify the design, I decided to add support for a temporarily incoherent
cursor state (VP::DocText::Cursor::StopAutoSync
and ResumeAutoSync).
This is now implemented and works...
- Worked a bit on MSDE for Daniel's project. Nice thing, this light
SQL Server.
18 September 2002
- Fixed coherence problem with VP::DocText::Meta::RemoveText
(the bug was found thanks to the use of the new VP::DocText::Cursor::IsCoherent
function).
- Added VP::DocText::Meta::ClearBreakTags
and VP::DocText::Meta::OptimiseBreakTags.
- Added support for virtual cursor IDs, for
both special cases : begin and end of stream.
- Added word break detection, as specified by the UNICODE Consortium :
this requires that VP parses a LineBreak
description file in order to extract the break class of every Unicode
character.
- Found a bug with the cursor updates, when optimising a skip tag stream.
17 September 2002
- Continuing work on VP::DocText namespace.
- Fixed VP::DocText::Stream::MoveBackwards
and VP::DocText::Meta::MoveForwardsInText.
- Finished, tested and fixed VP::DocText::Meta::MoveBackwardsInText.
Text navigation is therefore fully implemented now.
- Added more functions to the accessor (in order to check a cursor's
coherence, that is, make sure that the text position is the same as the tags
position, as specified by the skip tags).
14-16 September 2002
- Week-end (Jeûne Fédéral).
13 September 2002
- Continuing work on VP::DocText::Meta :
backwards navigation.
12 September 2002
- No work for EPSITEC today... but days have evenings.
- Debugged the VP::DocText::Meta::MoveForwardsInText
method, which crashed in case of a stream overrun.
- Debugged the VP::DocText::Cursor class,
which had a few problems :
- Finding a cursor could get stuck in an infinite loop. ü
- Accessor synchronisation now returns false if there is no more
data available, as expected. ü
11 September 2002
- Continuing work on VP::DocText::Meta
management class, to add support for higher level text manipulation and
navigation. While doing this, I realised that there were a few flaws in the
design : some tags are irrelevant and difficult to handle properly (the
kerning pair adjustment, specifically). So here we go : re-engineering
of the tags is in progress.
- Added simplified failure management with the VP::Failure
function; used it for some stream navigation methods.
- Implemented forward navigation in the text/tags stream.
- Daniel Roux has implemented a word breaking algorithm for the French
language (the basic algorithm was originally developed for the Smaky
computer and implemented in the COUPE
library).
10 September 2002
- The following low-level functions are now implemented and partially
tested :
- UTF-8 text insertion, staying in sync with the tags. ü
- UTF-8 text removal, partial tag management. ü
- Implemented in-place manipulation of data in the VP::DocText::Stream,
properly handling the fact that the data can be distributed over several
objects. The data access is coupled with an optional relative distance,
which can be used to peek at data before the current position (e.g. the
previous tag) without having to explicitely move the stream index/offset.
- The cursor record needed additional information to properly handle skip
tags (it is possible that, while moving through text, the cursor points into
a skip tag; a relative skip offset is needed here).
9 September 2002
- Added dumping support for the VP::DocText::Cursor
object.
- Defined the command tags used by VP::DocText::Tags.
- Added support for the UTF-8, UTF-16 and UTF-32 Unicode
representations. Internally, the text is stored as UTF-8, which is simple to
manipulate.
7-8 September 2002
- Week-end.
- Defined the hyphenation engine, so that it can get implemented by others.
6 September 2002
- EPSITEC meeting today.
- Handle properly cursors pointing into deleted
stuff thanks to the DocText::Meta::NotifyCollapse
method.
5 September 2002
- A compiler bug caused the polygon tools to fail compiling : somehow,
a call to VP::Point::operator = in the VP::TemplateSABase<VP::Point>::Remove
was the origin of the mess.
- Implemented data removal from the text stream and tested both insertion
and removal. Everything seems to be working properly.
- Implemented basic text cursor management : when an insertion or
deletion affects a cursor position, it gets updated automatically.
4 September 2002
- Continuing work on text stream.
3 September 2002
- Implementing the basic text objects used for internal data
representation :
- VP::DocText::Story, block containing
the text story (the text meta information, the text itself, the text
tags, the text formatting and the text cursors).
- VP::DocText::Meta, meta information
about a text story.
- VP::DocText::Text, the text itself,
stored as a UTF-8 stream.
- VP::DocText::Tags, the text tags,
stored as a stream of bytes encoding skip marks, kerning deltas,
typographic variants, state changes, etc
- VP::DocText::Format, the formatting
information associted with the text tags.
- VP::DocText::Cursor, position
information pointing into the text stream and maintaining the current
state.
- Added a base class for Text, Tags,
Format and Cursor,
which is VP::DocText::Stream. It contains
all the common insertion/removal/navigation logic.
- Added support for cacheable data to the document store : an
object tagged with the OBJFLAG_CACHE
flag will be handled specially by the object store, on deletion.
2 September 2002
- Fixed bug in polygonal path validation.
- Implementing font management code.
History of previous months.
- To do soon :
- Further improve the line style edition dialog (width, cap, join,
miter); a job for Daniel ?
- Finish the polygon plug-in; a job for Daniel ?
- Allow reordering of attributes in the attribute panels (e.g. color
first, transparency last).
- Change the way layers are represented in pages.
- Restore Bézier curve functionality.
- Adding support for grouping objects.