You are here

NSIS help

18 posts / 0 new
Last post
Simeon
Simeon's picture
Offline
Last seen: 9 years 9 months ago
DeveloperTranslator
Joined: 2006-09-25 15:15
NSIS help

I could use some help from some NSIS geek Smile
I have a Launcher with 3 checkboxes labeled "Firefox, Thunderbird, ClamWin" and I want to execute the related program but only if the checkbox is checked. Does anyone know how to get th checkbox value?
I found something on the web but I found it too complicated if I have 10+ checkboxes and hope there is a faster way.

Thats what I have so far:

;Copyright 2007 Simeon
OutFile "Launcher.exe"
RequestExecutionLevel user
Icon "\Documents\nsi\PAPPS.ico"
!include nsDialogs.nsh
!include LogicLib.nsh


Page custom nsDialogsPage
Page instfiles
;=== Variables
Var ClamWin
Var Firefox
Var Thunderbird


Function nsDialogsPage
SetAutoClose true
	nsDialogs::Create /NOUNLOAD 1018
	Pop $0
	${NSD_CreateCheckbox} 0 10 30% 8u Firefox
	Pop $Firefox
	GetFunctionAddress $0 OnCheckboxFirefox
	nsDialogs::OnClick /NOUNLOAD $Firefox $0
	${NSD_CreateCheckbox} 0 30 35% 8u Thunderbird
	Pop $Thunderbird
	GetFunctionAddress $2 OnCheckboxThunderbird
	nsDialogs::OnClick /NOUNLOAD $Thunderbird $2
	${NSD_CreateCheckbox} 0 70 30% 8u ClamWin
	Pop $Clamwin
	GetFunctionAddress $1 OnCheckboxClamWin
	nsDialogs::OnClick /NOUNLOAD $Clamwin $1
	nsDialogs::Show
FunctionEnd

Function OnCheckboxFirefox
SendMessage $Firefox ${BM_GETSTATE} 0 0 $0
${If} $0 != 0
	StrCpy $Firefox "true"
${Else}
	StrCpy $Firefox "false"
${EndIf}
FunctionEnd

Function OnCheckboxClamWin
SendMessage $Clamwin ${BM_GETSTATE} 0 0 $1
${If} $1 != 0
	StrCpy $Clamwin "true"
${Else}
	StrCpy $Clamwin "false"
${EndIf}
FunctionEnd

Function OnCheckboxThunderbird
SendMessage $Thunderbird ${BM_GETSTATE} 0 0 $2
${If} $2 != 0
	StrCpy $Thunderbird "true"
${Else}
	StrCpy $Thunderbird "false"
${EndIf}
FunctionEnd

 Function .onInstSuccess
	StrCmp $Thunderbird "true" "" +3
	Exec "$EXEDIR\PortableApps\ThunderbirdPortable\ThunderbirdPortable.exe"
	Sleep 10000
	StrCmp $Firefox "true" "" +3
	Exec "$EXEDIR\PortableApps\FirefoxPortable\FirefoxPortable.exe"
	Sleep 10000
	StrCmp $ClamWin "true" "" +3
	Exec "$EXEDIR\PortableApps\ClamWinPortable\ClamWinPortable.exe"
	Sleep 3000
  FunctionEnd

Section
SectionEnd

My hope is that I can get rid of the whole bunch of OnblablaCheckbox and let ${BM_GETSTATE} do this stuff at the end of the script.

Maybe I should ask at the NSIS forums but I dont wanna become a member for one question Smile

Any hints appreciated.

wraithdu
Offline
Last seen: 11 years 1 month ago
Developer
Joined: 2007-06-27 20:22
I would wait until your

I would wait until your leave page function to query the state of all the checkboxes. That way you can do it in one function, no need to query each time you change the check mark (I'm assuming this is a multi-launcher).

So your pages would be

Page custom nsDialogsPage nsDialogsPageLeave ; 

Then in your leave page func
Function nsDialogsPageLeave
   SendMessage $Firefox ${BM_GETSTATE} 0 0 $0
   ${If} $0 != 0
	StrCpy $Firefox "true"
   ${Else}
	StrCpy $Firefox "false"
   ${EndIf}

   SendMessage $Thunderbird ${BM_GETSTATE} 0 0 $2
   ${If} $2 != 0
	StrCpy $Thunderbird "true"
   ${Else}
	StrCpy $Thunderbird "false"
   ${EndIf}

   etc...
FunctionEnd

Then in your main page you can drop all the nsdialogs::OnClick and GetFunctionAddress lines.

PS - NSD has a builtin macro for OnClick, ie

${NSD_OnClick} $Firefox OnCheckboxFirefox
Simeon
Simeon's picture
Offline
Last seen: 9 years 9 months ago
DeveloperTranslator
Joined: 2006-09-25 15:15
Thanks

Ill try that tomorrow.
Yes its a multi Launcher for the times Im too lazy to launch the menu and just want 2 or 3 Apps launched.

Am I right that instead of
StrCpy $Thunderbird "true"
I could directly launch TB?
Or, if I do that, Tb gets launched as soon as I clicked the box?
Because I don't want to launch my Apps till the very end.

My optimum would be just 2 "blocks":
A first one to set up the checkboxes and a second one who gets executed as soon as I press "install" and it checks all the boxes and launches the Apps which are marked.
But even if that's not possible, your suggestions will shrink my source considerably (I hope) Smile

"What about Love?" - "Overrated. Biochemically no different than eating large quantities of chocolate." - Al Pacino in The Devils Advocate

wraithdu
Offline
Last seen: 11 years 1 month ago
Developer
Joined: 2007-06-27 20:22
Am I right that instead

Am I right that instead of
StrCpy $Thunderbird "true"
I could directly launch TB?

I suppose you could do that. The leave function is just another function, but just executed when you hit the 'Next' button on the installer page. You could just as easily change the text on that button to 'Run', run all your apps from the leave function, and skip the Instfiles page altogether.

The purpose of the leave function is it can still access the data on the associated page, so you can store checkbox states to varibles and such. Otherwise I don't think that data is available to later pages.

But no, apps would not be launched when you check the box. In fact nothing will happen, not even any notifications. However you could do that using your previous code and an OnClick notify, then launch apps in your notify function. But that's not what you want.

I've created basically the same thing in AutoIt3, cause I can make custom GUI's with it. The way I did it was to read all data from an INI file. The INI data creates the name of the checkbox item and stores the EXE info, all from FOR loops. So I can add, remove, re-order, etc. the apps listed by editing the INI file, and I don't have to mess with my source.

I can post it if you're interested.

Simeon
Simeon's picture
Offline
Last seen: 9 years 9 months ago
DeveloperTranslator
Joined: 2006-09-25 15:15
Yep

Id be interested although I don't know AutoIT.
I use the new nsDialogs.nsh plugin. The old one had ini files too but some people said its faster without so I used the new one. Maybe using the old one would have saved me a couple of hours Smile

Thanks for all the details. Ill try the whole stuff later.

EDIT

YEEPEEE & THANKS!!!

It works. Exactly the way I wanted it to work from the beginning.
And your tips shrank my code from 303 lines to 133.
I'm so happy.

"What about Love?" - "Overrated. Biochemically no different than eating large quantities of chocolate." - Al Pacino in The Devils Advocate

wraithdu
Offline
Last seen: 11 years 1 month ago
Developer
Joined: 2007-06-27 20:22
Great job!

Great job!

I use nsDialogs as well for custom pages, I never did use the old one, ummmm, can't even remember the name. But yes, nsDialogs is supposed to be smaller and faster. In fact the new MUI2 that just went final in NSIS 2.34 now uses nsDialogs. So all you have to do in the installers is

#include MUI2.nsh

(with the lessthan / greaterthan around MUI2.nsh, silly board tags)

and it will bring in nsDialogs by default.

The only thing I found you have to do to update installers built with MUI1 to MUI2 is change the line breaks in custom language strings (if you have any) like this -

\r\n ===> $\r$\n

I did this for the PApps installer on my last two releases so they use MUI2.

wraithdu
Offline
Last seen: 11 years 1 month ago
Developer
Joined: 2007-06-27 20:22
AutoIt3 Launcher

Here's the AutoIt3 source and sample INI file. I run this launcher from a separate NSIS launcher which, among other things, mounts my TrueCrypt volume and sets some temporary environment variables. That's where the EnvGet("PADrive") comes from in the run section.

#Region ;**** Directives created by AutoIt3Wrapper_GUI ****
#AutoIt3Wrapper_Compression=4
#AutoIt3Wrapper_Res_Comment=Launch programs on startup.
#AutoIt3Wrapper_Res_Description=TCLaunch
#AutoIt3Wrapper_Res_Fileversion=1.0.0.8
#AutoIt3Wrapper_Res_LegalCopyright=by wraithdu
#AutoIt3Wrapper_Res_Language=1033
#EndRegion ;**** Directives created by AutoIt3Wrapper_GUI ****

#NoTrayIcon
Opt("GUIOnEventMode", 1)
#include [*lessthan*]GUIConstants.au3[*greaterthan*]

#Region ### START Koda GUI section ### Form=c:\documents\downloads\autoit3\scripts\tclaunch\tclaunch.kxf
$nGUI = GUICreate("TCLaunch", 171, 242, -1, -1)
$tvProgs = GUICtrlCreateTreeView(8, 8, 153, 137, BitOR($TVS_HASBUTTONS,$TVS_HASLINES,$TVS_DISABLEDRAGDROP,$TVS_SHOWSELALWAYS,$TVS_CHECKBOXES,$WS_GROUP,$WS_TABSTOP,$WS_BORDER))
$iUser = GUICtrlCreateInput("", 40, 152, 121, 21, BitOR($ES_PASSWORD,$ES_AUTOHSCROLL))
$iPass = GUICtrlCreateInput("", 40, 176, 121, 21, BitOR($ES_PASSWORD,$ES_AUTOHSCROLL))
$bRun = GUICtrlCreateButton("Run", 16, 208, 65, 25, 0)
$bExit = GUICtrlCreateButton("Exit", 88, 208, 65, 25, 0)
$Label1 = GUICtrlCreateLabel("user:", 8, 152, 27, 17)
$Label2 = GUICtrlCreateLabel("pass:", 8, 176, 29, 17)
#EndRegion ### END Koda GUI section ###

; Create tree view items
$iniSec = IniReadSection(@ScriptDir & "\launch.ini", "launch")
Dim $tvItems[$iniSec[0][0]] ; create array to hold controlIDs
For $i = 1 To $iniSec[0][0]
	$tvItems[$i - 1] = GUICtrlCreateTreeViewItem($iniSec[$i][0], $tvProgs) ; save controlIDs to array
Next

; GUI Events
GUISetOnEvent($GUI_EVENT_CLOSE, "GUIClose")

; Control Events
GUICtrlSetOnEvent($bRun, "Launch")
GUICtrlSetOnEvent($bExit, "GUIClose")

; show GUI
GUISetState(@SW_SHOW)

; loop
While 1
	Sleep(1000)
WEnd

;functions
Func GUIClose()
	Exit
EndFunc

Func Launch()
	GUISetState(@SW_HIDE)
	; check alternate credentials and RunAsSet
	If Not GUICtrlRead($iUser) = "" And Not GUICtrlRead($iPass) = "" Then
		RunAsSet(GUICtrlRead($iUser), "", GUICtrlRead($iPass))
	EndIf
	; launch checked items
	For $i = 1 To $iniSec[0][0]
		If BitAND(GUICtrlRead($tvItems[$i - 1]), $GUI_CHECKED) Then ; if checked, then run
			$execstr = EnvGet("PADrive") & "\" & $iniSec[$i][1]
			$wrkdir = StringLeft($execstr, StringInStr($execstr, "\", 0, -1))
			Run('"' & $execstr & '"', $wrkdir)
			;MsgBox(0, "", $execstr & @LF & $wrkdir)
			Sleep(1000) ; wait for run
		EndIf
	Next
	
	Exit
EndFunc

And the INI -

# relative path to root of mounted volume

[launch]
PStart=PortableApps\PStart\PStart.exe
CAFE=PortableApps\CAFE\cafe.exe
VirtualBox=PortableApps\VirtualBoxPortable\VBStart.bat
MojoPac=Start.exe
Simeon
Simeon's picture
Offline
Last seen: 9 years 9 months ago
DeveloperTranslator
Joined: 2006-09-25 15:15
@Wraithdu

Do you know how to rename the "install" button?

"What about Love?" - "Overrated. Biochemically no different than eating large quantities of chocolate." - Al Pacino in The Devils Advocate

wraithdu
Offline
Last seen: 11 years 1 month ago
Developer
Joined: 2007-06-27 20:22
Yep

Create the new function -

Function myGUIInit
	GetDlgItem $InstallButton $HWNDPARENT 1 ; install button
        SendMessage $InstallButton ${WM_SETTEXT} 0 "STR:Run" ; set button text
FunctionEnd

You can check out the ModernUI readme from the NSIS documentation to find out about built-in functions like myGUIInit.

Then place this define right before your nsDialogs Page definition (assuming you're using MUI2 for this launcher) -

!define MUI_CUSTOMFUNCTION_GUIINIT myGuiInit
Simeon
Simeon's picture
Offline
Last seen: 9 years 9 months ago
DeveloperTranslator
Joined: 2006-09-25 15:15
cool

Thank you so much!

"What about Love?" - "Overrated. Biochemically no different than eating large quantities of chocolate." - Al Pacino in The Devils Advocate

wraithdu
Offline
Last seen: 11 years 1 month ago
Developer
Joined: 2007-06-27 20:22
I just added a line I forgot

I just added a line I forgot about, so make sure you got that !define in there Wink

Simeon
Simeon's picture
Offline
Last seen: 9 years 9 months ago
DeveloperTranslator
Joined: 2006-09-25 15:15
its even easier

after I got a nasty error I searched the nsis manual and I foung that you can specify the Install button text with:

InstallButtonText Run

Mine says Run now Smile

"What about Love?" - "Overrated. Biochemically no different than eating large quantities of chocolate." - Al Pacino in The Devils Advocate

digitxp
digitxp's picture
Offline
Last seen: 12 years 10 months ago
Joined: 2007-11-03 18:33
I got an error

here are the last few lines:
Function: "myGUIInit"
Usage: GetDlgItem $(user_var: handle output) dialog item_id
Error in script "G:\Documents\Development\Gamesuite\GameSuite Portable\Other\Source\GameSuitePortable.nsi" on line 224 -- aborting creation process

Insert original signature here with Greasemonkey Script.

wraithdu
Offline
Last seen: 11 years 1 month ago
Developer
Joined: 2007-06-27 20:22
Hmmm

Can you post up the full source for what you're trying to compile and I'll take a look.

Or at least post up Line 224 so I know where the error came from.

I could have messed something up, I haven't used that code in a while (maybe missing an !include somewhere).

digitxp
digitxp's picture
Offline
Last seen: 12 years 10 months ago
Joined: 2007-11-03 18:33
Never mind

I used Simeon's idea.
Strangely enough, my graphcalc is saving into cafeMOD again...

Insert original signature here with Greasemonkey Script.

wraithdu
Offline
Last seen: 11 years 1 month ago
Developer
Joined: 2007-06-27 20:22
You'll also need...

to include

!include "WinMessages.nsh"

Sorry, I told ya I hadn't used that code in a while Wink

Ok, so I'm also a little drunk right now, and I can't for the life of me find Simeon's launcher source to try my code that I posted here and above to see if it works.

Can someone point me to the right place so I can dld it and put my stuff in and see if it works?

Thanks...wine is yummy Biggrin

Simeon
Simeon's picture
Offline
Last seen: 9 years 9 months ago
DeveloperTranslator
Joined: 2006-09-25 15:15
He posted

the whole package here, including the source.

"What about Love?" - "Overrated. Biochemically no different than eating large quantities of chocolate." - Al Pacino in The Devils Advocate

wraithdu
Offline
Last seen: 11 years 1 month ago
Developer
Joined: 2007-06-27 20:22
Figured it out

Ok, I know why everything failed....cause you're all using the default interface, not MUI2. Not that it really matters now, but here's the correct instructions (also posted in the GameSuitePortable thread) -

1. add !include WinMessages.nsh
2. add these 2 lines to the top of your nsDialogs page function (doesn't work in the .onGUIInit function when using nsDialogs for some reason) -

GetDlgItem $0 $HWNDPARENT 1 ; install button
SendMessage $0 ${WM_SETTEXT} 0 "STR:Start!" ; change text
Log in or register to post comments