Insert bitmap inside a nsis label - nsis

I am trying to construct a page with has a horizontal area with coloured background. I did this using an empty label. Displaying no text and just fill color inside it.
On top on this now I want to add an image.
I ${NSD_CreateLabel} first and then after this wrote code for
${NSD_CreateBitmap} and ${NSD_SetImage}. I adjusted the X Y coordinates for image such that it sits on the label.
However, when I compile script, I only see the label. No bitmap image is displayed on top of it.
Can someone help with this?

The z-index (depth) of created controls is not defined/documented but in your case you should be able to just swap them so the label is not on top of the image:
Page Custom myPageCreate
Page InstFiles
!include nsDialogs.nsh
Function myPageCreate
nsDialogs::Create 1018
Pop $0
${NSD_CreateBitmap} 30% 30% 80% 80% ""
Pop $0
File "/oname=$pluginsdir\img.bmp" "${NSISDIR}\Contrib\Graphics\Wizard\arrow.bmp"
${NSD_SetImage} $0 "$pluginsdir\img.bmp" $1
${NSD_CreateLabel} 0 0 50% 50% "Hello"
Pop $0
SetCtlColors $0 000000 ff00cc
nsDialogs::Show
${NSD_FreeImage} $1
FunctionEnd

Related

Creating shortcut to console application in NSIS with particular font

I have an NSIS script which can create a shortcut to an application with CreateShortCut.
The application that the shortcut points to is a console application, but one which works much better if there is something other than the default font chosen. Of course, the user can be told to follow instructions like https://www.isunshare.com/windows-10/change-font-and-font-size-in-windows-10-command-prompt.html to change to a different font on the shortcut, but my quetsion is whether that can be automated in NSIS? That is, check if a particular font is available and then have the shortcut start a console with that font.
If that is impossible in NSIS for a particular shortcut, is there a way to give users the option to have a system-wide change to the font used in all terminals?
The CreateShortcut instruction only supports basic shortcut properties, it does not support console properties set by IShellLinkDataList.
Setting the NT_CONSOLE_PROPS data has two issues:
It is all or nothing, you have to set the size, color and edit options in addition to the font.
Ideally you should provide the "index of the font in the system's console font table" but that index is not really documented and I don't know how to map from a font name to the index.
If you still want to do it then you must use the System plug-in:
!include LogicLib.nsh
!include Win\COM.nsh ; NSIS v3
!define /ifndef LF_FACESIZE 32
!define /ifndef NT_CONSOLE_PROPS_SIG 0xA0000002
Section
StrCpy $R1 "$Desktop\MyApp.lnk" ; .Lnk path
StrCpy $R3 "Consolas" ; Font name
StrCpy $R5 i0x36 ; tmPitchAndFamily?
StrCpy $R6 400 ; "The weight can range from 100 to 1000, in multiples of 100. For example, the normal weight is 400, while 700 is bold"
StrCpy $R7 0xc0000 ; dwFontSize packed COORD
StrCpy $R8 0x200060 ; dwWindowSize packed COORD
System::Call '*(&l4,i${NT_CONSOLE_PROPS_SIG}, i0xf50007,i0x3e70050,i$R8,i0x0,i0x0,i0x0,i$R7,i$R5,i$R6, &w${LF_FACESIZE}"$R3", i0x19,i0x0,i0x1,i0x1,i0x1,i0x32,i0x4,i0x1,i0x0,i0x800000,i0x8000,i0x808000,i0x80,i0x800080,i0x8080,i0xc0c0c0,i0x808080,i0xff0000,i0xff00,i0xffff00,i0xff,i0xff00ff,i0xffff,i0xffffff)p.R2'
!insertmacro ComHlpr_CreateInProcInstance ${CLSID_ShellLink} ${IID_IShellLink} r0 ""
${If} $0 P<> 0
${IShellLink::SetPath} $0 '("%COMSPEC%").r1'
${IShellLink::SetArguments} $0 '("/k echo HelloWorld").r2'
${If} $1 = 0
${AndIf} $2 = 0
${IUnknown::QueryInterface} $0 '("${IID_IShellLinkDataList}",.r1)'
${If} $1 P<> 0
${IShellLinkDataList::AddDataBlock} $1 '(pR2).r2'
${IUnknown::Release} $1 ""
${EndIf}
${IUnknown::QueryInterface} $0 '("${IID_IPersistFile}",.r1)'
${If} $1 P<> 0
${IPersistFile::Save} $1 '("$R1",1).r2'
${IUnknown::Release} $1 ""
${EndIf}
${EndIf}
${IUnknown::Release} $0 ""
${EndIf}
System::Free $R2 ; Free NT_CONSOLE_PROPS
SectionEnd

Calling an Inno setup plugin from NSIS

I'm trying to use an Inno setup plugin called webcrtl (a web browser with more features than nsweb). I'm trying to call this dll with the system plugin.
The plugin:
http://restools.hanzify.org/article.asp?id=90
This is what I'm trying, without success:
Page custom Pre
Var hCtl_dialog
Var browser
Function Pre
InitPluginsDir
File "${BASEDIR}/Plugins/inno_webctrl_v2.1/webctrl.dll"
nsDialogs::Create 1018
Pop $hCtl_dialog
System::Call "webctrl::NewWebWnd(i $HWNDPARENT, i 100, i 100, i 200, i 200) i .s"
Pop $browser
System::Call "webctrl::DisplayHTMLPage(i '$browser', t 'http://www.google.com/') i .s"
Pop $R0
nsDialogs::Show $hCtl_neoinstaller_genericcustom
FunctionEnd
I'm getting an empty page...
DLL library function names are case sensitive, and you have used aliases instead of the function names from that InnoSetup script. Modify your script, so that will use function names with proper case sensitivity and you'll get your script to work. The name of a function to be imported, is the word before the # char from the external keyword import tail. For instance, in the following function import sample, the name of the imported function is newwebwnd, not NewWebWnd:
function NewWebWnd(hWndParent: HWND; X, Y, nWidth, nHeight: Integer): HWND;
external 'newwebwnd#files:webctrl.dll stdcall';
So in your case, modify the function names the following way and you should be fine:
...
System::Call "webctrl::newwebwnd(i $hCtl_dialog, i 0, i 0, i 150, i 150) i.s"
Pop $browser
System::Call "webctrl::displayhtmlpage(i $browser, t 'http://www.google.com/') b.s"
Pop $R0
...
The whole script for the WebCtrl control stretched inside the install page might then look like this:
!include "nsDialogs.nsh"
OutFile "Setup.exe"
RequestExecutionLevel user
InstallDir $DESKTOP\WebBrowserSetup
Page directory
Page custom InitializeWebBrowserPage
var hDialog
var hBrowser
Function InitializeWebBrowserPage
InitPluginsDir
SetOutPath $PLUGINSDIR
File "webctrl.dll"
nsDialogs::Create 1018
Pop $hDialog
; get the page client width and height
System::Call "*(i, i, i, i) i.r0"
System::Call "user32::GetClientRect(i $hDialog, i r0)"
System::Call "*$0(i, i, i.r1, i.r2)"
System::Free $0
; create a web browser window stretched to the whole page client rectangle
; and navigate somehwere; note that you should add some error handling yet
System::Call "webctrl::newwebwnd(i $hDialog, i 0, i 0, i $1, i $2) i.s"
Pop $hBrowser
System::Call "webctrl::displayhtmlpage(i $hBrowser, t 'http://www.google.com') b.s"
Pop $R0
nsDialogs::Show
FunctionEnd
Section ""
SectionEnd

Extra newline characters between items in a drop down menu

I am creating a installer using the nsis installer. In that installer I need to put a drop down menu for currency selection.
The text file which I am using is not being properly inserted, the newline character that I am using to separate the currencies is actually taking a character in the installer, while for the license page I am using the same extension for the text file which I am putting there and it is working fine over there.
How to filter out those extra characters?
Without a sample file I had to guess what the actual problem is, hopefully its just the newlines:
Page custom mycustompage
!include nsDialogs.nsh
!include TextFunc.nsh
Function mycustompage
nsDialogs::Create 1018
Pop $0
; I don't have a list of things so I generate one on the fly for this example:
!tempfile MYLIST
!appendfile "${MYLIST}" "Foo$\r"
!appendfile "${MYLIST}" "Bar$\r$\n"
!appendfile "${MYLIST}" "Baz$\n"
File "/oname=$pluginsdir\thelist.txt" "${MYLIST}" ; include list in installer
!delfile "${MYLIST}"
${NSD_CreateDropList} 10u 10u 50% 100% ""
Pop $0
FileOpen $1 "$pluginsdir\thelist.txt" r
loop:
FileRead $1 $2
IfErrors endloop
${TrimNewLines} $2 $2
StrCmp $2 "" loop ; skip empty line
${NSD_CB_AddString} $0 $2
goto loop
endloop:
nsDialogs::Show
FunctionEnd

Reading a text file into a text box using nsdialog? NSIS

I am new to NSIS scripting installer. I need to create a TextBox with Multiline support, in Custom page. Need to read a text file and set the text content to TextBox. Please find my code block below:
StrCpy $3 ""
FileOpen $4 "C:\Users\Surya\Desktop\Installer\License.txt" r
loop:
FileRead $4 $1
StrCpy $3 "$3$1" ; append the line and copy it to another variable
IfErrors +1 loop
FileClose $4
${NSD_SetText} $ctrlTextBox "$3"
The above code able to read only 8119 characters only, but my file contains 30,000+ characters.
Please help me to read the large file and set the content to TextBox.
Thank You
You can fill a textbox with a little bit of text at the time (inside your loop) if you use EM_SETSEL (twice) to move the caret to the end and then use EM_REPLACESEL to append text.
If you can use a rich edit box instead then use some code I wrote a long time ago, you can find the forum thread here...
Edit:
As long as the textbox is empty when you begin you don't have to deal with the caret:
function custcreate
nsDialogs::Create 1018
Pop $0
nsDialogs::CreateControl ${__NSD_Text_CLASS} ${__NSD_Text_STYLE}|${ES_MULTILINE}|${WS_VSCROLL}|${ES_READONLY} ${__NSD_Text_EXSTYLE} 0 0 100% 50u ""
Pop $0
FileOpen $4 ${__FILE__}" r
loop:
FileRead $4 $1
SendMessage $0 ${EM_REPLACESEL} 0 "STR:$1"
IfErrors +1 loop
FileClose $4
nsDialogs::Show
functionend

NSIS: How to add custom button to left bottom corner and handle it's click?

I tried the ButtonEvent plugin, but when I run compiled example, it fails with memory access error. Maybe it is able to do with System plugin via Windows API or something else? Can anyone show how it can be done?
UPD: Error was appeared because I tried to use non-unicode ButtonEvent on Unicode NSIS. Now example compiles and executes OK, but when I click on TryMe button, callback function is not called and nothing happens. How to determine what is the problem? Can anyone compile ButtonEventMUI.nsi and click on TryMe button? I downloaded latest ButtonEvent version. Using NSIS 2.46 Unicode
The system plugin cannot do this because it cannot subclass windows.
The ButtonEvent plugin works fine for me (NSIS 2.46):
Name BtnTest
Outfile test.exe
Installdir "$temp"
RequestExecutionLevel user
BrandingText " " ;Button covers this text
!include nsDialogs.nsh ;For WS_*
Function .onGuiInit
; You are supposed to use ChangeUI (or MUI_UI) and a modified ui file to add new buttons but this example adds the button at run-time...
GetDlgItem $0 $hwndparent 2 ; Find cancel button
System::Call *(i,i,i,i)i.r1
System::Call 'USER32::GetWindowRect(ir0,ir1)'
System::Call *$1(i.r2,i.r3,i.r4,i.r5)
IntOp $5 $5 - $3 ;height
IntOp $4 $4 - $2 ;width
System::Call 'USER32::ScreenToClient(i$hwndparent,ir1)'
System::Call *$1(i.r2,i.r3)
System::Free $1
IntOp $2 $2 + $4 ;x
IntOp $2 $2 + 8 ;x+padding
System::Call 'USER32::CreateWindowEx(i0,t "Button",t "Click Me",i${WS_CHILD}|${WS_VISIBLE}|${WS_TABSTOP},ir2,ir3,ir4,ir5,i $hwndparent,i 0x666,i0,i0)i.r0'
SendMessage $hwndparent ${WM_GETFONT} 0 0 $1
SendMessage $0 ${WM_SETFONT} $1 1
GetFunctionAddress $0 onmybtnclick
ButtonEvent::AddEventHandler 0x666 $0
FunctionEnd
Function onmybtnclick
MessageBox mb_ok "You clicked me!"
FunctionEnd
Page Directory
Page Instfiles
Section
SectionEnd

Resources