{Options dialog} procedure SetButtonIcons(Dialog:HWND); var ti:TTOOLINFOW; hwndTooltip:HWND; begin hwndTooltip:=CreateWindowW(TOOLTIPS_CLASS,nil,TTS_ALWAYSTIP, integer(CW_USEDEFAULT),integer(CW_USEDEFAULT), integer(CW_USEDEFAULT),integer(CW_USEDEFAULT), Dialog,0,hInstance,nil); FillChar(ti,SizeOf(ti),0); ti.cbSize :=sizeof(TOOLINFO); ti.uFlags :=TTF_IDISHWND or TTF_SUBCLASS; ti.hwnd :=Dialog; ti.hinst :=hInstance; ti.uId :=GetDlgItem(Dialog,IDC_EQ_ADD); ti.lpszText:=TranslateW('Add'); SetButtonIcon(ti.uId,IcoBtnAdd); SendMessageW(hwndTooltip,TTM_ADDTOOLW,0,lparam(@ti)); ti.uId :=GetDlgItem(Dialog,IDC_EQ_DEL); ti.lpszText:=TranslateW('Delete'); SetButtonIcon(ti.uId,IcoBtnDel); SendMessageW(hwndTooltip,TTM_ADDTOOLW,0,lparam(@ti)); end; function DlgProcOpt(Dialog:HWND;hMessage:uint;wParam:WPARAM;lParam:LPARAM):LRESULT; stdcall; const DlgInit:integer=1; var buf:array [0..MAX_PATH-1] of WideChar; psr:TPROTOSEARCHRESULT; dst:pWideChar; i:dword; vhi:TVARHELPINFO; wnd:HWND; p:pWideChar; begin result:=0; case hMessage of WM_INITDIALOG: begin DlgInit:=1; TranslateDialogDefault(Dialog); wnd:=GetDlgItem(Dialog,IDC_HLP_VARS); if isVarsInstalled then begin SendMessage(wnd,BM_SETIMAGE,IMAGE_ICON, CallService(MS_VARS_GETSKINITEM,0,VSI_HELPICON)); end else ShowWindow(wnd,SW_HIDE); if recpath<>nil then p:=recpath else begin buf[0]:=#0; p:=@buf; end; SetDlgItemTextW(Dialog,IDC_ED_RECPATH,p); CheckDlgButton(Dialog,IDC_LOOP ,doLoop); CheckDlgButton(Dialog,IDC_SHUFFLE ,doShuffle); CheckDlgButton(Dialog,IDC_CONTREC ,doContRec); CheckDlgButton(Dialog,IDC_PLAYFIRST,PlayFirst); CheckDlgButton(Dialog,IDC_CONNECT ,AuConnect); CheckDlgButton(Dialog,IDC_AUTOMUTE ,AuMute); CheckDlgButton(Dialog,IDC_OFFLINE ,AsOffline); SetDlgItemTextW(Dialog,IDC_STATUS,StatusTmpl); DlgInit:=0; end; WM_COMMAND: begin case wParam shr 16 of EN_CHANGE: begin if DlgInit=0 then case loword(wParam) of IDC_STATION,IDC_STATIONURL,IDC_GENRE,IDC_BITRATE: ; else SendMessage(GetParent(Dialog),PSM_CHANGED,0,0); end; end; BN_CLICKED: begin case loword(wParam) of IDC_IMPORT: begin ImportAll(0,0); end; IDC_EXPORT: begin ExportAll(0,0); end; IDC_HLP_VARS: begin FillChar(vhi,SizeOf(vhi),0); with vhi do begin cbSize :=SizeOf(vhi); flags :=VHF_FULLDLG or VHF_SETLASTSUBJECT; hwndCtrl :=GetDlgItem(Dialog,IDC_STATUS); szSubjectDesc:='test your variables'; end; CallService(MS_VARS_SHOWHELPEX,Dialog,tlparam(@vhi)); end; IDC_BN_URLPATH: begin dst:=ConstructFilter; if ShowDlgW(@buf,nil,dst) then SetDlgItemTextW(Dialog,IDC_STATIONURL,@buf); mFreeMem(dst); end; IDC_BN_RECPATH: begin dst:=nil; if SelectDirectory(pWideChar(nil),dst,Dialog) then begin PathToRelativeW(dst,buf); SetDlgItemTextW(Dialog,IDC_ED_RECPATH,pWideChar(@buf)); mFreeMem(dst); end; end; IDC_LOOP,IDC_SHUFFLE,IDC_CONTREC,IDC_CONNECT,IDC_OFFLINE,IDC_AUTOMUTE: SendMessage(GetParent(Dialog),PSM_CHANGED,0,0); IDC_ADD_LIST,IDC_ADD_INI: begin if GetWindowTextLength(GetDlgItem(Dialog,IDC_STATIONURL))>0 then begin FillChar(psr,SizeOf(psr),0); with psr do begin if loword(wParam)=IDC_ADD_LIST then begin GetDlgItemTextW(Dialog,IDC_STATIONURL,@buf,MAX_PATH); StrDupW(firstname.w,@buf); buf[0]:=#0; GetDlgItemTextW(Dialog,IDC_STATION,@buf,MAX_PATH); if buf[0]<>#0 then StrDupW(nick.w,@buf) else StrDupW(nick.w,firstname.w); buf[0]:=#0; GetDlgItemTextW(Dialog,IDC_GENRE,@buf,MAX_PATH); StrDupW(lastname.w,@buf); buf[0]:=#0; GetDlgItemTextW(Dialog,IDC_BITRATE,@buf,MAX_PATH); StrDupW(email.w,@buf); i:=Service_AddToList(0,tlparam(@psr)); { GetDlgItemTextW(Dialog,IDC_STATION,@buf,SizeOf(buf)); DBWriteUnicode(i,strCList,optMyHandle,@buf); GetDlgItemTextW(Dialog,IDC_STATIONURL,@buf,SizeOf(buf)); DBWriteUnicode(i,PluginName,optStationURL,@buf); } // "changing" station group dst:=GetNewGroupName(Dialog); if dst<>nil then DBWriteUnicode(i,strCList,optGroup,dst) else DBDeleteSetting(i,strCList,optGroup); end else if loword(wParam)=IDC_ADD_INI then begin GetDlgItemTextA(Dialog,IDC_STATIONURL,PAnsiChar(@buf),SizeOf(buf)); StrDup(firstname.a,PAnsiChar(@buf)); PAnsiChar(@buf)^:=#0; GetDlgItemTextA(Dialog,IDC_STATION,PAnsiChar(@buf),SizeOf(buf)); if PAnsiChar(@buf)^<>#0 then StrDup(nick.a,@buf) else StrDup(nick.a,firstname.a); PAnsiChar(@buf)^:=#0; GetDlgItemTextA(Dialog,IDC_GENRE,PAnsiChar(@buf),SizeOf(buf)); StrDup(lastname.a,@buf); PAnsiChar(@buf)^:=#0; GetDlgItemTextA(Dialog,IDC_BITRATE,PAnsiChar(@buf),SizeOf(buf)); StrDup(email.a,@buf); if WritePrivateProfileStringA(firstname.a,'URL',firstname.a,storage) then begin WritePrivateProfileStringA(firstname.a,'Name' ,nick.a ,storage); WritePrivateProfileStringA(firstname.a,optGenre ,lastname.a ,storage); WritePrivateProfileStringA(firstname.a,optBitrate,email.a ,storage); end else begin WritePrivateProfileStringA(firstname.a,'URL' ,firstname.a,storagep); WritePrivateProfileStringA(firstname.a,'Name' ,nick.a ,storagep); WritePrivateProfileStringA(firstname.a,optGenre ,lastname.a ,storagep); WritePrivateProfileStringA(firstname.a,optBitrate,email.a ,storagep); end; end; mFreeMem(nick); mFreeMem(firstname); mFreeMem(lastname); mFreeMem(email); end; end; end; end; end; end; end; WM_NOTIFY: begin if integer(PNMHdr(lParam)^.code)=PSN_APPLY then begin doShuffle:=IsDlgButtonChecked(Dialog,IDC_SHUFFLE); doContRec:=IsDlgButtonChecked(Dialog,IDC_CONTREC); PlayFirst:=IsDlgButtonChecked(Dialog,IDC_PLAYFIRST); AuConnect:=IsDlgButtonChecked(Dialog,IDC_CONNECT); AuMute :=IsDlgButtonChecked(Dialog,IDC_AUTOMUTE); AsOffline:=IsDlgButtonChecked(Dialog,IDC_OFFLINE); mFreeMem(StatusTmpl); StatusTmpl:=GetDlgText(Dialog,IDC_STATUS); doLoop:=IsDlgButtonChecked(Dialog,IDC_LOOP); if chan<>0 then begin BASS_ChannelFlags(chan,ord(doLoop<>BST_UNCHECKED),BASS_SAMPLE_LOOP); end; mFreeMem(recpath); buf[0]:=#0; GetDlgItemTextW(Dialog,IDC_ED_RECPATH,@buf,SizeOf(buf) div SizeOf(WideChar)); if buf[0]<>#0 then begin mGetMem(recpath,MAX_PATH*SizeOf(WideChar)); recpath^:=#0; PathToRelativeW(buf,recpath); end else recpath:=GetDefaultRecPath; SaveCommonSettings; end; end; // else // result:=DefWindowProc(Dialog,hMessage,wParam,lParam); end; end; //----- Tech tab ----- procedure FillDeviceCombo(wnd:HWND;choose:pAnsiChar); var i,select,def:integer; info:BASS_DEVICEINFO; buf: array [0..255] of AnsiChar; begin def:=0; SendMessage(wnd,CB_RESETCONTENT,0,0); if BassStatus<>rbs_null then begin i:=0; select:=-1; repeat if not BASS_GetDeviceInfo(i+1,info) then break; if (info.flags and BASS_DEVICE_ENABLED)<>0 then begin if (info.flags and BASS_DEVICE_INIT)<>0 then begin select:=i; buf[0]:='>'; end else if (info.flags and BASS_DEVICE_DEFAULT)<>0 then begin def:=i; buf[0]:='*'; end else buf[0]:=' '; if select<0 then begin if StrCmp(info.name,choose)=0 then select:=i; end; StrCopy(@buf[1],info.name); SendMessageA(wnd,CB_ADDSTRING,0,lparam(@buf)); end; inc(i); until false; if select>=0 then def:=select; end; SendMessage(wnd,CB_SETCURSEL,def,0); end; function DlgProcOptTech(Dialog:HWND;hMessage:uint;wParam:WPARAM;lParam:LPARAM):LRESULT; stdcall; const DlgInit:integer=1; var hEAXCombo:THANDLE; ltmp:longbool; wnd:HWND; buf:array [0..MAX_PATH-1] of WideChar; dst,old:pWideChar; device:pAnsiChar; i,level:integer; begin result:=0; case hMessage of WM_DESTROY: begin hVolCtrl:=0; for i:=0 to 9 do begin eq[i].wnd:=0; end; end; WM_INITDIALOG: begin DlgInit:=1; TranslateDialogDefault(Dialog); SetButtonIcons(Dialog); hVolCtrl:=GetDlgItem(Dialog,IDC_VOLUME); SendMessage(hVolCtrl,TBM_SETRANGE,0,(100 shl 16)+0); SendMessage(hVolCtrl,TBM_SETPOS,1,ABS(gVolume)); SetDlgItemInt(Dialog,IDC_BUFFER ,sBuffer ,false); SetDlgItemInt(Dialog,IDC_PREBUF ,sPreBuf ,false); SetDlgItemInt(Dialog,IDC_TIMEOUT,sTimeout,false); SetDlgItemInt(Dialog,IDC_TRIES ,NumTries,false); CheckDlgButton(Dialog,IDC_MONO,ForcedMono); // Fill EAX combo hEAXCombo:=GetDlgItem(Dialog,IDC_EAXTYPE); for i:=0 to EAX_ENVIRONMENT_COUNT do SendMessageW(hEAXCombo,CB_ADDSTRING,0,tlparam(TranslateW(EAXItems[i].name))); SendMessage(hEAXCombo,CB_SETCURSEL,DBReadByte(0,PluginName,optEAXType,0),0); if BassStatus=rbs_null then MyLoadBass; // Fill combo with devices FillDeviceCombo(GetDlgItem(Dialog,IDC_DEVICE),usedevice); // Add preset to combo wnd:=GetDlgItem(Dialog,IDC_PRESET); for i:=0 to HIGH(Presets) do SendMessageW(wnd,CB_ADDSTRING,0,tlparam(Presets[i].name)); SendMessage(wnd,CB_SETCURSEL,OldEQPreset,0); // Equalizer for i:=0 to 9 do begin eq[i].wnd:=GetDlgItem(Dialog,IDC_EQ00+i); SendMessage(eq[i].wnd,TBM_SETRANGE,1,(16 shl 16)-15); SendMessage(eq[i].wnd,TBM_SETTIC,0,0); SendMessage(eq[i].wnd,TBM_SETPOS,1,-trunc(eq[i].param.fGain)); SendDlgItemMessageA(Dialog,IDC_0+i,WM_SETTEXT,0,tlparam(eq[i].text)); EnableWindow(eq[i].wnd,isEQ_OFF=BST_UNCHECKED); end; CheckDlgButton(Dialog,IDC_EQOFF,isEQ_OFF); dst:=DBReadUnicode(0,PluginName,optBASSPath,nil); SetDlgItemTextW(Dialog,IDC_BASSPATH,dst); mFreeMem(dst); DlgInit:=0; end; WM_COMMAND: begin case wParam shr 16 of EN_CHANGE: begin if DlgInit=0 then SendMessage(GetParent(Dialog),PSM_CHANGED,0,0); end; BN_CLICKED: begin case loword(wParam) of IDC_EQOFF, IDC_ZERO: SendMessage(GetParent(Dialog),PSM_CHANGED,0,0); end; case loword(wParam) of IDC_BASSPTHBTN: begin dst:=nil; if SelectDirectory(pWideChar(nil),dst,Dialog) then begin PathToRelativeW(dst,buf); SetDlgItemTextW(Dialog,IDC_BASSPATH,pWideChar(@buf)); mFreeMem(dst); end; end; IDC_EQOFF: begin isEQ_OFF:=IsDlgButtonChecked(Dialog,IDC_EQOFF); if isEQ_OFF=BST_UNCHECKED then EQ_ON else EQ_OFF; for i:=0 to 9 do EnableWindow(eq[i].wnd,isEQ_OFF=BST_UNCHECKED); end; IDC_ZERO: begin OldEQPreset:=-1; for i:=0 to 9 do begin eq[i].param.fGain:=0; SendMessage(eq[i].wnd,TBM_SETPOS,1,0); if (chan<>0) and (isEQ_OFF=BST_UNCHECKED) then BASS_FXSetParameters(eq[i].fx,@eq[i].param); end; end; IDC_EQ_ADD: begin SetLength(Presets,Length(Presets)+1); for i:=0 to 9 do Presets[HIGH(Presets)].preset[i]:=-SendMessage(eq[i].wnd,TBM_GETPOS,0,0); wnd:=GetDlgItem(Dialog,IDC_PRESET); Presets[HIGH(Presets)].name:=GetDlgText(wnd,false); if Presets[HIGH(Presets)].name=nil then StrDupW(Presets[HIGH(Presets)].name,'New'); OldEQPreset:=SendMessage(wnd,CB_SETCURSEL, SendMessageW(wnd,CB_ADDSTRING,0,tlparam(Presets[HIGH(Presets)].name)),0); end; IDC_EQ_DEL: begin wnd:=GetDlgItem(Dialog,IDC_PRESET); i:=SendMessage(wnd,CB_GETCURSEL,0,0); if (i>=0) and (i<=HIGH(Presets)) then begin SendMessage(wnd,CB_DELETESTRING,i,0); mFreeMem(Presets[i].name); move(Presets[i+1],Presets[i],(HIGH(Presets)-i)*SizeOf(tPreset)); SetLength(Presets,Length(Presets)-1); OldEQPreset:=-1; SendMessage(wnd,CB_SETCURSEL,-1,0); end; end; end; end; CBN_SELCHANGE: begin SendMessage(GetParent(Dialog),PSM_CHANGED,0,0); case loword(wParam) of IDC_PRESET: begin OldEQPreset:=SendDlgItemMessage(Dialog,IDC_PRESET,CB_GETCURSEL,0,0); for i:=0 to 9 do begin SendMessage(eq[i].wnd,TBM_SETPOS,1,-Presets[OldEQPreset].preset[i]); eq[i].param.fGain:=Presets[OldEQPreset].preset[i]; if (chan<>0) and (isEQ_OFF=BST_UNCHECKED) then BASS_FXSetParameters(eq[i].fx,@eq[i].param); end; end; IDC_EAXTYPE: begin { i:=SendDlgItemMessage(Dialog,IDC_EAXTYPE,CB_GETCURSEL,0,0); DBWriteByte(0,PluginName,optEAXType,i); if i=0 then BASS_SetEAXParameters(-1,0,-1,-1) else BASS_SetEAXPreset(EAXItems[i].code); } end; end; end; end; end; WM_VSCROLL: begin for i:=0 to 9 do begin if HWND(lParam)=eq[i].wnd then begin eq[i].param.fGain:=-SendMessage(lParam,TBM_GETPOS,0,0); if (chan<>0) and (isEQ_OFF=BST_UNCHECKED) then BASS_FXSetParameters(eq[i].fx,@eq[i].param); OldEQPreset:=-1; break; end; end; SendMessage(GetParent(Dialog),PSM_CHANGED,0,0); end; WM_HSCROLL: begin Service_RadioSetVolume(SendMessage(lParam,TBM_GETPOS,0,0),1) end; WM_NOTIFY: begin if integer(PNMHdr(lParam)^.code)=PSN_APPLY then begin SavePresets; level:=0; device:=GetDlgText(Dialog,IDC_DEVICE,true); StrCopy(device,device+1); if StrCmp(usedevice,device)<>0 then begin level:=1; mFreeMem(usedevice); usedevice:=device; end else mFreeMem(device); //!! bass path saving here old:=DBReadUnicode(0,PluginName,optBASSPath,nil); dst:=GetDlgText(Dialog,IDC_BASSPATH); if lstrcmpiw(dst,old)<>0 then begin level:=2; DBWriteUnicode(0,PluginName,optBASSPath,dst); end; mFreeMem(dst); mFreeMem(old); i:=SendDlgItemMessage(Dialog,IDC_EAXTYPE,CB_GETCURSEL,0,0); DBWriteByte(0,PluginName,optEAXType,i); { level>0 - need to change ActiveContact<>0 - need to restart BassStatus<>rbs_null - need to stop (free, unload) really, if ActiveContact<>0 then BassStatus<>rbs_null } //!!really, need to do it if only active atm // need to reload dll or change outpout device // don't change proxy if level>0 then begin ltmp:=ActiveContact<>0; if ltmp then CallService(MS_RADIO_COMMAND,MRC_STOP,1); // save current, stop, bass free MyFreeBass; if level=2 then begin MyUnloadBass; // load dll if ltmp then MyLoadBass; end; // init device, restore current if ltmp and (BassStatus=rbs_load) then begin MyInitBass; end; if ltmp and (BassStatus=rbs_init) then begin CallService(MS_RADIO_COMMAND,MRC_PAUSE,0); end; end // if device re-init, EAX settings applied there else if BassStatus=rbs_init then begin if i=0 then BASS_SetEAXParameters(-1,0,-1,-1) else BASS_SetEAXPreset(EAXItems[i].code); end; ForcedMono:=IsDlgButtonChecked(Dialog,IDC_MONO); NumTries:=GetDlgItemInt(Dialog,IDC_TRIES,ltmp,false); if NumTries<1 then NumTries:=1; // Bass config settings sPreBuf:=GetDlgItemInt(Dialog,IDC_PREBUF,ltmp,false); if sPreBuf>100 then sPreBuf:=100; sBuffer:=GetDlgItemInt(Dialog,IDC_BUFFER,ltmp,false); if sBuffer>20000 then sBuffer:=20000; sTimeout:=GetDlgItemInt(Dialog,IDC_TIMEOUT,ltmp,false); if sTimeout>30000 then sTimeout:=30000; SetBassConfig; SaveTechSettings; end; end; // else // result:=DefWindowProc(Dialog,hMessage,wParam,lParam); end; end; function OnOptInitialise(wParam:WPARAM;lParam:LPARAM):int;cdecl; var odp:TOPTIONSDIALOGPAGE; begin FillChar(odp,SizeOf(odp),0); odp.flags :=ODPF_BOLDGROUPS; odp.Position :=900003000; odp.hInstance :=hInstance; odp.szGroup.a :='Network'; odp.szTitle.a :=PluginName; odp.pszTemplate:=MAKEINTRESOURCEA(IDD_SETTING); odp.pfnDlgProc :=@DlgProcOpt; odp.szTab.a :='Common'; CallService(MS_OPT_ADDPAGE,wParam,tlparam(@odp)); odp.pszTemplate:=MAKEINTRESOURCEA(IDD_SETTING_TECH); odp.pfnDlgProc :=@DlgProcOptTech;//!! odp.szTab.a :=Translate('Advanced'); CallService(MS_OPT_ADDPAGE,wParam,tlparam(@odp)); result:=0; end; // checking proto in several places for speed, not size economy function OnSettingsChanged(wParam:WPARAM;lParam:LPARAM):int;cdecl; var buf:array [0..MAX_PATH-1] of AnsiChar; i:integer; pc:PAnsiChar; begin result:=0; with PDBCONTACTWRITESETTING(lParam)^ do begin if AuMute<>BST_UNCHECKED then begin if StrCmp(szModule,'Skin')=0 then begin if StrCmp(szSetting,'UseSound')=0 then begin // Mute if value.bVal=0 then begin if gVolume>=0 then Service_RadioMute(0,0); end // Unmute else begin if gVolume<0 then Service_RadioMute(0,0); end; end; exit; end end; // works only if called AFTER changes if StrCmp(szModule,strCList)=0 then begin if StrCmp(szSetting,optMyHandle)=0 then begin if value._type=DBVT_DELETED then begin if StrCmp(Proto_GetProtoName(wParam),PluginName)<>0 then exit; pc:=DBReadString(wParam,PluginName,optNick); DBWriteString(wParam,strCList,optMyHandle,pc); mFreeMem(pc); end; end; exit; end; if StrCmp(szModule,'UserInfo')<>0 then exit; if StrCmp(szSetting,optAge)=0 then begin if StrCmp(Proto_GetProtoName(wParam),PluginName)<>0 then exit; if value._type=DBVT_DELETED then i:=DBReadWord(wParam,PluginName,optAge) else i:=value.wVal; DBWriteString(wParam,PluginName,optBitrate,IntToStr(buf,i)); exit; end; case value._type of DBVT_DELETED, DBVT_ASCIIZ , DBVT_WCHAR , DBVT_UTF8 : if StrCmp(Proto_GetProtoName(wParam),PluginName)<>0 then exit; else exit; end; case value._type of DBVT_DELETED: pc:=DBReadString(wParam,PluginName,szSetting); DBVT_ASCIIZ : pc:=value.szVal.a; DBVT_WCHAR : WideToAnsi(value.szVal.w,pc,MirandaCP); DBVT_UTF8 : UTF8ToAnsi(value.szVal.a,pc,MirandaCP); end; if StrCmp(szSetting,optFirstName)=0 then DBWriteString(wParam,PluginName,optStationURL,pc) else if StrCmp(szSetting,optNick )=0 then DBWriteString(wParam,strCList,optMyHandle,pc) else if StrCmp(szSetting,optLastName )=0 then DBWriteString(wParam,PluginName,optGenre,pc); if value._type<>DBVT_ASCIIZ then mFreeMem(pc); end; end; function OnContactDeleted(wParam:WPARAM;lParam:LPARAM):int;cdecl; begin result:=0; if ActiveContact<>THANDLE(wParam) then exit; ControlCenter(MRC_STOP,wParam); end;