V2 Syntax for AHK Studio

Editor for AutoHotkey written completely in AutoHotkey.

Moderator: maestrith

AHK_user
Posts: 515
Joined: 04 Dec 2015, 14:52
Location: Belgium

V2 Syntax for AHK Studio

28 Jul 2021, 05:32

Does somebody has experience in setting up AHK Studio to write code for AutoHotKey V2?
- Syntax
- Tooltip
- F1 Helpfile

I want to be able to run both AHK V1 and V2 code, so I made a versionLauncher that would do this automatically, so this works already great.

I was thinking of just making a separate copy of AHK studio that I just use for V2 code to keep it simple.
AHK_user
Posts: 515
Joined: 04 Dec 2015, 14:52
Location: Belgium

Re: V2 Syntax for AHK Studio

31 Jul 2021, 14:28

I started scraping the V2 beta help files to update the syntax for AHK Studio.

I have not got the chance to test this, because AHK Studio keeps deleting it from the language folder :think: . I have asked maestrith to explain how I can use it, so hopefully we can start testing it out.

if somebody wants to test/improve it:
https://github.com/dmtr99/AHK-Studio/blob/Beta/lib/Languages/ahkv2.xml

This is the scraper that scrapes the helpfiles for the syntax if you download them from github.
https://github.com/Lexikos/AutoHotkey_L-Docs/tree/v2/docs

It can be improved, but this collect a lot of data, and the rest can be fixed manually :D

Code: Select all

#NoEnv  ; Recommended for performance and compatibility with future AutoHotkey releases.
#SingleInstance, Force
; #Warn  ; Enable warnings to assist with detecting common errors.
#Requires AutoHotkey v1.1
SetWorkingDir %A_ScriptDir%  ; Ensures a consistent starting directory.

String:= "NewTitle [, WinTitle, WinText, ExcludeTitle, ExcludeText]"


Ahk_Xml:={}

OutputText :=""
loop, Files, %A_ScriptDir%\AutoHotkey_L-Docs-2\docs\objects\*
{

	FileRead, ContentBuffer, %A_LoopFileFullPath%
	
	;Used for testing on a specific file
	if !InStr(A_LoopFileFullPath, "StrPut"){
		;~ Continue
	}
	
	Content := ContentBuffer
	Loop, 
	{
		h1 := RegExReplace(Content, "sS).*?<h1>([^>]*?)</h1>.*", "$1", RegexCount)
		;~ h1 := RegExReplace(Content, "sS).*?</h\d>.*?<p>(.*?)</p>[^>]*?<pre class=""[^>]*Syntax"">.*", "$1", RegexCount)
		h1 := RegexCount>0 ? h1 : ""
		Description := RegExReplace(Content, "sS).*?</h\d[^>]*>.*?<p>(.*?)</p>[^>]*?<pre class=""[^>]*Syntax"">.*", "$1", RegexCount)
		Description := RegExReplace(Description, "sS).*<p>(.*?)$", "$1")
		Description := RegExReplace(Description, "<a[^>]*>", "")
		Description := RegExReplace(Description, "</a>", "")
		Description := RegexCount>0 ? Description : ""
		;~ Description := RegExReplace(Description, "<[^>]*>", "")
		Syntax := RegExReplace(Content, "sS).*?</h\d>.*?<pre class=""[^>]*Syntax"">(.*?)</pre>.*", "$1", RegexCount)
		
		Syntax := RegExReplace(Syntax, "sS)<span class=""optional"">(.*?)</span>", "[$1]")
		Syntax := RegexCount>0 ? Syntax : ""
		
		SyntaxText := RegExReplace(Syntax, "[\[\]]", "", RegexCount)
		SyntaxText := Syntax
		aSyntax := StrSplit(SyntaxText, "`n", "`r")
		
		OutputText .="Command: " h1 "`nDescription: " Description "`n"
		ParametersText := RegExReplace(Content, "sS).*?<h\d id=""Parameters"">Parameters</h\d>.*?<dl>(.*)</dl>.*", "$1", RegexCount)
		ParametersText := RegexCount>0 ? ParametersText : ""
		
		;~ OutputText .= "ParametersText: " ParametersText "`n"
		Parameter_old:=""
		aParameters:={}
		loop, {
			ParametersText_Buffer := ParametersText
			Parameter := RegExReplace(ParametersText_Buffer, "sS)^.*?<dt[^>]*>([^<]*?)</dt>.*", "$1", ParameterCount)
			Parameter := RegExReplace(Parameter, "\n", "")
			if (Parameter_old != Parameter){
				Parameter := ParameterCount>0 ? Parameter : ""
				ParameterChoices:=""
				OutputText .= Parameter!="" ? "Parameter: " Parameter "`n" : ""
			}
			if (Parameter=""){
				Break
			}
			
			ParameterText := RegExReplace(ParametersText, "sS)^.*?<dt[^>]*>([^>]*?)</dt>(.*?)</dd>(.*)", "$2")
			; Remove the note element
			
			Loop, Parse, ParameterText, `n, `r
			{
				ParameterValue := RegExReplace(A_LoopField, "sS)^\s*(<p[^>]*>|)<strong>(.*?):?</strong>.*", "$2", ParameterValueCount)
				if (ParameterValue!="note"){
					ParameterChoices .= ParameterValueCount>0 ? ParameterChoices="" ? "" ParameterValue : "|" ParameterValue : ""
				}
			}
			OutputText .= ParameterChoices="" ? "" : "[" Parameter "]`: " ParameterChoices "`n"
			aParameters[RegExReplace(Parameter, "\s", "")] := ParameterChoices="" ? "" : ParameterChoices 
			ParametersText := RegExReplace(ParametersText, "sS)^.*?<dt[^>]*>(.*?)</dt>(.*?)</dd>(.*)", "$3")
			Parameter_old := Parameter
		}
		
		loop, % aSyntax.Length()
		{
			if (aSyntax[A_Index]=""){
				Continue
			}
			
			Type := "Command"
			Function := RegExReplace(aSyntax[A_Index], "sS)<span class=""func"">(.*?)</span>.*", "$1", RegexCount)
			Function := RegexCount>0 ? Function : ""
			Function := RegExReplace(Function, "sS)^\s*\w+\s*?:=\s(.*)", "$1")
			SyntaxParameters := RegExReplace(aSyntax[A_Index], "sS)<span class=""func"">.*?</span>(.*)", "$1", RegexCount)
			SyntaxParameters := RegexCount>0 ? SyntaxParameters : ""
			SyntaxParameters := RegExReplace(SyntaxParameters, "sS)^\s*\w+\s*?:=\s(.*)", "$1")
			
			if (InStr(SyntaxParameters,"(") and InStr(SyntaxParameters,")")){
				Type := "Function"
			}
			if (SubStr(Function,1, 1) = "#"){
				Type := "Directive"
			}
			
			OutputText .= Type!="" ? "Type: " Type "`n" : ""
			SyntaxParameters := RegExReplace(SyntaxParameters, "<[^>]*>", "")
			SyntaxParameters := RegExReplace(SyntaxParameters, """", "&quot;")
			
			if (SyntaxParameters=": Same parameters as above."){
				SyntaxParameters:= SyntaxParameters_prev
			}
			SyntaxParameters_prev:= SyntaxParameters
			
			String := SyntaxParameters
			SyntaxParameters:= ""
			; Loop to replace the parameters by the options
			loop, {
				
				Prefix := RegExReplace(String, "^(.*?)(\w+)(.*)$", "$1", RegexCount)
				Parameter := RegExReplace(String, "^(.*?)(\w+)(.*)$", "$2", RegexCount)
				if (aParameters[Parameter]!=""){
					Parameter := aParameters[Parameter]
					if (A_Index=1 and Function!= ""){
						if InStr(Function, "#"){
							Function2:= StrReplace(Function, "#")
							Ahk_Xml["Content"] .= "`t`t<" Function2 ">`n`t`t`t<list add=""#"" list=""" 
							Ahk_Xml["Content"] .=  StrReplace(Parameter, "|", " ") """>" Function2 "</list>`n`t`t</" Function2 ">`n"
						}
						else{
							Ahk_Xml["Content"] .= "`t`t<" Function ">`n`t`t`t<list list=""" StrReplace(Parameter, "|", " ") """>" Function "</list>`n`t`t</" Function ">`n"
						}
					}
					else if (Function!= ""){
						if InStr(Function, "#"){
							Function2:= StrReplace(Function, "#")
							Ahk_Xml["Content2"] .= "`t`t<" Function2 ">`n`t`t`t<list add=""#"" list=""" 
							Ahk_Xml["Content2"] .=  StrReplace(Parameter, "|", " ") """>" Function2 "</list>`n`t`t</" Function2 ">`n"
						}
						else{
							Ahk_Xml["Content2"] .= "`t`t<" Function ">`n`t`t`t<list list=""" StrReplace(Parameter, "|", " ") """>" Function "</list>`n`t`t</" Function ">`n"
						}
					}
				}
				String := RegExReplace(String, "^(.*?)(\w+)(.*)$", "$3", RegexCount)
				if (RegexCount=0){
					SyntaxParameters .= String
					Break
				}
				SyntaxParameters .= Prefix  Parameter
			}
			
			OutputText .= "Syntax: " Function "" SyntaxParameters "`n"
			OutputText .= "`t`t<syntax syntax=""" SyntaxParameters """>" Function "</syntax>`n"
			if (Function!= ""){
				Ahk_Xml[Type] .= "`t`t<syntax syntax=""" SyntaxParameters "``n" Description """>" Function "</syntax>`n"
				
				;If also seen as a function in examples
				if (Type!="Function" and RegExMatch(ContentBuffer, "sS).*\b" Function "\(.*\)")){
					Ahk_Xml["Function"] .= "`t`t<syntax syntax=""(" Trim(SyntaxParameters) ")``n" Description """>" Function "</syntax>`n"
				}
			}
		}
		Content := RegExReplace(Content, "sS)^.*?<pre class=""[^>]*Syntax"">.*?</pre>.*?(<h\d\sid.*?<pre .*)$", "$1", RegexCount)
		
		if (RegexCount=0){
			Break
		}
	}
	
	OutputText .= "`n"
	
}
DebugWindow(OutputText,Clear:=0)

DebugWindow("`t<Command>`n" Ahk_Xml["Command"] "`t</Command>`n",Clear:=0)
DebugWindow("`t<Directive>`n" Ahk_Xml["Directive"] "`t</Directive>`n",Clear:=0)
DebugWindow("`t<Function>`n" Ahk_Xml["Function"] "`t</Function>`n",Clear:=0)
DebugWindow("`t<Content>`n" Ahk_Xml["Content"] "`t</Content>`n",Clear:=0)
DebugWindow("`t<Content2>`n" Ahk_Xml["Content2"] "`t</Content2>`n",Clear:=0)

ExitApp

hasantr
Posts: 933
Joined: 05 Apr 2016, 14:18
Location: İstanbul

Re: V2 Syntax for AHK Studio

19 Aug 2021, 01:37

I'm curious about the developments. I'd appreciate it if you'd share their new state with us. :)
AHK_user
Posts: 515
Joined: 04 Dec 2015, 14:52
Location: Belgium

Re: V2 Syntax for AHK Studio

19 Aug 2021, 05:34

Noting happened... I also asked on ahk studio Github, but got no response. :cry:

If somebody could show me how you can modify the syntax file for ahk or ah2 extension for ahk Studio, we could probably change it work.

I tried to override ahk.xml with the content, but ahk_studio keeps overriding this file. :headwall: (<Studio_Install_Directory>\Lib\Languages\ahk.xml)

Feel free to test if it works for you, but I got no results, so I stopped working on it.

Please let me know if somebody managed this. I am experimenting with ahk v2 and am starting to like it more and more.
User avatar
dd900
Posts: 121
Joined: 27 Oct 2013, 16:03

Re: V2 Syntax for AHK Studio

14 Dec 2021, 17:05

The file was invalid xml. There were html remnants <em></em>, <kbd></kbd>, <strong></strong> among others. Also found a couple " that needed to be '. I cleaned up the file and AhkStudio doesn't delete it. I'm not sure if it is working or not. I don't know how to set the language and most editors will generically highlight stuff so its hard to tell.
Attachments
ahk2..xml
(79.96 KiB) Downloaded 220 times

Return to “AHK Studio”

Who is online

Users browsing this forum: No registered users and 21 guests