Board index » delphi » Re: Syntax highlighter for cascading stylesheets

Re: Syntax highlighter for cascading stylesheets


2004-02-04 05:47:20 PM
delphi205
Gerrit Beuze writes:
Quote
>How should I do that? Inherit from TCustomHighlighter,
>TAggregateHighlighter or TDelegateHighlighter?

inherit from TCustomHighlighter.
The other types are used to extent / modify existing highlighters.
Right, that is the conclusion I also came to. But it is nice to get some
verification ;) I must admit though, that the though of extending and
modifying existing highlighters are QUITE exciting. E.g. it would be
possible to get the pascal highlighter to highlight e.g. Integer and
Boolean as reserved words.
--
Thomas Due
Software Developer
Scanvaegt Nordic A/S
Posted with XanaNews version 1.16.1.6
 
 

Re: Syntax highlighter for cascading stylesheets

"Gerrit Beuze" <XXXX@XXXXX.COM>writes
Quote
Hello Ryan,

I had a look at your source.
I think that the problems ("issue") on closing packages / dll are caused
by bad interface refcounting. I had similar problems a few years ago in
the IDE
and they all went away when I changed to real ref counted objects.
What I think that happens is this:
You install an notifier in the IDE, this saves that as a refcounted
interface pointer.
The IDE now assumes that as long as it has a non-nil in that ref, it's
valid to
access it. When the IDE wnat to delete your highlighter, it sets this ref
to nil,
which will call _release: but you have already deleted the implementing
objet=>AV.

Gerrit, Thanks for taking a look at it.
I started out with reference counted objects. It wasn't the destruction of
my objects that caused the problem. It is the specific scenario that I
+remove+ the prior borland supplied highlighter (but keep a reference to it
so it is reference count is still good) and then add my own in it is place.
During destruction I tried both not installing the old syntax highlighter
back in place as well as not causing it to decrement it is reference count
when I did my cleanup. I also had code in place to ensure I knew none of my
methods were being referenced during shutdown. That was all snipped out
prior to putting the cc entry in place.
To be honest I think they probably keep track of the index they added the
borland highlighter and then try to RemoveHighlighter( myID ) during cleanup
(but that ID is no longer valid).
While trying to get the delegate to work I tried the following scenarios:
- ref counted as it should be
- as a loaded library instead of packaged
I will probably take another run at again since I think wrapping the
highlighter is more beneficial adding a new one but I am not confident it is
a supported use case ;)
 

Re: Syntax highlighter for cascading stylesheets

"Thomas Due" <XXXX@XXXXX.COM>writes
Quote
Gerrit Beuze writes:

>>How should I do that? Inherit from TCustomHighlighter,
>>TAggregateHighlighter or TDelegateHighlighter?
>
>inherit from TCustomHighlighter.
>The other types are used to extent / modify existing highlighters.

It is definitely more complex/complete then is required but I struggled with
a reason for making a highlighter so I thought of adding an on the fly spell
checker to the existing highlighters that only spell-checks string variables
(highlight them with atHotlink for example). Just something quick and dirty,
not sure it would have any value other than a learning experience.
For a from scratch highlighter use the TCustomHighlighter.
Quote
Right, that is the conclusion I also came to. But it is nice to get some
verification ;) I must admit though, that the though of extending and
modifying existing highlighters are QUITE exciting. E.g. it would be
possible to get the pascal highlighter to highlight e.g. Integer and
Boolean as reserved words.

Isn't it. Let it do the grunt work and you do the decorations ;). While I
found the aggregate method worked quite well I didn't have any great
successes with the delegate method. Hopefully something will turn up in that
regard. I think that replacing the existing highlighter makes it seamless
rather than having the user have to point specifically at your highlighter.
 

Re: Syntax highlighter for cascading stylesheets

Hello Ryan,
Quote
I started out with reference counted objects. It wasn't the destruction of
my objects that caused the problem. It is the specific scenario that I
+remove+ the prior borland supplied highlighter (but keep a reference to it
so it is reference count is still good) and then add my own in it is place.
During destruction I tried both not installing the old syntax highlighter
back in place as well as not causing it to decrement it is reference count
when I did my cleanup.
Did you try code like this:
destructor TDeletegateHighlighter.Destroy;
begin
try
// this causes an implicit ._Release if non-nil and might
// be the reason for the AV
FDelegate := nil;
except
OutputdebugStr(...)
end;
inherited Destroy;
end;
If that is the case, you could replace it with
destructor TDelegateHighlighter.Destroy;
begin
Pointer(FDelegate) := nil;
// or FillChar(FDelegate, SizeOf(FDelegate), 0); // or is it size first
inherited Destroy;
end;
and also not not assign it that way:
Pointer(FDelegate) := FindHighlighter( FAggregateID );
Quote
To be honest I think they probably keep track of the index they added the
borland highlighter and then try to RemoveHighlighter( myID ) during cleanup
(but that ID is no longer valid).
That could be...
Quote
While trying to get the delegate to work I tried the following scenarios:
- ref counted as it should be
- as a loaded library instead of packaged
That does not make a difference in the object life time management:
the dll requires to be build with packages too. I am using both all the time.
Quote
I will probably take another run at again since I think wrapping the
highlighter is more beneficial adding a new one but I am not confident it is
a supported use case ;)
That could be the problem yes,
Good luck with it and make sure post changes, it is an interesting project,
Gerrit
 

Re: Syntax highlighter for cascading stylesheets

"Gerrit Beuze" <XXXX@XXXXX.COM>writes
Quote
Did you try code like this:

Yes, tried both methods, good stock ref count fighting ;)
Quote
and also not not assign it that way:

Pointer(FDelegate) := FindHighlighter( FAggregateID );

Didn't try this one, wanted to explicitly keep the reference count accurate.
But, it is worth trying.
Quote
>While trying to get the delegate to work I tried the following
scenarios:
>- ref counted as it should be
>- as a loaded library instead of packaged
That does not make a difference in the object life time management:
the dll requires to be build with packages too. I am using both all the
time.

I know it shouldn't but I was trying to eliminate the possibility.
Quote
Good luck with it and make sure post changes, it is an interesting project,

If I find a fix for the delegate I will update the cc entry but I know I
will give Thomas' one a try if he makes it publically available.
btw, must say I do like the MM that was included with D7, congrats on a fine
tool.
 

Re: Syntax highlighter for cascading stylesheets

Ryan VanIderstine writes:
Quote
If I find a fix for the delegate I will update the cc entry but I
know I will give Thomas' one a try if he makes it publically
available.
I'm honored. I an planning on releasing it as open source, once I got
it working to my liking. Might take time though, what with my workload
and all.
--
Thomas Due
Software Developer
Scanvaegt Nordic A/S
Posted with XanaNews version 1.16.1.7
 

Re: Syntax highlighter for cascading stylesheets

Thomas Due writes:
Quote
Ryan VanIderstine writes:

>If I find a fix for the delegate I will update the cc entry but I
>know I will give Thomas' one a try if he makes it publically
>available.

I'm honored. I an planning on releasing it as open source, once I got
it working to my liking. Might take time though, what with my workload
and all.
I actually got something working. Most of the css color coding should
be finished, as far as I can tell. There are most likely bugs, and it
is certainly not the prettiest code I have produced.
I have a few problems though. The highlighter does not always work
correctly. Especially when I scroll down a page using either the
scrollbar or <ctrl-down>/<ctrl-up>. The problem is that the identifiers
(tag names) is not colored correctly. Also sometimes the insides of a
block is colored as if it was an identifier.
The coloring problems is solved by clicking with the mouse, but that is
not really a good "workaround". I have uploaded the source to the
attachment group in this thread: "CSS Highlighter for Delphi 7"
(nntp:<XXXX@XXXXX.COM>)
--
Thomas Due
Software Developer
Posted with XanaNews version 1.16.1.7
 

Re: Syntax highlighter for cascading stylesheets

"Thomas Due" <XXXX@XXXXX.COM>writes
Quote
Thomas Due writes:

I just downloaded and installed it. I noticed the color problems and it
seems to upset the ide into access violations (not sure why, doesn't look
like it would). I will poke around with it a bit.
Thanks for uploading it.
 

Re: Syntax highlighter for cascading stylesheets

Ryan VanIderstine writes:
Quote
I just downloaded and installed it. I noticed the color problems and
it seems to upset the ide into access violations (not sure why,
doesn't look like it would). I will poke around with it a bit.
Yeah I struggled with the AV too. It _seems_ that it happens if I miss a
character in HighlightCodes.
But _man_ there are lot of eventualities to take into account ;)
--
Thomas Due
Software Developer
Posted with XanaNews version 1.16.1.7
 

Re: Syntax highlighter for cascading stylesheets

"Thomas Due" <XXXX@XXXXX.COM>writes
Quote
Ryan VanIderstine writes:

Yeah I struggled with the AV too. It _seems_ that it happens if I miss a
character in HighlightCodes.

You should be able to clear those up with the following code at the start of
the Tokenize method
var
i: Integer;
p: POTASyntaxCode;
begin
if LineBufLen <= 0 then Exit;
p := HighlightCodes;
for i := 0 to LineBufLen - 1 do begin
p^ := 0;
Inc( p );
end;
Sometimes the highlight codes are altogether out of wack (in the incoming
bytes) so I assume you are responsible for actually setting them each and
every time. Rather than using 0 you might use atHotLink so it points out
where you are skipping chars if you are doing that. The code above will do
it but you can probably get away with a FillChar( p^, LineBufLen, 0 ); for
an added performance boost.
I did play with it a bit. I think you will need to use the TokenizeLineClass
to assist in classifying the lines. I started playing your code a bit but
found a pretty strange behaviour. I set up line classes of (0, 1, 2) which
map to normal, start of a comment, and in a comment. However, when I return
the type that line maps to it actually uses the +last+ one I returned (i.e.
so line #2 has the StartClass I returned for line #1 and so on).
Anyway, it was nice to see highlighted css files even if it was a bit on the
buggy side.
Perhaps one of the Borland people can shed some light on the LineClass bits
and any other helpful hints.
 

Re: Syntax highlighter for cascading stylesheets

Ryan VanIderstine writes:
Quote
Sometimes the highlight codes are altogether out of wack (in the
incoming bytes) so I assume you are responsible for actually setting
them each and every time. Rather than using 0 you might use atHotLink
so it points out where you are skipping chars if you are doing that.
The code above will do it but you can probably get away with a
FillChar( p^, LineBufLen, 0 ); for an added performance boost.
Yeah, the link I referer to in an earlier post in this thread
(nntp://newsgroups.borland.com/borland.public.delphi.opentoolsapi/11029)
the author does exactly this.
Yikes, I just tried something, and the IDE crashed _hard_. No AVs no
nothing, it simply shutdown. I think I might have done something a wee
bit wrong...
--
Thomas Due
Software Developer
Posted with XanaNews version 1.16.1.7
 

Re: Syntax highlighter for cascading stylesheets

Ryan,
Quote
Sometimes the highlight codes are altogether out of wack (in the incoming
bytes) so I assume you are responsible for actually setting them each and
every time. Rather than using 0 you might use atHotLink so it points out
where you are skipping chars if you are doing that. The code above will do
it but you can probably get away with a FillChar( p^, LineBufLen, 0 ); for
an added performance boost.
You are correct. The highlight codes for each character in the stream must
be
set each and every time the line is tokenized. The highlight codes that
should be used
are the atSymbol, atIllegal, atComment, etc codes that can be found in the
ToolsAPI unit.
Quote
I did play with it a bit. I think you will need to use the
TokenizeLineClass
to assist in classifying the lines. I started playing your code a bit but
found a pretty strange behaviour. I set up line classes of (0, 1, 2) which
map to normal, start of a comment, and in a comment. However, when I
return
the type that line maps to it actually uses the +last+ one I returned
(i.e.
so line #2 has the StartClass I returned for line #1 and so on).
TokenizeLineClass is used to tell the next line what state it is starting
in. As an example,
if you define constants representing the state of a line (say lcNormal and
lcComment) and
TokenizeLineClass returns lcComment, then that means that the line after
this line in the editor
buffer will be called with a start class of lcComment to let you know that
you're starting
the tokenizing in the middle of a comment.
HTH,
-Adam
 

Re: Syntax highlighter for cascading stylesheets

"Adam Markowitz" <XXXX@XXXXX.COM>writes
Quote

TokenizeLineClass is used to tell the next line what state it is starting
in. As an example,
if you define constants representing the state of a line (say lcNormal and
lcComment) and
TokenizeLineClass returns lcComment, then that means that the line after
this line in the editor
buffer will be called with a start class of lcComment to let you know that
you're starting
the tokenizing in the middle of a comment.
Thanks Adam, that makes perfect sense as soon as you mention it.
 

Re: Syntax highlighter for cascading stylesheets

You're welcome :)
-Adam
"Ryan VanIderstine" <XXXX@XXXXX.COM>writes
Quote
"Adam Markowitz" <XXXX@XXXXX.COM>writes
news:402a705b$XXXX@XXXXX.COM...
>
>TokenizeLineClass is used to tell the next line what state it is
starting
>in. As an example,
>if you define constants representing the state of a line (say lcNormal
and
>lcComment) and
>TokenizeLineClass returns lcComment, then that means that the line after
>this line in the editor
>buffer will be called with a start class of lcComment to let you know
that
>you're starting
>the tokenizing in the middle of a comment.

Thanks Adam, that makes perfect sense as soon as you mention it.