V2 Possible bug - addListView() Error: Too many parameters passed to function

Get help with using AutoHotkey (v2 or newer) and its commands and hotkeys
User avatar
DrReflex
Posts: 42
Joined: 25 May 2015, 02:57
Location: Greer, SC

V2 Possible bug - addListView() Error: Too many parameters passed to function

10 Feb 2023, 12:56

addListView() fails when trying to pass header as an expanded array. See comments below:

Code: Select all

#SingleInstance Force

data := []
row1 := ["Col1", "Col2", "Col3"]
row2 := ["R1C1", "R1C2", "R1C3"]
row3 := ["R2C1", "R2C2", "R2C3"]
row4 := ["R3C1", "R3C2", "R3C3"]
data.push(row1)
data.push(row2)
data.push(row3)
data.push(row4)

main := gui()


for row in Data
{
	if (A_Index = 1)
	{
		;lv 	 := main.addListView("",["COL1","COL2","COL3"])  ; THIS WORKS
		;lv 	 := main.Add("ListView","",["COL1","COL2","COL3"])  ; THIS WORKS
		lv 	 := main.Add("ListView", "", row*) ; THIS FAILS WITH "Error: Too many parameters passed to function"
		;lv 	 := main.addListView("", row*)  ; THIS FAILS WITH "Error: Too many parameters passed to function"
	} else
	{
		lv.Add("", row*)
	}
}
main.show()
return
User avatar
flyingDman
Posts: 2832
Joined: 29 Sep 2013, 19:01

Re: V2 Possible bug - addListView() Error: Too many parameters passed to function

10 Feb 2023, 13:32

Not a bug:

Code: Select all

data := []
row1 := ["Col1", "Col2", "Col3"]
row2 := ["R1C1", "R1C2", "R1C3"]
row3 := ["R2C1", "R2C2", "R2C3"]
row4 := ["R3C1", "R3C2", "R3C3"]
data.push(row1)
data.push(row2)
data.push(row3)
data.push(row4)

main := gui()
for row in Data
	if (A_Index = 1)
		lv 	 := main.Add("ListView", "", row) ; w/o "*" i.e. not variadic, an array is expected here.
	else
		lv.Add("", row*)
main.show()
return
14.3 & 1.3.7
User avatar
DrReflex
Posts: 42
Joined: 25 May 2015, 02:57
Location: Greer, SC

Re: V2 Possible bug - addListView() Error: Too many parameters passed to function

11 Feb 2023, 01:25

Thanks flyingDman. I really appreciate your Help. It turns out that in addition to replacing "row*" with "row" as you suggested, replacing "row*" with [row*] also works. I prefer the semantics of the latter since I am loading listviews with variadic lists of elements from CSV files.

FOR LEXiKOS:
1. AHK v2 documentation gives the following format for the GUI Add method:

Add method (Gui): MyGui.Add(ControlType , Options, Text)

where:
ControlType is type String
Options is type String
Text type "Depends on the specific control type, a string, number or an array."

The documentaiton does not enumerate which type to use for which control or provide a reference to that information.
This should be fixed.

2. AHK v2 documentation gives the following format for the ListView Add method:

Add method (ListView): NewRowNumber := LV.Add(Options, Col1, Col2, ...)

where:
Options is type String.
Col1, Col2, ... is type String. The columns of the new row, which can be text or numeric (including numeric expression results).
To make any field blank, specify "" or the equivalent. If there are too few fields to fill all the columns, the columns at the end are left
blank. If there are too many fields, the fields at the end are completely ignored.

There is no mention of inputing Col1, Col2, ... as an array in the documentation. Is type String truely correct for Col1, Col2, ...?

3. AHK v2 documentaiton for ListView (in the first working script) shows that Cols can be added as an expanded array.

LV := MyGui.Add("ListView", "r20 w700", ["Name","Size (KB)"])

in contrast, (in the same script) cell values appear to be added to the listview as parameters:

LV.Add(, A_LoopFileName, A_LoopFileSizeKB)

Neither format option is enumerated in the documentation so the choice of best/working format remains ambiguous.

From a semantics point of view, the most consistent usage would be to have both methods use parametric inputs. Not only would this get rid of the ambiguity, it would best support variadic loading of both methods. I know that we are now at an alpha release, so I would settle for better documentation and examples showing how to do load listviews with variadic references.

Suggested example:

Code: Select all

;sCSV = CSV formated string.  Obtain from file with sCSV := FileRead(Filename)
sCSV := "
( Ltrim Join`n
		COL1,COL2,COL3
		R1C1,R1C2,R1C3
		R2C1,R2C2,R2C3
		R3C1,R3C2,R3C3
)"

aCSV := []
Loop Parse sCSV, "`n" {
	aElements := []
	Loop Parse A_LoopField, "," {
		aElements.Push(A_LoopField)
	}
	aCSV.Push(aElements)
}

MyGui := gui(,"Variadic LV load")
for row in aCSV {
	if (A_Index = 1)
		lv 	 := MyGui.addListView("", [row*])  ;NOTE: "row" could be used in place of [row*].  
	else
		lv.Add("", row*)
}
MyGui.show()
User avatar
flyingDman
Posts: 2832
Joined: 29 Sep 2013, 19:01

Re: V2 Possible bug - addListView() Error: Too many parameters passed to function

11 Feb 2023, 02:30

row is an array. Using [row*] instead of row is counter-intuitive to me and IMHO should be avoided.
14.3 & 1.3.7
just me
Posts: 9528
Joined: 02 Oct 2013, 08:51
Location: Germany

Re: V2 Possible bug - addListView() Error: Too many parameters passed to function

11 Feb 2023, 04:55

DrReflex wrote:Neither format option is enumerated in the documentation so the choice of best/working format remains ambiguous.
That's because there is no choice.

Introduction and Simple Example

Code: Select all

LV := GuiObj.Add("ListView", Options, ["ColumnTitle1","ColumnTitle2","..."])
Clearly shows that the last parameter must be an array which will be used for the header.

Add

Code: Select all

NewRowNumber := LV.Add(Options, Col1, Col2, ...)
Also clearly shows that column values must be passed as single parameters.

No choice! ;)
User avatar
DrReflex
Posts: 42
Joined: 25 May 2015, 02:57
Location: Greer, SC

Re: V2 Possible bug - addListView() Error: Too many parameters passed to function

11 Feb 2023, 18:02

Thanks just me! I agree. However, I am still new to V2 and I did not find variadic loading of the header in .Add("ListView"...) to be as intuitive in V2 as it was in V1. In V1, you just built a header string and inserted it. With V2 the load should be direct and once you workout the formatting it is.

In both versions of AHK, ListView is built to accept variadic input from an array. I spent too much time figuring out how to make this work in V2 and that with the help of Isaias Baez. The V2 documentation did not help as much as I feel it should have.

I am passing the same data from a CSV file to an array and then to a listview. If the data has a header, then the first row in the array contains the header data. If it does not, then a header is generated (code omitted) and the first row in the array is added to the listview (code omitted).

Unfortunately, the format for passing the same data to the same GUI control using methods of the same name is different between the two methods. I don't think we need to change V2. (It should be a considered in the future. There does not appear to be a clear reason not use use the same input format for both methods, and let the internal code do the transformation.)

---------------

What I am recommending to Lexikos at this time is better documentation of this inconsistency and putting a clear example into the documentation to demonstrate how ListView can be loaded with variadic parameter lists from an array. I have provided an example.

Based upon 10,000 timing there does not appear to be a noticable time cost for using [row*] instead of [row] (62 ms difference in the best times with < 400 ms difference in the 3 best times for both versions. I modified the Gui code by adding a loop with start and stop times around the GUI code, commenting out the "show()" statement, and adding a gui.delete() statement to execute before starting the next loop.

In closing, examples are there to help new users. We want everyone to adopt V2. If doing simple tasks takes too much time, then they are not going adopt V2. With respect to my example, just like I would not use RegEx expressions in place of If statements in non-RegEx examples, I would not use "row" in place of "[row*]" when I am trying to demonstrate variadic loading of a listview. I would and did include a comment that the codes are equivalent but I would still use "[row*]" in the example.
just me
Posts: 9528
Joined: 02 Oct 2013, 08:51
Location: Germany

Re: V2 Possible bug - addListView() Error: Too many parameters passed to function

12 Feb 2023, 05:02

@DrReflex:

for LV_ADD() respectively GuiListViewControl.Add() nothing changed between the two versions.

For Gui, Add, ListView, ... it isn't possible to pass a variadic parameter for the header string with v1 and the same is true with v2. Only the parameter type changed from string to array. It doesn't matter how you create the array.

If you switch from v1 to v2 and pass a header string to Gui.AddListView("", ...) you get the following error:
Error: Expected an Array but got a String.

Specifically: COL1|COL2|COL3

015: aHdr := aCSV.RemoveAt(1)
016: sHdr := "COL1|COL2|COL3"
▶ 017: LV := MyGui.AddListView("", sHDR)
018: For aRow in aCsv
019: LV.Add("", aRow*)

Show call stack »
If you read the documentation of the ListView control then, what would remain unclear?
User avatar
DrReflex
Posts: 42
Joined: 25 May 2015, 02:57
Location: Greer, SC

Re: V2 Possible bug - addListView() Error: Too many parameters passed to function

21 Feb 2023, 20:42

Thanks just me.

FYI: It is possible to pass a variadic paramenter for the listview header in v2. See my example. This is a great addition to V2! In V1 you had to use a loop to construct the header (see viewtopic.php?t=28155)

Code: Select all

;sCSV = CSV formated string.  Obtain from file with sCSV := FileRead(Filename)
sCSV := "
( Ltrim Join`n
		COL1,COL2,COL3
		R1C1,R1C2,R1C3
		R2C1,R2C2,R2C3
		R3C1,R3C2,R3C3
)"

aCSV := []
Loop Parse sCSV, "`n" {
	aElements := []
	Loop Parse A_LoopField, "," {
		aElements.Push(A_LoopField)
	}
	aCSV.Push(aElements)
}

MyGui := gui(,"Variadic LV load")
for row in aCSV {
	if (A_Index = 1)
		lv 	 := MyGui.addListView("", [row*])  ;NOTE: "row" could be used in place of [row*].  
	else
		lv.Add("", row*)
}
MyGui.show()

Return to “Ask for Help (v2)”

Who is online

Users browsing this forum: ntepa, onandoffwhat, songdg and 27 guests