PDA

View Full Version : Constant String Arrays with non-linear "indexes"



ReneMiner
12-06-2013, 09:51
Now having some area for new ideas that have to grow before they become a real official suggest, I'm gonna lay an egg here that has to be breeded.:egg26:

Constant String Arrays with non-linear indexes
where Index is actually just a "key" like it's known from Dictionary-module.

Huh? Now what's that supposed to be?

I'll try to explain, imagine ordinary script using UI + callbacks:



Begin ControlID
%ID_BtnOK = 1
%ID_BtnCancel
%ID_BtnExit
'...
End ControlID

$Control_ID(%ID_BtnOK) = "OK"
$Control_ID(%ID_BtnCancel) = "Cancel"
$Control_ID(%ID_BtnExit) = "Exit"

' still very linear 'til here...
' - - - - - - - - - - - - - - -
' but now:

$CBMSG(%WM_Command) = "Action_"
$CBMSG(%WM_Init) = "Init_"

$CBCTLMSG(%BN_Clicked) = "ClickButton_"
'...
Dialog New pixels, 0, "TB-Script, esc to quit", 0, 0, 800, 600, Style, ExStyle To hWin1
$DialogID(hWin1) = "Window1_"
Dialog New pixels, 0, "another window", 0, 0, 640, 480, Style, ExStyle To hWin2
$DialogID(hWin2) = "Window2_"
'...

Callback Function universalCallback()
Call_IfExists $DialogID(CBHNDL) + $CBMSG(CBMSG) + $CBCTLMSG(CBCTLMSG) + $Control_ID(CBCTL) (CBLPARAM, CBWPARAM, CBNMID, CBNHWND, CBMHDR)
' nothing else needed...
' no select case nor other filtering...
End Function

' rest reads like this:
Sub Window1_Action_ClickButton_OK(Byval lCBLPARAM As Long, Byval lCBWPARAM As Long, Byval lCBNMID As Long, Byval lCBNHWND As Long, Byval lCBMHDR as Long)

End sub

Sub Window2_Action_ClickButton_OK(...)

End sub

Sub Window1_Action_ClickButton_Cancel(...)

End sub


OK, for the callback-messages there should be fixed built-in constant strings - sure - I could use a function like this:




Callback Function universalCallback()
local sMsg as String
sMsg = GetName(CBHNDL)
sMsg += GetName(CBMSG)
sMsg += GetName(CBCTLMSG)
sMsg += GetName(CBCTL)

Call_IfExists sMsg (CBLPARAM, CBWPARAM, CBNMID, CBNHWND, CBMHDR)
End Function

Function GetName(ByVal forWhat as Long) As String
' very simplified, should be different function for each "parameter-style"
Select Case ForWhat
Case %WM_Command
Return "Action_"
Case %BN_Clicked
Return "ClickButton_"
'...etc...
End Select

End Function

but somehow I don't like it this way because that Select Case neutralizes the "Call_IfExists"-advantage again.
Dictionary could be a work-around without the need to Select Case...

So it would be great to have a fixed constant-string-table for common CB-messages and the opportunity to create like
constant strings that have a "key" in parenthesis (like an Index)

The use of callbacks here is just an example and the most common and easiest understandable reason- I have a lot of other usage in mind...

Petr Schreiber
12-06-2013, 10:27
I like this, I think it is called associative arrays.

Petr

ReneMiner
16-06-2013, 12:37
Yes. Currently I use some similar way as this:



$Msg_BtnClicked = "ClickButton_"
Const %Msg_BtnClicked As Dword = StrPtr($Msg_BtnClicked)


that works pretty well with my own constants - since all stringpointers are unique anyway - but I can not make it the opposing way that would be needed for the system-constants or the callback-messages in the example above.

Therefore I currently need to store the messages together with their text into some typed arrays as this



Type t_ID_Txt
ID as Dword
Txt as String
End Type

Dim CB_MSG() as t_ID_Txt
Dim CB_CTLMSG() as t_ID_Txt
'...
' fill these arrays with all information...
' like
CB_MSG(123).ID = %WM_Command
CB_MSG(123).Txt = "Action_"
'...
CB_CTLMSG(34).ID = %BN_Clicked
CB_CTLMSG(34).Txt ="ClickButton_"

'and always pass these like

Callback Function alwaysWorks()
Local sMsg as String = GetDialogname(CBHNDL)

sMsg += GetCBMessageText(MKDWD$(CBMSG))
sMsg += GetCBCTLMessageText(MKDWD$(CBCTLMSG))
'etc...
Call_IfExists sMsg (CBLPARAM, CBWPARAM, CBNMID, CBNHWND, CBMHDR)
End Function

Function GetCBMessageText(Byval sDword as String)

Long lResult = Array Scan CB_MSG, Byte(UDT_ElementByte(CB_MSG(1).ID, SizeOf(Dword)), = sDword

If lResult Then Function = CB_MSG(lResult).Txt

End Function
'...


so to speed this up it would be great for UI to have all standard-messages associated to some text already built-in by default like

sMsg += $CBMSG(CBMSG)

but for other usage I still think a possibility to associate constant strings with some key-alike index will save a lot of typing and calling search-for-functions.
Perhaps use square brackets...

ReneMiner
22-08-2013, 10:21
Dig this out again:

For the Controls/Dialogs there would be a possibility to somewhat like that:



Uses "UI"

$myDialog = "myDialog"
$myOKButton = "myOKButton"
'...

Begin ControlID
'...
%myOKButton
' ...
End ControlID

Dialog New 0, "TB_Script", 100, 50, 600, 300,.., 0 To hDlg
Dialog Set User, hDlg, 1 , StrPtr($myDialog)
Control Add Button, hDlg, %myOKButton, "OK", 10,10,20,20
Control Set User, hDlg, %myOKButton, 1, StrPtr($myOKButton)

'...

'in Callback-function then

Dword sPtr
String subsName

Dialog Get User, CBHNDL, 1 To sPtr
subsName = Memory_Get(sPtr, Peek(Dword, sPtr-4))

Select Case CBMSG
Case %WM_InitDialog, %WM_Close, %WM_SysCommand ',...
'sort out the messages that go to Dialog directly
subsName += "_" & Get_CBMSG$(CBMSG) ' associative array instead of a function would be great...
Case Else
' the leftover goes to controls
Control Get User, CBHNDL, CBCTL, 1 To sPtr
subsName += "_" & Memory_Get(sPtr, Peek(Dword, sPtr-4)) & "_" & Get_CBCTLMSG$(CBCTLMSG)
End Select


Call_IfExists subsName ( CBLPARAM, CBWPARAM, CBNMID, CBNHWND, CBMHDR )
' ...