Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
Hi,

When I type "<a", the intelliprompt pops to complete the code/word. How do I start to show another list when I type: "<a cl.." (it should start when I start pressing the spacebar).

I hope you understand what I'm trying to say.

[Modified at 07/13/2011 08:09 AM]

[Modified at 09/01/2011 10:03 AM]

Comments (36)

Posted 13 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar


Actipro Software Support

Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
Hmmm... Any simple example available?
Don't really understand what's being said there. (noob)
Posted 13 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar
Sorry we don't have any examples. But as mentioned in that other post, you'd want to handle KeyTyped event and see if a character was being typed (a-z). If so, get a TextStream (from Document.GetTextStream()) at the current caret offset. Then back up one character in the stream and see if it is at a word start (stream.IsAtTokenStart can probably tell you that). If so you know a new word was just typed and then you can tell your language to show a member list.


Actipro Software Support

Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
Can you give me a jump start here: "If so, get a TextStream (from Document.GetTextStream()) at the current caret offset." I don't mind C# code. I need to understand how to begin in code.
Private Sub SyntaxEditor1_KeyTyped(sender..)handles....
'''code... how to begin
En sub

Thanks for answering my question above.
Posted 13 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar
Probably something like this in a KeyTyped handler:
// If the typed character was a letter...
if (Char.IsLetter(e.KeyChar)) {
    // See if a new token starts after the character that was typed
    var stream = editor.Document.GetTextStream(editor.Caret.Offset);
    if (stream.IsAtTokenStart) {
        // See if the character that was typed started a new token
        stream.ReadCharacterReverse();
        if (stream.IsAtTokenStart) {
            // Show member list here
        }
    }
}


Actipro Software Support

Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
Great example. Will try it and let you know.
Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
okay,

I looked up the example "htmldynamicsyntaxlanguage" an found the following which contains the "master" intelli-members. (Protected Overrides Sub OnSyntaxEditorTriggerActivated(ByVal syntaxEditor). How do I create a new one (memberlist) and call it? Can't figure it out. Sorry for being such a noob.

Let say, I type <a + space: the new memberlist appears or a type <abbr + space and another memberlist appears. The most important is how to create a new one and how to call it.

[Modified at 07/15/2011 04:44 PM]
Posted 13 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar
The OnSyntaxEditorTriggerActivated method you saw is showing how you can create and display a member list. You can create keypress triggers that activate in certain lexical states when various keys are pressed and then use that method to handle those and display a member list.

If you look in the ActiproSoftware.HTML.xml file (C# project) you can see where triggers are set up. You make them for a character and which states they are for. It looks like we might already have one configured for tag attributes too.


Actipro Software Support

Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
Hmm... I still don't understand how to create the memberlist. Do I need to add them into the existing one? To bad there isn't a simple example available.

Okay. I've found the following in the html.xml

<KeyPressTrigger Key="TagAttributeListTrigger" Character=" ">
  <KeyPressTriggerValidStates>
    <KeyPressTriggerValidState State="StartTagState" />
    <KeyPressTriggerValidState State="StartTagAttributeState" />                
    <KeyPressTriggerValidState state="StartTagAttributeValueState"/>                
  </KeyPressTriggerValidStates>
</KeyPressTrigger>

I understand that this trigger after the "spacebar is being pressed.
How do I continue? Thanks for everything you have told me already btw.
Posted 13 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar
As mentioned in the previous reply, the HtmlDynamicSyntaxLanguage.OnSyntaxEditorTriggerActivated method has a complete example of building items in a member list and showing it, that is in response to a trigger. There is only one member list (in the WinForms version that is; in WPF/Silverlight we redesigned how this works) so you need to clear it and add items when showing it again (in case things change).


Actipro Software Support

Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
Ola,

After giving it some rest I started today again and finally I got it... untill...

<KeyPressTrigger Key="TagAttributeListTrigger" Character=" "> triggers the "space"
In the HtmlDynamicSyntaxLanguage: Protected Overrides Sub OnSyntaxEditorTriggerActivated(ByVal.. I needed to add the trigger.

Case "TagAttributeListTrigger"
With memberList
.ResetAllowedCharacters()
.AllowedCharacters.Add("!"c)
.AllowedCharacters.Add("-"c)
.Clear()

.Add(New IntelliPromptMemberListItem("testing", imagename))
It works!!! Thanks for that. But now...

When I start with <a and hit "space" the "2nd" intelliprompt appears. How do I change the listitems when I start typing (e.g.) <b (and hit space to see a new list)?
What do I need to add to the XML to make that work?

Thanks in advance.
Posted 13 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar
Well the trigger just fires when you press space while in one of those lexical states. You'd need to get a TextStream and do some reverse token scanning to figure out the name of the tag you're on and then use that to figure out which attribute names to add to the list. So an "a" tag name might say that "href" should be in the list, etc. But you need to track all that data on your own somehow.


Actipro Software Support

Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
It seems I wasn't on the right track at all. You keep telling me that I need to get a textstream and do some reverse token scanning to figure out the name of the tag.

In this example I tried it: http://www.mediafire.com/?kvvlojr0323wmba (28KB)
What am I doing wrong?

The attributes have no meaning in this btw. I already have them all. It's just that I need to learn how to implement it.
Posted 13 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar
Something like this finds the tag name:
Dim stream = syntaxEditor.Document.GetTextStream(syntaxEditor.Caret.Offset)
If stream.GoToPreviousTokenWithKey("StartTagNameToken") Then
    Dim tagName = stream.TokenText
    ...
End If


Actipro Software Support

Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
Thanks, but still not working properly:
Private Sub SyntaxEditor1_KeyTyped(sender As Object,...
Dim synEditor As SyntaxEditor = Nothing
Dim memberList As IntelliPromptMemberList = synEditor.IntelliPrompt.MemberList
Dim _blue As Integer = CInt(ActiproSoftware.Products.SyntaxEditor.IconResource.XmlTag)

Dim stream = SyntaxEditor1.Document.GetTextStream(SyntaxEditor1.Caret.Offset)
   If stream.GoToPreviousTokenWithKey("StartTagNameToken") Then
      Dim tagName = stream.TokenText
      Select Case tagName  ' <a
         Case "a"
            With memberList
               .Clear()        '   clear the list and add new members
               .Add(New IntelliPromptMemberListItem("test", _blue))
               .Show
            End With
      End Select
   End If
End Sub
memberList As IntelliPromptMemberList = synEditor.IntelliPrompt.MemberList
not set to a object...
What is the proper way to set the new memberlist?
Posted 13 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar
Your problem is that you set the synEditor variable to Nothing in the previous line.


Actipro Software Support

Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
Uuuuh, call me stupid (which I really seem to be), but what should it be?
Dim synEditor As SyntaxEditor gives me the same result.

Here's the example: http://www.mediafire.com/?qx8sdgumqhqfk1e
Posted 13 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar
Dim synEditor As SyntaxEditor = Nothing
Dim memberList As IntelliPromptMemberList = synEditor.IntelliPrompt.MemberList
In those two lines you initialize a variable called synEditor to type SyntaxEditor but the variable is still null. So doing synEditor.IntelliPrompt will throw an object not initialized exception.

I think you meant to do this instead:
Dim memberList As IntelliPromptMemberList = SyntaxEditor1.IntelliPrompt.MemberList


Actipro Software Support

Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
Aha! Now I get that part. Changed it, but it seems that the rest of the code isn't correct also, but I really want to figure it out:
1) What does "Dim tagName = stream.TokenText" do/mean?

When I have this:

Dim memberList As IntelliPromptMemberList = SyntaxEditor1.IntelliPrompt.MemberList
Dim image_index As Integer = CInt(ActiproSoftware.Products.SyntaxEditor.IconResource.XmlTag)
Dim stream = SyntaxEditor1.Document.GetTextStream(SyntaxEditor1.Caret.Offset)
   If stream.GoToPreviousTokenWithKey("StartTagNameToken") Then
   Dim tagName = stream.TokenText
      Select Case tagName
         Case "a"
            With memberList
               .Clear()        '   clear the list and add new members
               .Add(New IntelliPromptMemberListItem("test 1", image_index, "this is a test"))
               .Add(New IntelliPromptMemberListItem("test 2", image_index, "this is the second test"))
.Show()
            End With
       End Select
   End If
I see it: <a>here the list popsup</a>and here again
instead of <a ...

[Modified at 08/12/2011 05:35 PM]
Posted 13 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar
Hydra,

Sorry, I'm not clear on what you're asking. But you only want to execute the 'If' block you have if the caret is in a start tag attribute lexical state. If it's showing up in other places then look at the triggers you have set up to execute this code.

The code I posted scans back from the current token to look for the first tag start name token it finds. That's why it's essential that you only do it if you know you're in a start tag, after the name token. Then as you wrote in your sample, you want to do a Select on the tag name to figure out which attributes to show.


Actipro Software Support

Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
Thanks for the reply. Things are getting more confused for me, but I know I'm almost there.

[quote]That's why it's essential that you only do it if you know you're in a start tag[/quote]
But How do I know that I'm in a start tag?
What would the code be?
Posted 13 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar
One way is to look at the current Token in the stream to see which lexical state it's in, right before the GoToPreviousTokenWithKey call. The available lexical state and token keys are all defined in the XML language definition.


Actipro Software Support

Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
Sorry, but I can't get it to work. Anyone else that has a working example?
Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
Really no one with an example?
Posted 13 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar
All you would do is look at stream.Token.LexicalState.Key after getting the stream variable in our code sample above. Then make sure it's one of the inside-start-tag values defined in the language definition, like: "StartTagAttributeState".


Actipro Software Support

Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
You make it sound so easy and it probably is, but if you don't understand how everything works/communicates with each other, it's hard to make it work/code it. The documentation isn't helpful in the case unfortunately.

I found this in the language definition:

<!-- Start Tag Attributes -->
<State Key="StartTagAttributeState" TokenKey="StartTagDefaultToken" Style="TagAttributeStyle">
<!-- Scopes -->
<Scopes>
   <Scope>
      <RegexPatternGroup Type="StartScope" TokenKey="StartTagNameToken" Style="TagNameStyle"       PatternValue="{LineTerminatorWhitespaceMacro}* {TagNameMacro}+ {LineTerminatorWhitespaceMacro}*" />
   </Scope>
</Scopes>
<!-- Patterns Groups -->
<PatternGroups>
   <!-- Brackets -->
   <RegexPatternGroup TokenKey="StartTagAttributeToken" Style="TagAttributeStyle" LookAhead="{NonWordMacro}|\z" PatternValue="{WordMacro}+" />
</PatternGroups>
   <!-- Child States -->
   <ChildStates>
      <ChildState Key="StartTagAttributeStringValueState" />
      <ChildState Key="StartTagAttributeValueState" />
   </ChildStates>
</State>
I tried the following code, but nothing happens:
If stream.GoToPreviousTokenWithKey("StartTagNameToken") Then
If stream.Token.LexicalState.Key = "StartTagAttributeState" Then
   Dim tagName = stream.TokenText
   Select Case tagName
      Case "ab"
         With memberList
            .Clear()        '   clear the list and add new members
            .Add(New IntelliPromptMemberListItem("test 1", image_index, "this is a test"))
            .Add(New IntelliPromptMemberListItem("test 2", image_index, "this is the second test"))
            .Show()
         End With
      End Select
   End If
End If
Posted 13 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar
Hydra,

If you look at my prior messages, I had said the new lexical state check needs to be before (not after) the GoToPreviousTokenWithKey call. You are adding that to see if the token you start at is in an attribute state. Then if so, you are backing up to the tag name token and getting its text.


Actipro Software Support

Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
Hi,

Thanks for having that much patience with me.

The code I have now (nothing happens:

Private Sub SyntaxEditor1_KeyTyped(sender As Object, e As ActiproSoftware.SyntaxEditor.KeyTypedEventArgs) Handles SyntaxEditor1.KeyTyped
Dim memberList As IntelliPromptMemberList = SyntaxEditor1.IntelliPrompt.MemberList
Dim image_index As Integer = CInt(ActiproSoftware.Products.SyntaxEditor.IconResource.XmlTag)
Dim stream = SyntaxEditor1.Document.GetTextStream(SyntaxEditor1.Caret.Offset)

' check if token is in a attribute state
 If stream.Token.LexicalState.Key = "StartTagAttributeState" Then
   '   find tagname
   If stream.GoToPreviousTokenWithKey("StartTagNameToken") Then
      Dim tagName = stream.TokenText
      Select Case tagName
         Case "base"
            With memberList
               .Clear()        '   clear the list and add new members
               .Add(New IntelliPromptMemberListItem("test 1", image_index, "test1"))
               .Add(New IntelliPromptMemberListItem("test 2", image_index, "test2"))
               .Show()
            End With
         End Select
   End If
 End If
End Sub
What am I missing?
Posted 13 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar
If you debug, you can see the tagName ends up containing any whitespace after the initial text too. So throw a Trim() on that.

Then if I have this in the editor and type space it pops up your list:
<base
You'll obviously want to do other checks to see if you are probably typing a new word, etc. before you auto-show the list. You can get a ton of information by using the TextStream and looking at the token data and offset data.


Actipro Software Support

Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
I only see the list when I press the backspace to remove the ">".
I've included my example: http://www.mediafire.com/?tctn3qgg2hj8hdq

- What would the code be to check if I'm typing a new word?
Posted 13 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar
I modified your source code to better illustrate how to show the attribute name list when an attribute is starting to be typed.
    Private Sub SyntaxEditor1_KeyTyped(sender As Object, e As ActiproSoftware.SyntaxEditor.KeyTypedEventArgs) Handles SyntaxEditor1.KeyTyped
        Dim memberList As IntelliPromptMemberList = SyntaxEditor1.IntelliPrompt.MemberList
        Dim image_index As Integer = CInt(ActiproSoftware.Products.SyntaxEditor.IconResource.XmlTag)
        Dim stream = SyntaxEditor1.Document.GetTextStream(SyntaxEditor1.Caret.Offset)

        ' If the member list is not yet visible and the character typed is a letter...
        If (Not memberList.Visible) AndAlso (Char.IsLetter(e.KeyChar)) Then
            ' Check if token is in a attribute state
            If stream.Token.LexicalState.Key = "StartTagAttributeState" Then
                ' Move back a character and see if the character was at the start of an attribute name token
                stream.ReadCharacterReverse()
                If (stream.IsAtTokenStart) AndAlso (stream.Token.Key = "StartTagAttributeToken") Then
                    ' Save the token text range so that the member list will replace any existing text
                    Dim initializationTextRange As TextRange = stream.Token.TextRange

                    ' Move back to get the containing tag name
                    If stream.GoToPreviousTokenWithKey("StartTagNameToken") Then
                        Dim tagName = stream.TokenText.Trim()
                        Select Case tagName
                            Case "base"
                                With memberList
                                    .Clear()        '   clear the list and add new members
                                    .Add(New IntelliPromptMemberListItem("test 1", image_index, "test1"))
                                    .Add(New IntelliPromptMemberListItem("test 2", image_index, "test2"))
                                    .Show(initializationTextRange.StartOffset, initializationTextRange.Length)
                                End With
                        End Select
                    End If
                End If
            End If
        End If
    End Sub


Actipro Software Support

Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
You really are going to hate me for this, but the code doesn't work. I copy and pasted it in the testeditor and typed <base, after that I pressed SPACE. No new memberlist is shown. :cry:
Posted 13 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar
The code I have up there doesn't look for space, it's looking for the starting of typing a new attribute name. Like: <base t


Actipro Software Support

Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
Ah, like that. What do I needs to change to make it work with a SPACE?
Posted 13 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar
    Private Sub SyntaxEditor1_KeyTyped(sender As Object, e As ActiproSoftware.SyntaxEditor.KeyTypedEventArgs) Handles SyntaxEditor1.KeyTyped
        Dim memberList As IntelliPromptMemberList = SyntaxEditor1.IntelliPrompt.MemberList
        Dim image_index As Integer = CInt(ActiproSoftware.Products.SyntaxEditor.IconResource.XmlTag)
        Dim stream = SyntaxEditor1.Document.GetTextStream(SyntaxEditor1.Caret.Offset)

        ' If the member list is not yet visible and the character typed is a space...
        If (Not memberList.Visible) AndAlso (e.KeyChar = " "c) Then
            Dim showList As Boolean = False

            ' Check if token is in a proper state
            Select Case stream.Token.LexicalState.Key
                Case "StartTagState"
                    ' Already on the tag name
                    If (stream.Token.Key = "StartTagNameToken") Then
                        showList = True
                    Else
                        If stream.GoToPreviousTokenWithKey("StartTagNameToken") Then showList = True
                    End If
                Case "StartTagAttributeState"
                    ' Move back to get the containing tag name
                    If stream.GoToPreviousTokenWithKey("StartTagNameToken") Then showList = True
            End Select

            If (showList) Then
                Dim tagName = stream.TokenText.Trim()
                Select Case tagName
                    Case "base"
                        With memberList
                            .Clear()        '   clear the list and add new members
                            .Add(New IntelliPromptMemberListItem("test 1", image_index, "test1"))
                            .Add(New IntelliPromptMemberListItem("test 2", image_index, "test2"))
                            .Show()
                        End With
                End Select
            End If
        End If
    End Sub


Actipro Software Support

Posted 13 years ago by Radjesh Klauke - Mr., X-impress
Avatar
Thanks. It works fine. Now it's up to me to understand how the code works.
The latest build of this product (v24.1.0) was released 2 months ago, which was after the last post in this thread.

Add Comment

Please log in to a validated account to post comments.