Play a sound only in a specific page in Inno Setup

人走茶凉 提交于 2021-01-21 05:34:06

问题


I'm creating a installer for my application with Inno Setup. I use BASS audio library to play music in background of the installer.

Here is my code for playing the sound.

[Code]
const
  DI_NORMAL = 3;
  FR_PRIVATE = $10;  {added to compact Mode}
  BASS_SAMPLE_LOOP = 4;
  BASS_ACTIVE_STOPPED = 0;
  BASS_ACTIVE_PLAYING = 1;
  BASS_ACTIVE_STALLED = 2;
  BASS_ACTIVE_PAUSED  = 3;
  BASS_UNICODE = $80000000;
  BASS_CONFIG_GVOL_STREAM = {#MusicVolume};
  EncodingFlag = BASS_UNICODE;
  #if CheckCRC == "1"
  PM_REMOVE = 1;
  WM_QUIT   = 18;
  #endif

function BASS_Init(device: LongInt; freq, flags: DWORD; win: HWND; clsid: Cardinal): BOOL;
  external 'BASS_Init@files:bass.dll stdcall';
function BASS_StreamCreateFile(mem: BOOL; f: string; offset1: DWORD; offset2: DWORD; length1: DWORD; length2: DWORD; flags: DWORD): HSTREAM;
  external 'BASS_StreamCreateFile@files:bass.dll stdcall';
function BASS_Start: BOOL;
  external 'BASS_Start@files:bass.dll stdcall';
function BASS_Pause: BOOL;
  external 'BASS_Pause@files:bass.dll stdcall';
function BASS_ChannelPlay(handle: DWORD; restart: BOOL): BOOL;
  external 'BASS_ChannelPlay@files:bass.dll stdcall';
function BASS_SetConfig(option: DWORD; value: DWORD ): BOOL;
  external 'BASS_SetConfig@files:bass.dll stdcall';
function BASS_ChannelIsActive(handle: DWORD): DWORD;
  external 'BASS_ChannelIsActive@files:bass.dll stdcall';
function BASS_Free: BOOL;

procedure MusicButtonClick(Sender: TObject);
begin
  case BASS_ChannelIsActive(SoundStream) of
    BASS_ACTIVE_PLAYING:
    begin
      if BASS_Pause then
        MusicButton.Caption := ExpandConstant('{cm:MusicButtonCaptionSoundOn}');
    end;
    BASS_ACTIVE_PAUSED:
    begin
      if BASS_Start then
        MusicButton.Caption := ExpandConstant('{cm:MusicButtonCaptionSoundOff}');
    end;
  end;
end;

ExtractTemporaryFile('{#MusicFile}');
if BASS_Init(-1, 44100, 0, 0, 0) then
begin
  SoundStream := BASS_StreamCreateFile(False,
  ExpandConstant('{tmp}\{#MusicFile}'), 0, 0, 0, 0,
  EncodingFlag or BASS_SAMPLE_LOOP);
  BASS_SetConfig(BASS_CONFIG_GVOL_STREAM, 2500);
  BASS_ChannelPlay(SoundStream, False);
end;

i want to play a sound only in a page of my installer (in this case licence page) i want when the user come in license page, normal music stop and other sound start play,after finish this sound music start play again and also there is anyway to disable next button until sound end?

thanks


With Martin Prikryl's help, I've edited my code a little. My code now like this (again I can't put full code on post because it has many lines)

procedure InitializeWizard();
var
  SoundStream: HSTREAM;
  LicenseSoundStream: HSTREAM;
  //-some other code-//
  IniFile := ExpandConstant('{tmp}\Settings.ini');
  #if Music == "1"
  if BASS_Init(-1, 44100, 0, 0, 0) then
    begin
      BASS_SetConfig(BASS_CONFIG_GVOL_STREAM, 2500);
      ExtractTemporaryFile('{#MusicFile}');
      ExtractTemporaryFile('lic.mp3');
      SoundStream :=
        BASS_StreamCreateFile(
          False, ExpandConstant('{tmp}\{#MusicFile}'), 0, 0, 0, 0,
          BASS_UNICODE or BASS_SAMPLE_LOOP);
      LicenseSoundStream :=
        BASS_StreamCreateFile(
      False, ExpandConstant('{tmp}\lic.mp3'), 0, 0, 0, 0, BASS_UNICODE);
      BASS_ChannelPlay(SoundStream, False);
    end;
  #endif

procedure CurPageChanged(CurPageID: integer);
begin
  //-some other code-//
  #if UseLicense == "1"
  if CurPageID = wpLicense then
  begin
    AboutButton.Hide;
    WizardForm.DirEdit.Hide;
    WizardForm.DirBrowseButton.Hide;
    WizardForm.GroupEdit.Hide;
    WizardForm.GroupBrowseButton.Hide;
    WizardForm.PageNameLabel.Hide;
    WizardForm.PageDescriptionLabel.Hide;
    WizardForm.UserInfoNameLabel.Hide;
    WizardForm.UserInfoNameEdit.Hide;
    if Assigned(LicenseSoundStream) then
    begin
      BASS_ChannelPlay(LicenseSoundStream, True);
      BASS_Start;
    end;
  end
    else
  begin
    { On other pages, restore the standard music }
    if Assigned(SoundStream) then
    begin
      BASS_ChannelPlay(SoundStream, False);
    end;
  end;
  #endif
end;

its now give me compiler error in if Assigned(LicenseSoundStream), error is Line 4416: Column 17: Unknown identifier 'LicenseSoundStream'


-edit 2-

as you know i have 2 sound in installer

  1. is background music (its play in whole installer page except license page)
  2. is license page sound (when user inter license page background sound pause and other sound play, and when exit other sound start play again)

im add button to disable and enable background sound with this codes

procedure MusicButtonClick(Sender: TObject);
begin
  case BASS_ChannelIsActive(SoundStream) of
    BASS_ACTIVE_PLAYING:
    begin
      if BASS_Pause then
        MusicButton.Caption := ExpandConstant('{cm:MusicButtonCaptionSoundOn}');
    end;
    BASS_ACTIVE_PAUSED:
    begin
      if BASS_Start then
        MusicButton.Caption := ExpandConstant('{cm:MusicButtonCaptionSoundOff}');
    end;
  end;
end;

but my problem is if user pause background sound before inter license page, inside license page background sound play again (instead of other sound)


回答1:


Assuming your ExtractTemporaryFile and BASS_Init calls are in InitializeSetup like here: How to make Stop and Pause/Resume/Play music buttons in Inno Setup

Update the code to load both music files:

var
  SoundStream: HSTREAM;
  LicenseSoundStream: HSTREAM;

procedure InitializeWizard;
begin
  if BASS_Init(-1, 44100, 0, 0, 0) then
  begin
    BASS_SetConfig(BASS_CONFIG_GVOL_STREAM, 2500);
    ExtractTemporaryFile('{#MusicFile}');
    ExtractTemporaryFile('{#LicenseMusicFile}');
    SoundStream :=
      BASS_StreamCreateFile(
        False, ExpandConstant('{tmp}\{#MusicFile}'), 0, 0, 0, 0,
        BASS_UNICODE or BASS_SAMPLE_LOOP);
    LicenseSoundStream :=
      BASS_StreamCreateFile(
        False, ExpandConstant('{tmp}\{#LicenseMusicFile}'), 0, 0, 0, 0, BASS_UNICODE);
    BASS_ChannelPlay(SoundStream, False);
  end;
end;

Then in CurPageChanged event function on the license page, start the "license" music:

procedure CurPageChanged(CurPageID: Integer);
begin
  if CurPageID = wpLicense then
  begin
    if LicenseSoundStream <> 0 then
    begin
      BASS_ChannelPause(SoundStream);
      BASS_ChannelPlay(LicenseSoundStream, True);
      BASS_Start;
    end;
  end
    else
  begin
    { On other pages, restore the standard music }
    if SoundStream <> 0 then
    begin
      BASS_ChannelPause(LicenseSoundStream);
      BASS_ChannelPlay(SoundStream, False);
    end;
  end;
end;

Untested – may need few tweaks.



来源:https://stackoverflow.com/questions/63763066/play-a-sound-only-in-a-specific-page-in-inno-setup

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!