; NSIS installer file
; Requires the NsExec and Inetc plugins

!include "MUI.nsh" ; modern UI
!include "FileFunc.nsh" ; to get estimated size for uinstaller display
!include "LogicLib.nsh"

RequestExecutionLevel admin
AutoCloseWindow true

; Compress installer exe
SetCompressor LZMA
SetCompress Force

; Folder selection page
InstallDir "$PROGRAMFILES\${GAME}"

; Finish page settings
Function .onInstSuccess
  ExecShell "open" "$INSTDIR\${EXE}" 
FunctionEnd

!insertmacro MUI_PAGE_DIRECTORY
!insertmacro MUI_PAGE_COMPONENTS
!insertmacro MUI_PAGE_INSTFILES
!insertmacro MUI_UNPAGE_CONFIRM
!insertmacro MUI_UNPAGE_INSTFILES
!insertmacro MUI_LANGUAGE "English"

BrandingText /TRIMRIGHT "${GAME} Installer"

!define TMPFILE "12345.tmp"
; validate installation dir by writing a dummy tmp file
Function .onVerifyInstDir
  IfFileExists "$INSTDIR\..\*.*" +2
  Abort

  ClearErrors
  FileOpen $0 "$INSTDIR\..\${TMPFILE}" "w"
  FileWriteByte $0 "0"
  IfErrors invalid valid

  invalid:
    Abort
  valid:
    FileClose $0
    Delete "$INSTDIR\..\${TMPFILE}"
FunctionEnd

; For updating file associations
!define SHCNE_ASSOCCHANGED 0x08000000
!define SHCNF_IDLIST 0
 
Function RefreshShellIcons
  ; By jerome tremblay - april 2003
  System::Call 'shell32.dll::SHChangeNotify(i, i, i, i) v \
  (${SHCNE_ASSOCCHANGED}, ${SHCNF_IDLIST}, 0, 0)'
FunctionEnd

Function CheckVC
  ; Test for Visual C++ distribution
  ;; See https://stackoverflow.com/questions/62092185/how-to-install-the-visual-c-redist-using-nsis
  ;; need to use nsExec plugin to prevent error popup (if redist is missing)
  ;; This doesn't actually work, so replace with a registry check
  ;; nsExec::Exec '"$INSTDIR\bin\dreamseeker.exe" -check-runtimes'
  ;; Pop $0
  ;; An error over 1 probably means Visual C++ wasn't available
  ;; ${If} $0 > 1

  ClearErrors
  EnumRegKey $0 HKLM "SOFTWARE\WOW6432Node\Microsoft\VisualStudio\14.0\VC\Runtimes\X86" 0
  ${If} ${Errors}
    ClearErrors
    EnumRegKey $0 HKLM "SOFTWARE\Microsoft\VisualStudio\14.0\VC\Runtimes\X86" 0
  ${EndIf}

  ${If} ${Errors}   # key does not exist
    DetailPrint "Downloading Visual C++ Redistributable package..."
    ; Sleep 5000 ; for testing
    inetc::get /CAPTION "Downloading Visual C++ Redistributable package..." "https://aka.ms/vs/17/release/vc_redist.x86.exe" $INSTDIR\vcredist.exe
    DetailPrint "Installing Visual C++ Redistributable package..."
    ExecWait '"$INSTDIR\vcredist.exe" /install /passive /norestart'
    DetailPrint "Done"
  ${EndIf}
FunctionEnd

; Program Files
Section "Game Files" SecPrograms

; Validate permissions
  ClearErrors
  UserInfo::GetName	; On NT-based systems this
			; will grab the current user's username.
  IfErrors user  	; If we don't get a username from this it means
			; the user isn't using an NT-based system.

  UserInfo::GetAccountType  ; Returns 'admin', 'power', 'user', or 'guest'
  Pop $1
  StrCmp $1 "Admin" admin 0
  StrCmp $1 "Power" admin user

admin:
  SetShellVarContext all
  Goto +2

user:
  SetShellVarContext current

  SetOutPath $INSTDIR
  SetOverwrite on
  SectionIn RO ; Can't unselect

  ;Only install known files and mimic for uninstall to avoid dangerous dir-deletes
  File "${FILEDIR}\${EXE}"
  File "${FILEDIR}\dd.exe"
  File "${FILEDIR}\byondcore.dll"
  File "${FILEDIR}\byondext.dll"
  File "${FILEDIR}\byondwin.dll"
  File "${FILEDIR}\fmodex.dll"
  File "${FILEDIR}\steam_api.dll"
  File "${FILEDIR}\WebView2Loader.dll"

  Call CheckVC
  
  WriteUninstaller "$INSTDIR\uninst.exe"

  Call RefreshShellIcons

SectionEnd

; Start Menu
Section "Start Menu" SecStartMenu
  CreateDirectory "$SMPROGRAMS\${GAME}"
  CreateShortCut "$SMPROGRAMS\${GAME}\${GAME}.lnk" "$INSTDIR\${EXE}" "" "$INSTDIR\${EXE}" 0
  CreateShortCut "$SMPROGRAMS\${GAME}\Uninstall ${GAME}.lnk" "$INSTDIR\uninst.exe" "" "$INSTDIR\uninst.exe" 0
SectionEnd

; Desktop icons
Section "Desktop Icons" SecDesktop
  CreateShortCut "$DESKTOP\${GAME}.lnk" "$INSTDIR\${EXE}" "" "$INSTDIR\${EXE}" 0
SectionEnd

Section "DirectX" SecDirectX
  SetOutPath $INSTDIR\directx
  SetOverwrite on
  File "${FILEDIR}\directx\DXSETUP.exe"
  File "${FILEDIR}\directx\DSETUP.dll"
  File "${FILEDIR}\directx\dsetup32.dll"
  File "${FILEDIR}\directx\dxupdate.cab"
  File "${FILEDIR}\directx\Jun2010_d3dx9_43_x86.cab"
  File "${FILEDIR}\directx\Jun2010_D3DCompiler_43_x86.cab"

  DetailPrint "Updating DirectX..."
  nsExec::ExecToStack '"${FILEDIR}\directx\DXSETUP.exe" /silent'
SectionEnd

; Quicklaunch (uncomment to use)
;Section "QuickLaunch Icons" SecQuickLaunch
;  CreateShortCut "$QUICKLAUNCH\${GAME}.lnk" "$INSTDIR\${EXE}" "" "$INSTDIR\${EXE}" 0
;SectionEnd

!insertmacro GetSize

; Registry for add/remove programs
Section "" Registry
  WriteRegStr SHELL_CONTEXT "Software\Microsoft\Windows\CurrentVersion\Uninstall\${GAME}" "DisplayName" "${GAME}"
  WriteRegStr SHELL_CONTEXT "Software\Microsoft\Windows\CurrentVersion\Uninstall\${GAME}" "UninstallString" "$INSTDIR\Uninst.exe"
  WriteRegStr SHELL_CONTEXT "Software\Microsoft\Windows\CurrentVersion\Uninstall\${GAME}" "InstallLocation" "$INSTDIR"
  WriteRegStr SHELL_CONTEXT "Software\Microsoft\Windows\CurrentVersion\Uninstall\${GAME}" "DisplayIcon" "$INSTDIR\${EXE}"
  WriteRegStr SHELL_CONTEXT "Software\Microsoft\Windows\CurrentVersion\Uninstall\${GAME}" "DisplayVersion" "${VERSION}"
  WriteRegStr SHELL_CONTEXT "Software\Microsoft\Windows\CurrentVersion\Uninstall\${GAME}" "Publisher" "${COMPANY}"
  WriteRegDWORD SHELL_CONTEXT "Software\Microsoft\Windows\CurrentVersion\Uninstall\${GAME}" "NoModify" 1
  WriteRegDWORD SHELL_CONTEXT "Software\Microsoft\Windows\CurrentVersion\Uninstall\${GAME}" "NoRepair" 1

; Get cumulative size of all files in and under install dir
; report the total in KB (decimal)
; place the answer into $0  ($1 and $2 get other info we don't care about)
  ${GetSize} "$INSTDIR" "/S=0K" $0 $1 $2

; Convert the decimal KB value in $0 to DWORD
; put it right back into $0
  IntFmt $0 "0x%08X" $0

  WriteRegDWORD SHELL_CONTEXT "Software\Microsoft\Windows\CurrentVersion\Uninstall\${GAME}" "EstimatedSize" $0
SectionEnd

; Descriptions
LangString DESC_SecPrograms ${LANG_ENGLISH} "Required Game Files"
LangString DESC_SecStartMenu ${LANG_ENGLISH} "Create Start Menu Shortcuts"
LangString DESC_SecDesktop ${LANG_ENGLISH} "Create Desktop Icons"
LangString DESC_SecDirectX ${LANG_ENGLISH} "Update DirectX"
;LangString DESC_QuickLaunch ${LANG_ENGLISH} "Create QuickLaunch Icons"
!insertmacro MUI_FUNCTION_DESCRIPTION_BEGIN
!insertmacro MUI_DESCRIPTION_TEXT ${SecDesktop} $(DESC_SecDesktop)
!insertmacro MUI_DESCRIPTION_TEXT ${SecStartMenu} $(DESC_SecStartMenu)
!insertmacro MUI_DESCRIPTION_TEXT ${SecPrograms} $(DESC_SecPrograms)
!insertmacro MUI_DESCRIPTION_TEXT ${SecDirectX} $(DESC_SecDirectX)
!insertmacro MUI_FUNCTION_DESCRIPTION_END

; Uninstaller
UninstallText "This will uninstall ${GAME} from your system"
Section Uninstall

  ClearErrors

; Delete known files in the installation to avoid dangerous dir-deletes
  Delete "$INSTDIR\${EXE}"
  Delete "$INSTDIR\byondcore.dll"
  Delete "$INSTDIR\byondext.dll"
  Delete "$INSTDIR\byondwin.dll"
  Delete "$INSTDIR\fmodex.dll"
  Delete "$INSTDIR\msvcp120.dll"
  Delete "$INSTDIR\msvcr120.dll"
  Delete "$INSTDIR\mfc120u.dll"
  Delete "$INSTDIR\steam_api.dll"
  Delete "$INSTDIR\WebView2Loader.dll"
  Delete "$INSTDIR\uninst.exe"

  Delete "$INSTDIR\directx\DXSETUP.exe"
  Delete "$INSTDIR\directx\DSETUP.dll"
  Delete "$INSTDIR\directx\dsetup32.dll"
  Delete "$INSTDIR\directx\dxupdate.cab"
  Delete "$INSTDIR\directx\Jun2010_d3dx9_43_x86.cab"
  Delete "$INSTDIR\directx\Jun2010_D3DCompiler_43_x86.cab"
  RMDir "$INSTDIR\directx"
  RMDir "$INSTDIR"

; Delete admin-installed links
  SetShellVarContext all
  Delete "$DESKTOP\${GAME}.lnk"
  Delete "$SMPROGRAMS\${GAME}\*.*"
  RmDir "$SMPROGRAMS\${GAME}"
  Delete "$QUICKLAUNCH\${GAME}.lnk"

; And repeat for current user in case this was installed with less permissions
  SetShellVarContext current
  Delete "$DESKTOP\${GAME}.lnk"
  Delete "$SMPROGRAMS\${GAME}\*.*"
  RmDir "$SMPROGRAMS\${GAME}"
  Delete "$QUICKLAUNCH\${GAME}.lnk"

; Delete uinstaller registry entries
  DeleteRegKey HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${GAME}"
  DeleteRegKey HKCU "Software\Microsoft\Windows\CurrentVersion\Uninstall\${GAME}"

SectionEnd
; End Uninstaller
