I'm following the NSIS nsDialog tutorial with a goal to gather some user input I will use to write into a config file later. The NSISEclipse plugin has generated an MUI2 template that has gotten me started and successfully installs the files.

I have used the nsDialog tutorial to generate a dialog that does get emitted exactly where I want it to, but for some reason the "Back/Next/Cancel" buttons are all grey. I don't see where in the nsDialog documentation it says to enable/disable those buttons.

Here's my code:

Var Dialog
Var Label
Var MyTextBox
Section configLocationDialog
   nsDialogs::Create 1018
   Pop $Dialog
   ${If} $Dialog == error
       Abort
   ${EndIf}

   ${NSD_CreateLabel} 0 0 100% 12u "Hello, welcome to nsDialogs!"
   Pop $Label

   ${NSD_CreateText} 10% 20u 80% 12u "Hello World"
   Pop $MyTextbox

   nsDialogs::Show
SectionEnd

And, the dialog once displayed:

dialog with disabled buttons

What do I need to change to tell NSIS to allow back/next/cancel?

EDIT More code was asked for. Here's the whole thing as it exists now.

# Auto-generated by EclipseNSIS Script Wizard
# Dec 19, 2013 3:48:34 PM
Name SecureKeypad

# General Symbol Definitions
!define REGKEY "SOFTWARE\$(^Name)"
!define VERSION 1.0.0
!define COMPANY **COMPANY**
!define URL http://www.**COMPANY**.com

# MultiUser Symbol Definitions
!define MULTIUSER_EXECUTIONLEVEL Standard
!define MULTIUSER_INSTALLMODE_COMMANDLINE
!define MULTIUSER_INSTALLMODE_INSTDIR $PROGRAMFILES\SecureKeypad
!define MULTIUSER_INSTALLMODE_INSTDIR_REGISTRY_KEY "${REGKEY}"
!define MULTIUSER_INSTALLMODE_INSTDIR_REGISTRY_VALUE "Path"

# MUI Symbol Definitions
!define MUI_ICON "${NSISDIR}\Contrib\Graphics\Icons\modern-install-colorful.ico"
!define MUI_FINISHPAGE_NOAUTOCLOSE
!define MUI_STARTMENUPAGE_REGISTRY_ROOT HKLM
!define MUI_STARTMENUPAGE_NODISABLE
!define MUI_STARTMENUPAGE_REGISTRY_KEY ${REGKEY}
!define MUI_STARTMENUPAGE_REGISTRY_VALUENAME StartMenuGroup
!define MUI_STARTMENUPAGE_DEFAULTFOLDER SecureKeypad
!define MUI_UNICON "${NSISDIR}\Contrib\Graphics\Icons\modern-uninstall-colorful.ico"
!define MUI_UNFINISHPAGE_NOAUTOCLOSE

# Included files
#!include MultiUser.nsh
!include LogicLib.nsh
!include nsDialogs.nsh
!include AdvReplaceInFile.nsh
!include Sections.nsh
!include MUI2.nsh

# Variables
Var StartMenuGroup

# Installer pages
!insertmacro MUI_PAGE_WELCOME
!insertmacro MUI_PAGE_DIRECTORY
!insertmacro MUI_PAGE_STARTMENU Application $StartMenuGroup
!insertmacro MUI_PAGE_INSTFILES
!insertmacro MUI_PAGE_FINISH
!insertmacro MUI_UNPAGE_CONFIRM
!insertmacro MUI_UNPAGE_INSTFILES

# Installer languages
!insertmacro MUI_LANGUAGE English

# Installer attributes
OutFile setup.exe
CRCCheck on
InstallDir $PROGRAMFILES\${COMPANY}\SecureKeypad
XPStyle on
ShowInstDetails show
VIProductVersion 1.0.0.0
VIAddVersionKey ProductName SecureKeypad
VIAddVersionKey ProductVersion "${VERSION}"
VIAddVersionKey CompanyName "${COMPANY}"
VIAddVersionKey CompanyWebsite "${URL}"
VIAddVersionKey FileVersion "${VERSION}"
VIAddVersionKey FileDescription ""
VIAddVersionKey LegalCopyright ""
InstallDirRegKey HKLM "${REGKEY}" Path
ShowUninstDetails show

# Input dialogs
Var Dialog
Var Label
Var MyTextbox
#Page custom configLocationDialog configLocationDialogLeave
#Page custom doConfiguration
Section configLocationDialog
    nsDialogs::Create 1018
    Pop $Dialog
    ${If} $Dialog == error
        Abort
    ${EndIf}

    GetFunctionAddress $0 "configLocationDialogLeave"
    nsDialogs::OnBack $Dialog $0
    #nsDialogs::OnNext $Dialog

    ${NSD_CreateLabel} 0 0 100% 12u "Hello, welcome to nsDialogs!"
    Pop $Label

    ${NSD_CreateText} 10% 20u 80% 12u "Hello World"
    Pop $MyTextbox

    nsDialogs::Show
SectionEnd

Function configLocationDialogLeave
    ${NSD_GetText} $MyTextbox $0
    MessageBox mb_ok $0
FunctionEnd

# Installer sections
Section -Main SEC0000
    SetOutPath $INSTDIR
    SetOverwrite on
    File installable-content\CYBSSecurity.dll
    File installable-content\SecureKeypad.exe
    File installable-content\SecureKeypad.exe.config
    File installable-content\SecureKeypad.config
    File installable-content\SecureKeypad.frmSecureKeypad.resources
    WriteRegStr HKLM "${REGKEY}\Components" Main 1

    !insertmacro AdvReplaceInFile $INSTDIR\SecureKeypad.exe.config "@@configFile@@" $INSTDIR
SectionEnd

Section -post SEC0001
    WriteRegStr HKLM "${REGKEY}" Path $INSTDIR
    SetOutPath $INSTDIR
    WriteUninstaller $INSTDIR\uninstall.exe
    !insertmacro MUI_STARTMENU_WRITE_BEGIN Application
    SetOutPath $SMPROGRAMS\$StartMenuGroup
    CreateShortcut "$SMPROGRAMS\$StartMenuGroup\Uninstall $(^Name).lnk" $INSTDIR\uninstall.exe
    !insertmacro MUI_STARTMENU_WRITE_END
    WriteRegStr HKLM "SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\$(^Name)" DisplayName "$(^Name)"
    WriteRegStr HKLM "SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\$(^Name)" DisplayVersion "${VERSION}"
    WriteRegStr HKLM "SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\$(^Name)" Publisher "${COMPANY}"
    WriteRegStr HKLM "SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\$(^Name)" URLInfoAbout "${URL}"
    WriteRegStr HKLM "SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\$(^Name)" DisplayIcon $INSTDIR\uninstall.exe
    WriteRegStr HKLM "SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\$(^Name)" UninstallString $INSTDIR\uninstall.exe
    WriteRegDWORD HKLM "SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\$(^Name)" NoModify 1
    WriteRegDWORD HKLM "SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\$(^Name)" NoRepair 1
SectionEnd

# Macro for selecting uninstaller sections
!macro SELECT_UNSECTION SECTION_NAME UNSECTION_ID
    Push $R0
    ReadRegStr $R0 HKLM "${REGKEY}\Components" "${SECTION_NAME}"
    StrCmp $R0 1 0 next${UNSECTION_ID}
    !insertmacro SelectSection "${UNSECTION_ID}"
    GoTo done${UNSECTION_ID}
next${UNSECTION_ID}:
    !insertmacro UnselectSection "${UNSECTION_ID}"
done${UNSECTION_ID}:
    Pop $R0
!macroend

# Uninstaller sections
Section /o -un.Main UNSEC0000
    Delete /REBOOTOK $INSTDIR\SecureKeypad.frmSecureKeypad.resources
    Delete /REBOOTOK $INSTDIR\SecureKeypad.exe.config
    Delete /REBOOTOK $INSTDIR\SecureKeypad.exe
    Delete /REBOOTOK $INSTDIR\<sensored>.dll
    DeleteRegValue HKLM "${REGKEY}\Components" Main
SectionEnd

Section -un.post UNSEC0001
    DeleteRegKey HKLM "SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\$(^Name)"
    Delete /REBOOTOK "$SMPROGRAMS\$StartMenuGroup\Uninstall $(^Name).lnk"
    Delete /REBOOTOK $INSTDIR\uninstall.exe
    DeleteRegValue HKLM "${REGKEY}" StartMenuGroup
    DeleteRegValue HKLM "${REGKEY}" Path
    DeleteRegKey /IfEmpty HKLM "${REGKEY}\Components"
    DeleteRegKey /IfEmpty HKLM "${REGKEY}"
    RmDir /REBOOTOK $SMPROGRAMS\$StartMenuGroup
    RmDir /REBOOTOK $INSTDIR
SectionEnd

# Installer functions
Function .onInit
    InitPluginsDir
FunctionEnd

# Uninstaller functions
Function un.onInit
    !insertmacro MUI_STARTMENU_GETFOLDER Application $StartMenuGroup
    !insertmacro SELECT_UNSECTION Main ${UNSEC0000}
FunctionEnd
有帮助吗?

解决方案

Calling nsDialogs::Create/Show in a section is never valid, they can only be called in the create callback function of a custom page.

Some buttons will be disabled after the instfiles page (Already installed, cannot cancel or go back) but this is done by NSIS itself, not nsDialogs...

其他提示

If you put your call to nsDialogs:Create in a section it will be run when the installer is installing files and such. In that state you won't be able to keep navigating through the pages in the installer and you are stuck.

Your notice about your custom page running at the end of the installer is really what you should be trying to fix, not dismissing it as the wrong way (it's the only way). NSIS-scripts are quite simple in many ways. For example, pages are loaded in the order that they are declared. So when you declare that you want MUI_PAGE_WELCOME, MUI_PAGE_DIRECTORY and the others you are also setting the order of them.

# Installer pages
!insertmacro MUI_PAGE_WELCOME                                 # First page
!insertmacro MUI_PAGE_DIRECTORY                               # Second page
!insertmacro MUI_PAGE_STARTMENU Application $StartMenuGroup   # Third page
!insertmacro MUI_PAGE_INSTFILES                               # Etc
!insertmacro MUI_PAGE_FINISH
!insertmacro MUI_UNPAGE_CONFIRM
!insertmacro MUI_UNPAGE_INSTFILES

So if you then try to keep all your code together and add your custom page alongside the functions that handle it, it will undoubtedly be the last page in that order.

# Installer pages
!insertmacro MUI_PAGE_WELCOME                                 # First page
!insertmacro MUI_PAGE_DIRECTORY                               # Second page
!insertmacro MUI_PAGE_STARTMENU Application $StartMenuGroup   # Third page

...

# Input dialogs
Var Dialog
Var Label
Var MyTextbox
Page custom configLocationDialog configLocationDialogLeave    # Last page
Section configLocationDialog
  nsDialogs::Create 1018
  Pop $Dialog

So to illustrate this I took your code and brewed it down to basically the page you wanted.

    # Included files
!include LogicLib.nsh
!include nsDialogs.nsh
!include Sections.nsh
!include MUI2.nsh

# Installer pages
!insertmacro MUI_PAGE_WELCOME                                 # First page
Page custom configLocationDialog configLocationDialogLeave    # Second page!
!insertmacro MUI_PAGE_FINISH                                  # Last page

# Installer languages
!insertmacro MUI_LANGUAGE English

# Input dialogs
Var Dialog
Var Label
Var MyTextbox

Function configLocationDialog
    nsDialogs::Create 1018
    Pop $Dialog
    ${If} $Dialog == error
    Abort
    ${EndIf}

    GetFunctionAddress $0 "configLocationDialogLeave"
    nsDialogs::OnBack $Dialog $0

    ${NSD_CreateLabel} 0 0 100% 12u "Hello, welcome to nsDialogs!"
    Pop $Label

    ${NSD_CreateText} 10% 20u 80% 12u "Hello World"
    Pop $MyTextbox

    nsDialogs::Show
FunctionEnd

Function configLocationDialogLeave
    ${NSD_GetText} $MyTextbox $0
    MessageBox mb_ok $0
FunctionEnd

Section -Main SEC0000

SectionEnd

The NSISEclipse plugin generates a lot of code, including a set of macros that execute the various pages that are displayed:

# Installer pages
!insertmacro MUI_PAGE_WELCOME
!insertmacro MUI_PAGE_DIRECTORY
!insertmacro MUI_PAGE_STARTMENU Application $StartMenuGroup
!insertmacro MUI_PAGE_INSTFILES
!insertmacro MUI_PAGE_FINISH
!insertmacro MUI_UNPAGE_CONFIRM
!insertmacro MUI_UNPAGE_INSTFILES

The trick is to inject the page call at the right step.

# Installer pages
!insertmacro MUI_PAGE_WELCOME
!insertmacro MUI_PAGE_DIRECTORY
!insertmacro MUI_PAGE_STARTMENU Application $StartMenuGroup
Page custom configLocationDialog configLocationDialogLeave
!insertmacro MUI_PAGE_INSTFILES
!insertmacro MUI_PAGE_FINISH
!insertmacro MUI_UNPAGE_CONFIRM
!insertmacro MUI_UNPAGE_INSTFILES
许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top