|
Компьютерный форум OSzone.net » Автоматическая установка Windows » Автоматическая установка приложений » Скрипты Inno Setup. Помощь и советы [часть 8] |
|
Скрипты Inno Setup. Помощь и советы [часть 8]
|
Ветеран Сообщения: 1264 |
Профиль | Отправить PM | Цитировать
Внимание! Данная тема предназначена только для обсуждения написания скриптов !
Остальные вопросы, а также последние версии компилятора в теме Inno Setup. Прочие вопросы. Показать/скрыть: Справка, руководство, примеры:
Показать/скрыть: Ссылки на примеры скриптов:
Показать/скрыть: Дополнительные программы для Inno Setup:
Предыдущие ветки обсуждения по ссылкам ниже и в прикреплённых архивах: Скрипты Inno Setup. Помощь и советы (Archive Pack 1):
Скрипты Inno Setup. Помощь и советы [часть 6] Скрипты Inno Setup. Помощь и советы [часть 7] |
|
Отправлено: 08:52, 02-02-2015 |
Новый участник Сообщения: 10
|
Профиль | Отправить PM | Цитировать
Добавил IDPForm.FileProgressBar.Visible := False; IDPForm.TotalProgressBar.Visible := False; в результате получилось такое окно (на скрепке)
|
||||
Отправлено: 14:31, 09-08-2017 | #2021 |
Для отключения данного рекламного блока вам необходимо зарегистрироваться или войти с учетной записью социальной сети. Если же вы забыли свой пароль на форуме, то воспользуйтесь данной ссылкой для восстановления пароля. |
Пользователь Сообщения: 76
|
Профиль | Отправить PM | Цитировать Как сделать чтобы при изменении пути в DirEdit кнопка NewButton становилась активной, а при нажатии на кнопку NewButton
она становилась неактивной? |
Отправлено: 00:09, 10-08-2017 | #2022 |
Новый участник Сообщения: 33
|
Профиль | Отправить PM | Цитировать
Господа, есть тут кто-нибудь, кто разбирается в Unicode-версии Inno Setup?
Или возможно ли отключить жёсткую проверку синтаксиса? Установил Inno Setup с поддержкой Unicode, чтобы корректно отображалось название языков. При компиляции появляются ошибки, а в обычной версии компиляция скрипта проходит без каких-либо проблем. Что делать с этой строкой "record..."? Сам скрипт
#include "botva2.iss" #include "BASS_Module.iss" #define GDFExe "{app}\Prog.exe" #define GDFBinary "{app}\GDF.dll" [Setup] SourceDir=. OutputDir=Setup AppName=MyProg AppVersion=1.0 AppPublisher=EmuGames AppCopyright=EmuGames AppPublisherURL= AppSupportURL= AppUpdatesURL= DefaultDirName={pf64}\MyProg™ DefaultGroupName=\MyProg™ AllowNoIcons=yes InfoBeforeFile=\System requirements.txt InfoAfterFile=\Recommendation.txt OutputBaseFilename=setup WizardImageFile=\picture.bmp WizardSmallImageFile=\small picture.bmp SetupIconFile=\icon.ico WindowVisible=no WindowShowCaption=no WindowResizable=no Compression=none CompressionThreads=4 DiskSpanning=yes DiskSliceSize=2100000000 SlicesPerDisk=1 RestartIfNeededByRun=no ShowUndisplayableLanguages=yes [Languages] Name: russian; MessagesFile: compiler:Languages\Russian.isl Name: english; MessagesFile: compiler:Languages\English.isl Name: french; MessagesFile: compiler:Languages\French.isl Name: german; MessagesFile: compiler:Languages\German.isl Name: spanish; MessagesFile: compiler:Languages\Spanish.isl Name: italian; MessagesFile: compiler:Languages\Italian.isl [Messages] SelectLanguageTitle=MyProg SelectLanguageLabel=Please select a language. Выберите язык установки. [LangOptions] russian.LanguageName=Русский / Russian english.LanguageName=Английский / English french.LanguageName=Французский / French german.LanguageName=Немецкий / German spanish.LanguageName=Испанский / Spanish italian.LanguageName=Итальянский / Italian [Tasks] Name: desktopicon; Description: Создать ярлык на рабочем столе; GroupDescription: Ярлыки: Name: pin; Description: Закрепить ярлык на панели задач; GroupDescription: Ярлыки:; Flags: unchecked Name: DirectX; Description: Обновить DirectX; GroupDescription: Дополнительное программное обеспечение:; Flags: checkablealone Name: Redist; Description: Установить Microsoft Visual C++ 2010 Redist; GroupDescription: Дополнительное программное обеспечение:; Flags: checkablealone Name: desktopicon; Description: Русский | Английский | Multi6; GroupDescription: Язык интерфейса:; Flags: exclusive [Files] Source: include/GDF.dll; DestDir: {app}; Source: include/GameuxInstallHelper.dll; DestDir: {localappdata}; Flags: overwritereadonly Source: CallbackCtrl.dll; DestDir: {tmp}; Flags: dontcopy Source: BASS.dll; DestDir: {tmp}; Flags: dontcopy Source: innocallback.dll; Flags: dontcopy Source: botva2.dll; DestDir: {tmp}; Flags: dontcopy Source: Bass_Files\*; DestDir: {tmp}; Flags: dontcopy Source: OST.mp3; DestDir: {tmp}; Flags: dontcopy Source: "\MyProg™.png"; DestDir: {tmp}; Flags: ignoreversion dontcopy nocompression Source: "\miniature.png"; DestDir: {tmp}; Flags: ignoreversion dontcopy nocompression Source: "\miniature-2.png"; DestDir: {tmp}; Flags: ignoreversion dontcopy nocompression Source: "isgsg.dll"; DestDir: {tmp}; Flags: ignoreversion dontcopy nocompression Source: "\Pakovano\*"; DestDir: "{app}"; Flags: ignoreversion recursesubdirs createallsubdirs sortfilesbyextension; [Icons] Name: "{userdesktop}\MyProg"; Filename: "{app}\MyProg.exe"; WorkingDir: "{app}"; Tasks: desktopicon; Name: "{group}\MyProg"; Filename: "{app}\MyProg.exe"; Name: "{group}\{cm:UninstallProgram,MyProg}"; Filename: "{uninstallexe}" [Run] Description: {cm:LaunchProgram, MyProg}; Filename: {app}\MyProg.exe; WorkingDir: {app}; Flags: nowait postinstall skipifsilent Filename: {src}\Soft\DirectX®\DXSETUP.exe; Parameters: /silent; Tasks: DirectX; StatusMsg: Обновление DirectX... Filename: {src}\Soft\Vcredist\Vcredist_2010 (x64+x86).exe; Parameters: /q; Tasks: Redist; StatusMsg: Установка Microsoft Visual С++ 2010 Redistributable... [UninstallDelete] Type: filesandordirs; Name: "{app}"; Type: filesandordirs; Name: "{localappdata}\Spoon"; Type: filesandordirs; Name: "{localappdata}\VirtualStore"; [Сode] type TGUID = record Data1: Cardinal; Data2, Data3: Word; Data4: array [0..8] of Char; end; const PlayTask = 0; SupportTask = 1; var GameuxGUID: TGUID; function GenerateGUID(var GUID: TGUID): Cardinal; external 'GenerateGUID@files:GameuxInstallHelper.dll stdcall setuponly'; function AddToGameExplorer(Binary: String; Path: String; InstallType: Integer; var GUID: TGUID): Cardinal; external 'AddToGameExplorerA@files:GameuxInstallHelper.dll stdcall setuponly'; function CreateTask(InstallType: Integer; var GUID: TGUID; TaskType: Integer; TaskNumber: Integer; TaskName: String; Binary: String; Parameters: String): Cardinal; external 'CreateTaskA@files:GameuxInstallHelper.dll stdcall setuponly'; function RetrieveGUIDForApplication(Binary: String; var GUID: TGUID): Cardinal; external 'RetrieveGUIDForApplicationA@{localappdata}\GameuxInstallHelper.dll stdcall uninstallonly'; function RemoveFromGameExplorer(var GUID: TGUID): Cardinal; external 'RemoveFromGameExplorer@{localappdata}\GameuxInstallHelper.dll stdcall uninstallonly'; function RemoveTasks(var GUID: TGUID): Cardinal; external 'RemoveTasks@{localappdata}\GameuxInstallHelper.dll stdcall uninstallonly'; function IntToHex(Int: Cardinal; Digits: Integer): String; var i, Digit: Integer; ch: Byte; begin result:=''; for i:=0 to Digits-1 do begin digit:=Int mod 16; Int:=Int div 16; if digit<0 then digit:=digit+16; ch:=Ord('0')+digit; if digit>9 then ch:=ch+7; result:=chr(ch)+result; end; end; function GetGUID(GGUID: TGUID): String; var i: Integer; begin result:='{'+IntToHex(GGUID.Data1, 8)+'-'+IntToHex(GGUID.Data2, 4)+'-'+IntToHex(GGUID.Data3, 4)+'-'+IntToHex(Ord(GGUID.Data4[0]), 2)+IntToHex(Ord(GGUID.Data4[1]), 2)+'-'; for i:=2 to 7 do result:=result+IntToHex(Ord(GGUID.Data4[i]), 2); result:=result+'}'; end; procedure GDFInstall(Binary, MainExe: String); begin GenerateGUID(GameuxGUID); AddToGameExplorer(ExpandConstant(Binary), ExpandConstant('{app}'), 3, GameuxGUID); CreateTask(3, GameuxGUID, PlayTask, 0, 'Play', ExpandConstant(MainExe), ''); end; procedure win7fix; var regGDF: Cardinal; var GUXPath: string; begin GUXPath := 'Software\Microsoft\Windows\CurrentVersion\GameUX\Games\' + GetGUID(GameuxGUID); if isWin64 then begin if RegQueryDWordValue(HKLM64, GUXPath, 'IsSigned', regGDF) then if regGDF=0 then if RegDeleteValue(HKLM64, GUXPath, 'IsSigned') then RegWriteDWordValue(HKLM64, GUXPath, 'IsSigned', 1); end else begin if RegQueryDWordValue(HKLM, GUXPath, 'IsSigned', regGDF) then if regGDF=0 then if RegDeleteValue(HKLM, GUXPath, 'IsSigned') then RegWriteDWordValue(HKLM, GUXPath, 'IsSigned', 1); end; end; type TPBProc = function (h:hWnd;Msg,wParam,lParam:Longint):Longint; var TimeLeftLabel : TLabel; PBOldProc : Longint; eTime, sTime : DWORD; var BASS_Initialized: Boolean; const AW_BLEND = $00080000; AW_HIDE = $00010000; const LOAD_LIBRARY_AS_DATAFILE = $2; #define A = (Defined UNICODE) ? "W" : "A" function AnimateWindow(hWnd: HWND; dwTime: DWORD; dwFlags: DWORD): Boolean; external 'AnimateWindow@user32 stdcall'; function LoadLibraryEx(lpFileName: String; hFile: THandle; dwFlags: DWORD): THandle; external 'LoadLibraryEx{#A}@kernel32.dll stdcall'; function LoadString(hInstance: THandle; uID: SmallInt; var lpBuffer: Char; nBufferMax: Integer): Integer; external 'LoadString{#A}@user32.dll stdcall'; function SHGetNewLinkInfo(pszLinkTo, pszDir: String; var pszName: Char; var pfMustCopy: Longint; uFlags: UINT): BOOL; external 'SHGetNewLinkInfo{#A}@shell32.dll stdcall'; function PinToTaskbar(const szFilename: String; IsPin: Boolean): Boolean; var hInst: THandle; buf: array [0..255] of Char; i, res: Integer; strLnk, strVerb: String; objShell, colVerbs: Variant; begin Result := False; if (GetWindowsVersion < $06010000) or not FileExists(szFilename) then Exit; { below Windows 7 } { String resources } if IsPin then begin if SHGetNewLinkInfo(szFilename, ExpandConstant('{tmp}'), buf[0], res, 0) then begin while buf[Length(strLnk)] <> #0 do Insert(buf[Length(strLnk)], strLnk, Length(strLnk)+1); if FileExists(ExpandConstant('{userappdata}\Microsoft\Internet Explorer\Quick Launch\User Pinned\TaskBar\') + ExtractFileName(strLnk)) then Exit; end; res := 5386; { Pin to Tas&kbar } end else res := 5387; { Unpin from Tas&kbar } { Load string resource } hInst := LoadLibraryEx(ExpandConstant('{sys}\shell32.dll'), 0, LOAD_LIBRARY_AS_DATAFILE); if hInst <> 0 then try for i := 0 to LoadString(hInst, res, buf[0], 255)-1 do Insert(buf[i], strVerb, i+1); try objShell := CreateOleObject('Shell.Application'); colVerbs := objShell.Namespace(ExtractFileDir(szFilename)).ParseName(ExtractFileName(szFilename)).Verbs; for i := 1 to colVerbs.Count do if CompareText(colVerbs.Item[i].Name, strVerb) = 0 then begin colVerbs.Item[i].DoIt; Result := True; Break; end; except Exit; end; finally FreeDLL(hInst); end; end; type TTimerProc = procedure(HandleW, Msg, idEvent, TimeSys: LongWord); var PercentsTimer: LongWord; PercentsLabel: TLabel; function SetWindowLong(hWnd: HWND; nIndex: Integer; dwNewLong: Longint): Longint; external 'SetWindowLongA@user32.dll stdcall'; function CallBackProc(P:TPBProc;ParamCount:integer):LongWord; external 'wrapcallbackaddr@files:CallbackCtrl.dll stdcall'; function CallWindowProc(lpPrevWndFunc: Longint; hWnd: HWND; Msg: UINT; wParam, lParam: Longint): Longint; external 'CallWindowProcA@user32.dll stdcall'; function GetTickCount: DWORD; external 'GetTickCount@kernel32.dll stdcall'; function WrapTimerProc(callback: TTimerProc; Paramcount: Integer): longword; external 'wrapcallback@files:innocallback.dll stdcall'; function SetTimer(hWnd, nIDEvent, uElapse, lpTimerFunc: LongWord): longword; external 'SetTimer@user32'; function KillTimer(hWnd, nIDEvent: LongWord): LongWord; external 'KillTimer@user32 stdcall delayload'; function LongintToStringTime(t:Longint):string; var h,m,s:integer; begin h:=t div 3600; t:=t-h*3600; m:=t div 60; s:=t-m*60; Result:=''; if h>0 then Result:=Result+IntToStr(h)+' ч. '; if (m>0) or (h>0) then Result:=Result+IntToStr(m)+' мин. '; if (m>0) or (h>0) or (s>0) then Result:=Result+IntToStr(s)+' сек.'; end; function PBProc(h:hWnd;Msg,wParam,lParam:Longint):Longint; var lt:Longint; dt,at,pr,i1,i2:Extended; p:string; tc:DWORD; begin Result:=CallWindowProc(PBOldProc,h,Msg,wParam,lParam); if (Msg=$402) and (WizardForm.ProgressGauge.Position>WizardForm.ProgressGauge.Min) then begin i1:=WizardForm.ProgressGauge.Position-WizardForm.ProgressGauge.Min; i2:=WizardForm.ProgressGauge.Max-WizardForm.ProgressGauge.Min; tc:=GetTickCount; if (tc-eTime)>=1000 then begin //???????????? ????? ?????????? ?? ????? ????????? ?? ????, ??? ??? ? 1 ??????? dt:=(tc-sTime)/1000; at:=i2*dt/i1; lt:=Round(at-dt) TimeLeftLabel.Caption:='Осталось - '+LongintToStringTime(lt); eTime:=tc; end; pr:=i1*100/i2; p:=' - ['+Format('%f',[pr])+'%]'; StringChange(p,',','.'); end; end; procedure AllCancel; begin SetWindowLong(WizardForm.ProgressGauge.Handle,-4,PBOldProc); TimeLeftLabel.Free; end; function InitializeSetup:boolean; begin if not FileExists(ExpandConstant('{tmp}\CallbackCtrl.dll')) then ExtractTemporaryFile('CallbackCtrl.dll'); Result:=True; end; Function NumToStr(Float: Extended): String; Begin Result:= Format('%.1n', [Float]); StringChange(Result, ',', '.'); while ((Result[Length(Result)] = '0') or (Result[Length(Result)] = '.')) and (Pos('.', Result) > 0) do SetLength(Result, Length(Result)-1); End; Procedure PercentsProc(h, msg, idevent, dwTime: Longword); Begin with WizardForm.ProgressGauge do begin PercentsLabel.Caption:= 'Выполнено ' + NumToStr((Position*100)/Max) + ' %'; end; End; const Indent=25; function GetWindowLong(hWnd: HWND; nIndex: Integer): Longint; external 'GetWindowLongA@user32.dll stdcall delayload'; function ssInitialize(hParent:HWND;ssTimeShow:integer;FadeOut:boolean;StretchMode:integer;BkgColor:DWORD):boolean; external 'ssInitialize@files:isgsg.dll stdcall delayload'; procedure ssDeInitialize; external 'ssDeInitialize@files:isgsg.dll stdcall delayload'; procedure ssSetBkgImage(FileName:PChar); external 'ssSetBkgImage@files:isgsg.dll stdcall delayload'; procedure ssAddImage(FileName:PChar); external 'ssAddImage@files:isgsg.dll stdcall delayload'; procedure ssStartShow; external 'ssStartShow@files:isgsg.dll stdcall delayload'; procedure ssStopShow; external 'ssStopShow@files:isgsg.dll stdcall delayload'; procedure ShowSplashScreen(p1:HWND;p2:string;p3,p4,p5,p6,p7:integer;p8:boolean;p9:Cardinal;p10:integer); external 'ShowSplashScreen@files:isgsg.dll stdcall delayload'; function GetSystemMetrics(nIndex:Integer):integer; external 'GetSystemMetrics@user32.dll stdcall delayload'; procedure RunListClickCheck(Sender: TObject); var i:integer; begin if WizardForm.RunList.Checked[WizardForm.RunList.ItemIndex] then begin for i:=0 to WizardForm.RunList.Items.Count-1 do WizardForm.RunList.Checked[i]:=False; WizardForm.RunList.Checked[WizardForm.RunList.ItemIndex]:=True; end; end; procedure InitializeWizard(); begin ExtractTemporaryFile('Bass.dll'); ExtractTemporaryFile('botva2.dll'); ExtractTemporaryFile('volmax.png'); ExtractTemporaryFile('volmin.png'); ExtractTemporaryFile('volpb.png'); ExtractTemporaryFile('voldote.png'); ExtractTemporaryFile('OST.mp3'); ExtractTemporaryFile('MusicButton.png'); ExtractTemporaryFile('miniature.png'); ExtractTemporaryFile('miniature-2.png'); ShowSplashScreen(WizardForm.Handle,ExpandConstant('{tmp}')+'\miniature.png',4000,4000,2000,0,255,False,$FFFFFF,10); ShowSplashScreen(WizardForm.Handle,ExpandConstant('{tmp}')+'\miniature-2.png',4000,4000,2000,0,255,False,$FFFFFF,10); ssInitialize(GetWindowLong(MainForm.Handle,-8),5,True,1,$FF000000); WizardForm.RunList.OnClickCheck:=@RunListClickCheck; BASS_Init('{tmp}\OST.mp3') BASS_CreateMediaPlayer(WizardForm, '{tmp}\volmax.png', '{tmp}\volmin.png', '{tmp}\volpb.png', '{tmp}\voldote.png', 20, 325) BASS_Initialized := True; ExtractTemporaryFile('MyProg™.png'); ssSetBkgImage(ExpandConstant('{tmp}')+'\MyProg™.png'); WizardForm.TypesCombo.ItemIndex:=0; PercentsLabel:= TLabel.Create(WizardForm); with PercentsLabel do begin Left:= WizardForm.ProgressGauge.Left; Top:= WizardForm.ProgressGauge.Top + WizardForm.ProgressGauge.Height + ScaleY(10); Width:= WizardForm.StatusLabel.Width; Height:= WizardForm.StatusLabel.Height; AutoSize:= False; Transparent := True; Parent:= WizardForm.InstallingPage; end; end; procedure CurStepChanged(CurStep: TSetupStep); var Version: TWindowsVersion; begin GetWindowsVersionEx(Version); if (CurStep = ssPostInstall) and Version.NTPlatform and (Version.Major > 5) then begin GDFInstall('{#GDFBinary}', '{#GDFExe}'); win7fix; end; begin case CurStep of ssInstall: begin TimeLeftLabel:=TLabel.Create(nil); with TimeLeftLabel do begin Parent:=WizardForm.InstallingPage; AutoSize:=True; SetBounds(WizardForm.ProgressGauge.Left + ScaleX(250),WizardForm.ProgressGauge.Top + ScaleY(30),ScaleY(80),ScaleY(21)); end; sTime:=GetTickCount; eTime:=sTime; PBOldProc:=SetWindowLong(WizardForm.ProgressGauge.Handle,-4,CallBackProc(@PBProc,4)); end; ssPostInstall: AllCancel; end; begin if CurStep=ssInstall then begin PercentsTimer:= SetTimer(0, 0, 100, WrapTimerProc(@PercentsProc, 4)); ExtractTemporaryFile('MyProg™.png'); ssAddImage(ExpandConstant('{tmp}')+'\MyProg™.png'); end; if CurStep=ssPostInstall then ssStopShow; end; end; end; procedure CurPageChanged(CurPageID: Integer); begin case CurPageID of wpFinished: end if IsTaskSelected('Pin') then PinToTaskbar(ExpandConstant('{app}\MyProg.exe'), True); if CurPageID=wpInstalling then begin; WizardForm.MainPanel.Visible:=False; WizardForm.Bevel1.Visible:=False; WizardForm.Width:=ScaleX(395); WizardForm.Height:=ScaleY(142); WizardForm.Left:=ScaleX(GetSystemMetrics(0)-WizardForm.Width-Indent); WizardForm.Top:=ScaleY(GetSystemMetrics(1)-WizardForm.Height-Indent); WizardForm.InnerNotebook.Left:=ScaleX(10); WizardForm.InnerNotebook.Top:=ScaleY(10); WizardForm.InnerNotebook.Width:=ScaleX(370); WizardForm.StatusLabel.Left:=ScaleX(0); WizardForm.StatusLabel.Top:=ScaleY(0); WizardForm.StatusLabel.Width:=WizardForm.InnerNotebook.Width; WizardForm.FileNameLabel.Left:=ScaleX(0); WizardForm.FileNameLabel.Top:=ScaleY(20); WizardForm.FileNameLabel.Width:=WizardForm.InnerNotebook.Width; WizardForm.ProgressGauge.Top:=ScaleY(40); WizardForm.ProgressGauge.Width:=WizardForm.InnerNotebook.Width; WizardForm.CancelButton.Left:=ScaleX(154); WizardForm.CancelButton.Top:=ScaleY(80); end; if (CurPageID=wpFinished) or (CurPageID=wpInfoAfter) then begin WizardForm.RunList.Checked[0]:=True; if WizardForm.Width<>502 then begin WizardForm.Visible:=False; WizardForm.Width:=ScaleX(502); WizardForm.Height:=ScaleY(392); WizardForm.Left:=(GetSystemMetrics(0)-WizardForm.Width) div 2; WizardForm.Top:=(GetSystemMetrics(1)-WizardForm.Height) div 2; WizardForm.MainPanel.Visible:=True; WizardForm.Bevel1.Visible:=True; WizardForm.InnerNotebook.Left:=ScaleX(40); WizardForm.InnerNotebook.Top:=ScaleY(72); WizardForm.InnerNotebook.Width:=ScaleX(417); WizardForm.Visible:=True; end; end; end; function NextButtonClick(CurPageID: Integer): Boolean; begin Result := True; if CurPageID=wpFinished then begin if WizardForm.RunList.Checked[0] then Result := True; end; end; procedure CancelButtonClick(CurPageID: Integer; var Cancel, Confirm: Boolean); begin if MsgBox(SetupMessage(msgExitSetupMessage), mbConfirmation, MB_OKCANCEL) = IDOK then begin Confirm := False; AnimateWindow(WizardForm.Handle, 2500, AW_BLEND or AW_HIDE); Cancel := True; end else Cancel := False; end; procedure CurUninstallStepChanged(CurUninstallStep: TUninstallStep); var Binary: String; GUID: TGUID; begin if CurUninstallStep=usUninstall then begin Binary:=ExpandConstant('{#GDFBinary}'); RetrieveGUIDForApplication(Binary, GUID); RemoveFromGameExplorer(GUID); RemoveTasks(GUID); UnloadDll(ExpandConstant('{localappdata}\GameuxInstallHelper.dll')); end; begin if (CurUninstallStep=usUninstall) then begin case CurUninstallStep of usUninstall: begin PinToTaskbar(ExpandConstant('{app}\MyProg.exe'), False); end; end; end; end; end; procedure DeinitializeSetup(); begin if BASS_Initialized then begin KillTimer(0, PercentsTimer); ssDeInitialize; BASS_DeInit; gdipShutdown end; end; Буду очень благодарен за помощь. |
||||||||
Последний раз редактировалось OldGamer, 10-08-2017 в 23:01. Отправлено: 20:14, 10-08-2017 | #2023 |
Новый участник Сообщения: 28
|
Профиль | Отправить PM | Цитировать Пытаюсь прикрутить к Inno чтение с консоли, причем нужна реализация через пайпы и чтобы текст построчно отображался в Memo.
Пытаюсь адаптировать следующий пример, 3-ий на странице (RunDosInMemo): http://decoding.dax.ru/faq/vcl/console/console001.html Вроде почти перевел, но осталась заморочка именно с чтением через ReadFile и вывод, соответственно в Memo, да, там должны передаваться символы и строки, у меня счас там цифры, содрал с одного примера, но подружить с текстом не удается. Просьба продвинутых поправить пример, если это возможно. Скрипт (для версии Unicode)
[Setup] AppName=MyApp Appvername=MyApp DefaultDirname={pf}\MyApp [_Code] const ReadBuffer = 2400; STARTF_USESTDHANDLES = $100; STARTF_USESHOWWINDOW = 1; NORMAL_PRIORITY_CLASS = $00000020; HEAP_ZERO_MEMORY = $0008; WAIT_TIMEOUT = $00000102; type TMyMsg = record hWnd: HWND; msg, wParam: Word; lParam: LongWord; Time: TFileTime; pt: TPoint; end; type TSecurityAttributes = record nLength: DWord; lpSecurityDescriptor: longint; bInheritHandle: Boolean; end; TProcessInformation = record hProcess:DWORD; hThread:DWORD; dwProcessId:DWORD; dwThreadId:DWORD; end; TStartupInfo = record cb:DWORD; lpReserved:DWORD; // not PChar; - need NULL pointer lpDesktop:DWORD; // not PChar; - need NULL pointer lpTitle:DWORD; // not PChar; - need NULL pointer dwX:DWORD; dwY:DWORD; dwXSize:DWORD; dwYSize:DWORD; dwXCountChars:DWORD; dwYCountChars:DWORD; dwFillAttribute:DWORD; dwFlags:DWORD; wShowWindow:WORD; cbReserved2:WORD; lpReserved2:DWORD; hStdInput:DWORD; hStdOutput:DWORD; hStdError:DWORD; end; // ----------------------------------------------------------- // function PeekMessage(var lpMsg: TMyMsg; hWnd: HWND; wMsgFilterMin, wMsgFilterMax, wRemoveMsg: UINT): BOOL; external 'PeekMessageW@user32.dll stdcall'; function TranslateMessage(const lpMsg: TMyMsg): BOOL; external 'TranslateMessage@user32.dll stdcall'; function DispatchMessage(const lpMsg: TMyMsg): Longint; external 'DispatchMessageW@user32.dll stdcall'; // ----------------------------------------------------------- // function CloseHandle(hObject: THandle): BOOLEAN; external 'CloseHandle@kernel32.dll stdcall'; function CreateProcess(lpApplicationName: String; lpCommandLine: string; lpProcAttrib,lpThreadAttrib: TSecurityAttributes; bInheritHandles: Boolean; dwCreationFlags: DWORD; lpEnvironment:DWORD; lpCurrentDirectory: String; var lpStartupInfo:TStartupInfo; var lpProcessInfo:TProcessInformation): Boolean; external 'CreateProcessW@kernel32.dll stdcall'; function CreatePipe(out hReadPipe,hWritePipe: THandle; lpPipeAttributes: TSecurityAttributes; nSize: dword): BOOLEAN; external 'CreatePipe@kernel32.dll stdcall'; function WaitForSingleObject(hHandle: THandle; dwMilliseconds: DWORD): DWORD; external 'WaitForSingleObject@kernel32.dll stdcall'; function ReadFile(hFile: THandle; lpBuffer: Longint; nNumberOfBytesToRead: DWORD; var lpNumberOfBytesRead: DWORD; lpOverlapped: Longint): BOOL; external 'ReadFile@kernel32.dll stdcall'; function GetProcessHeap: THandle; external 'GetProcessHeap@kernel32.dll stdcall'; function HeapAlloc(hHeap: THandle; dwFlags, dwBytes: DWORD): Longint; external 'HeapAlloc@kernel32.dll stdcall'; function HeapSize(hHeap: THandle; dwFlags: DWORD; lpMem: Longint): DWORD; external 'HeapSize@kernel32.dll stdcall'; function HeapFree(hHeap: THandle; dwFlags: DWORD; lpMem: Longint): BOOL; external 'HeapFree@kernel32.dll stdcall'; Function OemToChar(lpszSrc, lpszDst: AnsiString): longint; external 'OemToCharA@user32.dll stdcall'; procedure AppProcessMessage; var Msg: TMyMsg; begin while PeekMessage(Msg, 0, 0, 0, 1) do begin TranslateMessage(Msg); DispatchMessage(Msg); end; end; function OemToAnsiStr(strSource: AnsiString): AnsiString; var nRet: longint; begin SetLength(Result, Length(strSource)); nRet:= OemToChar(strSource, Result); end; procedure InitializeWizard; var MyMemo: TMemo; Security: TSecurityAttributes; ReadPipe, WritePipe: THandle; Start: TStartUpInfo; ProcessInfo: TProcessInformation; Buffer: PAnsiChar; BytesRead: DWord; Apprunning: DWord; appName, commandLine,workingDirectory: string; hFile, hHeap: THandle; lpBuffer: Longint; dwBufferSize, dwRead: DWORD; begin WizardForm.InnerNoteBook.Hide; WizardForm.OuterNotebook.Hide; MyMemo:=TMemo.Create(WizardForm); MyMemo.SetBounds(30, 30, 440, 260); MyMemo.Parent:=WizardForm; MyMemo.Text:='Hello!'; { with Security do begin nlength := SizeOf(Security); binherithandle := true; lpsecuritydescriptor := 0; end; } Security.nlength := SizeOf( Security ); Security.binherithandle := true; Security.lpSecurityDescriptor := 0; if Createpipe( ReadPipe, WritePipe, Security, 0 ) then begin hHeap := GetProcessHeap; lpBuffer := HeapAlloc(hHeap, HEAP_ZERO_MEMORY, ReadBuffer); dwBufferSize := HeapSize(hHeap, 0, lpBuffer); //Buffer := AllocMem( ReadBuffer+1 ); //FillChar( Start, Sizeof( Start ), #0 ); Start.cb := SizeOf( Start ); Start.hStdOutput := WritePipe; Start.hStdInput := ReadPipe; Start.dwFlags := STARTF_USESTDHANDLES + STARTF_USESHOWWINDOW; Start.wShowWindow := SW_HIDE; if CreateProcess('c:\windows\System32\PING.EXE', ' ' + 'ya.ru', Security, Security, True, NORMAL_PRIORITY_CLASS, 0, 'c:\windows\System32', Start, ProcessInfo) then begin repeat Apprunning := WaitForSingleObject( ProcessInfo.hProcess, 100 ); ReadFile(ReadPipe, lpBuffer, dwBufferSize, dwRead, 0); //ReadFile( ReadPipe, lpBuffer[0], ReadBuffer, BytesRead, nil ); //lpBuffer[BytesRead] := #0; MyMemo.Text := MyMemo.text + OemToAnsiStr(lpBuffer); AppProcessMessage; until ( Apprunning <> WAIT_TIMEOUT ); // until ( BytesRead < ReadBuffer ); end; HeapFree(hHeap, 0, lpBuffer); CloseHandle( ProcessInfo.hProcess ); CloseHandle( ProcessInfo.hThread ); CloseHandle( ReadPipe ); CloseHandle( WritePipe ); end; end; |
Последний раз редактировалось usermode, 15-08-2017 в 14:29. Отправлено: 14:23, 15-08-2017 | #2024 |
Пользователь Сообщения: 50
|
Профиль | Отправить PM | Цитировать |
Последний раз редактировалось TheLeon, 17-08-2017 в 20:04. Отправлено: 15:14, 16-08-2017 | #2025 |
Ветеран Сообщения: 1264
|
Профиль | Отправить PM | Цитировать Цитата usermode:
Скрытый текст
[Setup] AppName=test AppVerName=test CreateAppDir=false DefaultDirName={tmp} Uninstallable=false DisableWelcomePage=no [Languages] Name: ru; MessagesFile: compiler:Languages\russian.isl [Code] #define A = (Defined UNICODE) ? "W" : "A" const WM_QUIT = $0012; PM_REMOVE = $1; MSGF_SLEEPMSG = $5300; STARTF_USESTDHANDLES = $0100; STARTF_USESHOWWINDOW = $0001; QS_ALLINPUT = $04FF; WAIT_TIMEOUT = $00000102; EM_LINESCROLL = $B6; type #ifndef IS_ENHANCED TMsg = record hwnd: HWND; message: LongWord; wParam: Longint; lParam: Longint; time: LongWord; pt: TPoint; end; #endif TSecurityAttributes = record nLength: DWORD; lpSecurityDescriptor: Longint; bInheritHandle: BOOL; end; TStartupInfo = record cb: DWORD; lpReserved: Longint; lpDesktop: Longint; lpTitle: Longint; dwX: DWORD; dwY: DWORD; dwXSize: DWORD; dwYSize: DWORD; dwXCountChars: DWORD; dwYCountChars: DWORD; dwFillAttribute: DWORD; dwFlags: DWORD; wShowWindow: Word; cbReserved2: Word; lpReserved2: Longint; hStdInput: THandle; hStdOutput: THandle; hStdError: THandle; end; TProcessInformation = record hProcess: THandle; hThread: THandle; dwProcessId: DWORD; dwThreadId: DWORD; end; // Message Functions function PeekMessage(var lpMsg: TMsg; hWnd: HWND; wMsgFilterMin, wMsgFilterMax, wRemoveMsg: UINT): BOOL; external 'PeekMessage{#A}@user32.dll stdcall'; function TranslateMessage(const lpMsg: TMsg): BOOL; external 'TranslateMessage@user32.dll stdcall'; function DispatchMessage(const lpmsg: TMsg): Longint; external 'DispatchMessage{#A}@user32.dll stdcall'; procedure PostQuitMessage(nExitCode: Integer); external 'PostQuitMessage@user32.dll stdcall'; // Hook Functions function CallMsgFilter(lpMsg: TMsg; nCode: Integer): BOOL; external 'CallMsgFilter{#A}@user32.dll stdcall'; // Synchronization Functions function WaitForSingleObject(hHandle: THandle; dwMilliseconds: DWORD): DWORD; external 'WaitForSingleObject@kernel32.dll stdcall'; // Handle and Object Functions function CloseHandle(hObject: THandle): BOOL; external 'CloseHandle@kernel32.dll stdcall'; // Process and Thread Functions function CreateProcess(lpApplicationName, lpCommandLine: string; lpProcessAttributes, lpThreadAttributes: TSecurityAttributes; bInheritHandles: BOOL; dwCreationFlags: DWORD; lpEnvironment: Longint; lpCurrentDirectory: string; lpStartupInfo: TStartupInfo; out lpProcessInformation: TProcessInformation): BOOL; external 'CreateProcess{#A}@kernel32.dll stdcall'; // Pipe Functions function CreatePipe(out hReadPipe, hWritePipe: THandle; lpPipeAttributes: TSecurityAttributes; nSize: DWORD): BOOL; external 'CreatePipe@kernel32.dll stdcall'; function PeekNamedPipe(hNamedPipe: THandle; lpBuffer: AnsiString; nBufferSize: DWORD; out lpBytesRead: DWORD; lpTotalBytesAvail, lpBytesLeftThisMessage: DWORD): BOOL; external 'PeekNamedPipe@kernel32.dll stdcall'; // File Management Functions function ReadFile(hFile: THandle; lpBuffer: AnsiString; nNumberOfBytesToRead: DWORD; var lpNumberOfBytesRead: DWORD; lpOverlapped: Longint): BOOL; external 'ReadFile@kernel32.dll stdcall'; var OutputMemo: TMemo; RunButton: TButton; ////////////////////////////////// function ProcessMessages: Boolean; var Msg: TMsg; begin Result := True; while PeekMessage(Msg, 0, 0, 0, PM_REMOVE) do begin if (Msg.Message = WM_QUIT) then begin PostQuitMessage(Msg.wParam); Result := False; Exit; end; if not CallMsgFilter(Msg, MSGF_SLEEPMSG) then begin TranslateMessage(Msg); DispatchMessage(Msg); end; end; end; /////////////////////////////// /////////////////////////////////// procedure CaptureConsoleOutput(const ACommand, AParameters: string; const AOEMConvert: Boolean; AMemo: TMemo); var SecurityAttributes: TSecurityAttributes; StartupInfo: TStartupInfo; ProcessInformation: TProcessInformation; ReadHandle, WriteHandle: THandle; BufSize, ResultCode, BytesRead: DWORD; Buffer: AnsiString; begin SecurityAttributes.nLength := SizeOf(SecurityAttributes); SecurityAttributes.bInheritHandle := True; if CreatePipe(ReadHandle, WriteHandle, SecurityAttributes, 0) then try StartupInfo.cb := SizeOf(StartupInfo); StartupInfo.hStdInput := ReadHandle; StartupInfo.hStdOutput := WriteHandle; StartupInfo.hStdError := WriteHandle; StartupInfo.dwFlags := STARTF_USESTDHANDLES or STARTF_USESHOWWINDOW; StartupInfo.wShowWindow := SW_HIDE; if CreateProcess('', Format('%s %s', [ACommand, AParameters]), SecurityAttributes, SecurityAttributes, True, 0, 0, '', StartupInfo, ProcessInformation) then try CloseHandle(WriteHandle); BufSize := 1024; // 1KB Buffer := StringOfChar(#0, BufSize); repeat ResultCode := WaitForSingleObject(ProcessInformation.hProcess, 0); PeekNamedPipe(ReadHandle, Buffer, BufSize, BytesRead, 0, 0); while ProcessMessages and (BytesRead > 0) do begin #ifdef IS_ENHANCED AMemo.Lines.BeginUpdate; #endif ReadFile(ReadHandle, Buffer, BytesRead, BytesRead, 0); if AOEMConvert then OemToCharBuff(Buffer); AMemo.Text := AMemo.Text + Copy(Buffer, 1, BytesRead); SendMessage(AMemo.Handle, EM_LINESCROLL, 0, AMemo.Lines.Count); #ifdef IS_ENHANCED AMemo.Lines.EndUpdate; #endif end; until not ProcessMessages or (ResultCode <> WAIT_TIMEOUT); finally CloseHandle(ProcessInformation.hProcess); CloseHandle(ProcessInformation.hThread); end; finally CloseHandle(ReadHandle); end; end; //////////////////////////////////////////// procedure RunButtonOnClick(Sender: TObject); begin CaptureConsoleOutput('cmd.exe', '/c ping ya.ru', True, OutputMemo); end; /////////////////////////// procedure InitializeWizard; begin WizardForm.OuterNotebook.Hide; OutputMemo := TMemo.Create(WizardForm); with OutputMemo do begin Parent := WizardForm; SetBounds(WizardForm.OuterNotebook.Left, WizardForm.OuterNotebook.Top, WizardForm.OuterNotebook.Width, WizardForm.OuterNotebook.Height); ScrollBars := ssVertical; ReadOnly := True; #ifdef IS_ENHANCED DoubleBuffered := True; #endif end; RunButton := TButton.Create(WizardForm); with RunButton do begin Parent := WizardForm; SetBounds(WizardForm.OuterNotebook.Left, WizardForm.NextButton.Top, WizardForm.NextButton.Width, WizardForm.NextButton.Height); Caption := 'Run'; OnClick := @RunButtonOnClick; end; end; ////////////////////////////////////////////////////// function NextButtonClick(CurPageID: Integer): Boolean; begin Result := False; end; |
|
Последний раз редактировалось El Sanchez, 16-08-2017 в 21:39. Причина: legacy code Отправлено: 15:23, 16-08-2017 | #2026 |
Новый участник Сообщения: 28
|
Профиль | Отправить PM | Цитировать El Sanchez,
Привык к стандартной официальной версии, буду пробовать адаптировать, за пример огромное спасибо! добавлено подскажите, какой изврат можно использовать в стандартной версии Unicode вместо: Buffer := CastIntegerToString(BufPtr); чтобы перевести содержимое в ANSI. Адаптировал пример под официальную ANSI версию компилятора - все нормально, отображает символы корректно, но UNICODE не содержит CastIntegerToAnsiString. Что нужно учесть, чтобы написать свою функцию CastIntegerToAnsiString, либо как решить задачу другим способом? ====================================================================================== Цитата El Sanchez:
|
|
Последний раз редактировалось usermode, 16-08-2017 в 22:05. Отправлено: 16:21, 16-08-2017 | #2027 |
Старожил Сообщения: 440
|
Профиль | Сайт | Отправить PM | Цитировать El Sanchez, а вывод с консоли заголовка окна возможен? Скажем, проценты выполнения процесса? Было бы здорово.
|
------- Последний раз редактировалось nik1967, 16-08-2017 в 20:48. Отправлено: 16:57, 16-08-2017 | #2028 |
Ветеран Сообщения: 1264
|
Профиль | Отправить PM | Цитировать Цитата usermode:
Цитата nik1967:
|
||
Отправлено: 21:44, 16-08-2017 | #2029 |
Старожил Сообщения: 440
|
Профиль | Сайт | Отправить PM | Цитировать El Sanchez, спасибо за направление, но это не мой уровень, увы.
|
------- Последний раз редактировалось nik1967, 17-08-2017 в 09:11. Отправлено: 22:42, 16-08-2017 | #2030 |
Участник сейчас на форуме | Участник вне форума | Автор темы | Сообщение прикреплено |
| |||||
Название темы | Автор | Информация о форуме | Ответов | Последнее сообщение | |
Скрипты Inno Setup. Помощь и советы [часть 7] | El Sanchez | Автоматическая установка приложений | 2499 | 02-02-2015 08:59 | |
Скрипты Inno Setup. Помощь и советы [часть 6] | El Sanchez | Автоматическая установка приложений | 2494 | 10-03-2014 11:51 | |
Скрипты Inno Setup. Помощь и советы [часть 5] | El Sanchez | Автоматическая установка приложений | 1999 | 28-03-2013 19:09 | |
Скрипты Inno Setup. Помощь и советы [часть 4] | El Sanchez | Автоматическая установка приложений | 2099 | 22-05-2012 23:16 | |
Скрипты Inno Setup. Помощь и советы [часть 3] | Serega | Автоматическая установка приложений | 3755 | 26-10-2011 17:58 |
|