unit WidgetMain; (* *) interface uses Windows, Messages, SysUtils, Classes, CommCtrl, ComObj, ActiveX, Widgets, GdipApi, WinInet, InetThrd, GdipObj, Contnrs, WIniFiles, MMSystem, InetUtil, WStrings, ShellApi, ShlObj; const WM_VERSIONDONE = WM_USER + $11; WM_THREADDONE = WM_USER + $12; WM_HIDEFORM = WM_USER + $13; WM_SHOWFORM = WM_USER + $14; WM_ALWAYSTOP = WM_USER + $15; WM_DETAILS = WM_USER + $16; WM_DELETEWIDGET = WM_USER + $18; WM_CHANGELANG = WM_USER + $19; INTERVAL_MIN = 7000; INTERVAL_DISABLE = 0; { IDS_TRAY_TIP0 = 1000; IDS_TRAY_TIP1 = 1001; IDS_TRAY_TIP2 = 1002; } IDS_TEXT_1003 = 1003; IDS_TEXT_1004 = 1004; IDS_TEXT_1005 = 1005; IDS_TEXT_1006 = 1006; IDS_TEXT_1007 = 1007; IDS_TEXT_1008 = 1008; IDS_TEXT_1009 = 1009; IDS_TEXT_1010 = 1010; IDS_TEXT_1011 = 1011; const CBtnChecks: array[Boolean] of Integer = (BST_UNCHECKED, BST_CHECKED); CChecks: array[Boolean] of Integer = (MF_UNCHECKED, MF_CHECKED); CChangeImages: array[-1..+1] of WideString = ('DEC.PNG', 'EQUAL.PNG', 'INC.PNG'); CStateImages: array[Boolean] of WideString = ('IDLE.PNG', 'BUSY.PNG'); type { Forward Declation } TWidgetImageControl = class; TWidgetLabel = class; TWidgetManager = class; { TWidgetMainForm } TWidgetMainForm = class(TWidgetForm) private FThread: TInetThread; FMainMenu: HMENU; FAmungusID, FTitle: WideString; FWidgetURL: WideString; FInterval: Integer; FDragging: Boolean; FPrevious, FTracker: Integer; FSection: WideString; FChangeControl: TWidgetImageControl; FPreviousLabel: TWidgetLabel; FCloseLabel: TWidgetLabel; FAlwaysTop, FEnableTracker: Boolean; FInitDelay: Integer; FBusyControl: TWidgetImageControl; FOpacityMax: Integer; FEffect: Boolean; FShowHide: Boolean; FDialogHandle: HWND; FIgnoreMouse: Boolean; FPreventDragging: Boolean; FBackColor: Cardinal; protected procedure WndProc(var Message: TWidgetMessage); override; procedure WMTimer(var Message: TWidgetMessage); override; procedure WMDestroy(var Message: TWidgetMessage); override; procedure WMClose(var Message: TWidgetMessage); override; procedure WMCommand(var Message: TWidgetMessage); virtual; procedure WMWindowPosChanging(var Message: TWidgetMessage); override; procedure WMThreadDone(var Message: TWidgetMessage); virtual; procedure WMHideForm(var Message: TWidgetMessage); virtual; procedure WMShowForm(var Message: TWidgetMessage); virtual; procedure WMAlwaysTop(var Message: TWidgetMessage); virtual; procedure WMChangeLang(var Message: TWidgetMessage); virtual; public TrackerLabel, TitleLabel: TWidgetLabel; Background, Overlay: TWidgetImageControl; constructor Create(AOwner: TComponent); override; destructor Destroy; override; procedure CreateForm; override; procedure CreateControls; procedure DoMouseDown(Sender: TObject; Keys: Integer; X, Y: Integer); procedure DoCloseButtonClick(Sender: TObject; Keys: Integer; X, Y: Integer); procedure LoaderTimerExecute(Sender: TObject); procedure RefreshTimerExecute(Sender: TObject); procedure RefreshTracker; procedure DialogCloseButtonClick(Sender: TObject; Keys: Integer; X, Y: Integer); procedure RightButtonClick(Sender: TObject); procedure ClickAboutMenu(Sender: TObject); procedure ClickExitMenu(Sender: TObject); procedure ClickUpdateMenu(Sender: TObject); procedure ClickAlwaysTopMenu(Sender: TObject); procedure ClickHibernateMenu(Sender: TObject); procedure ClickShowHideMenu(Sender: TObject); procedure ClickOptionsMenu(Sender: TObject); procedure ClickDetailsMenu(Sender: TObject); procedure ClickDeleteMenu(Sender: TObject); procedure ControlHide(Control: TWidgetControl); procedure ControlShow(Control: TWidgetControl); procedure ShowForm; procedure HideForm; procedure ChangeAlwaysTop(const Value: Boolean); procedure ChangeRefresh(const Value: Integer); procedure ChangeShowHide(const Value: Boolean); procedure ChangeIgnoreMouse(const Value: Boolean); procedure ChangePreventDragging(const Value: Boolean); function FormatTracker(const Value: Integer): WideString; function FormatPrevious(const Value1, Value2: Integer): WideString; function FormatChangeImage(const Value1, Value2: Integer): WideString; function ProcessMessage(var Msg: TMsg): Boolean; procedure ProcessMessages; procedure ModifyLanguage; procedure ModifyMenuLanguage; procedure DeleteSelf; { Properties } property WidgetURL: WideString read FWidgetURL write FWidgetURL; property AmungusID: WideString read FAmungusID write FAmungusID; property Title: WideString read FTitle write FTitle; property Interval: Integer read FInterval write FInterval; property Section: WideString read FSection write FSection; property Tracker: Integer read FTracker write FTracker; property Previous: Integer read FPrevious write FPrevious; property AlwaysTop: Boolean read FAlwaysTop write FAlwaysTop; property IgnoreMouse: Boolean read FIgnoreMouse write FIgnoreMouse; property PreventDragging: Boolean read FPreventDragging write FPreventDragging; property InitDelay: Integer read FInitDelay write FInitDelay; property OpacityMax: Integer read FOpacityMax write FOpacityMax; property EnableTracker: Boolean read FEnableTracker write FEnableTracker; property Effect: Boolean read FEffect write FEffect; property DialogHandle: HWND read FDialogHandle write FDialogHandle; property BackColor: Cardinal read FBackColor write FBackColor; end; { TAboutForm } TAboutForm = class(TWidgetForm) private Background: TWidgetImageControl; TitleLabel, VersionLabel, CopyrightLabel, HomepageLabel: TWidgetLabel; public constructor Create(AOwner: TComponent); override; destructor Destroy; override; procedure PaintWindow; override; procedure CreateForm; override; procedure CreateControls; procedure ShowForm; procedure HideForm; procedure ControlHide(Control: TWidgetControl); procedure ControlShow(Control: TWidgetControl); procedure DoMouseDown(Sender: TObject; Keys: Integer; X, Y: Integer); procedure HomepageLabelClick(Sender: TObject; Keys: Integer; X, Y: Integer); end; { TWidgetImageControl } TWidgetImageControl = class(TWidgetControl) private FImage: TWidgetImage; FCached: TGPCachedBitmap; FFileName: string; procedure SetFileName(const Value: string); procedure AllocateImage; procedure ReleaseImage; protected procedure CreateParams(var Params: TCreateParamsW); override; procedure ChangeImageData(Data: TBitmapData; Color: Cardinal; Opacity: Byte); procedure ChangeImage(ABitmap: TGPBitmap; Color: Cardinal; Opacity: Byte); public constructor Create(AOwner: TComponent); override; destructor Destroy; override; procedure PaintWindow; override; procedure CreateHandle; override; procedure ColorizeImage(const Color: TGPColor); procedure OpacityImage(const AImageOpacity: Byte); { Properties } property FileName: string read FFileName write SetFileName; property Image: TWidgetImage read FImage; end; { TWidgetLabel } TWidgetLabel = class(TWidgetControl) private FBorder: Boolean; FShadow: Boolean; FTransparent: Boolean; protected procedure CreateParams(var Params: TCreateParamsW); override; public constructor Create(AOwner: TComponent); override; destructor Destroy; override; procedure PaintWindow; override; property Border: Boolean read FBorder write FBorder; property Shadow: Boolean read FShadow write FShadow; property Transparent: Boolean read FTransparent write FTransparent; end; { TFormList } TFormList = class(TObjectList) end; { TWidgetManager } TWidgetManager = class(TWinForm) private FFormList: TFormList; FIniFile: TWMemIniFile; FWidgetTray: TWidgetTray; FConfigFolder: WideString; FThread: TInetThread; FVersionThread: TInetThread; FMainMenu: HMENU; FMultiThread: Boolean; FDialogHandle: HWND; FLangsMenu: HMENU; FWidgetsMenu: HMENU; FFirstTime: Boolean; FAboutForm: TAboutForm; function GetCount: Integer; function GetItem(Index: Integer): TWidgetMainForm; protected procedure CreateParams(var Params: TCreateParamsW); override; procedure WndProc(var Message: TWidgetMessage); override; procedure WMDestroy(var Message: TWidgetMessage); override; procedure WMClose(var Message: TWidgetMessage); override; procedure WMTimer(var Message: TWidgetMessage); override; procedure WMThreadDone(var Message: TWidgetMessage); procedure WMVersionDone(var Message: TWidgetMessage); procedure WMCommand(var Message: TWidgetMessage); virtual; procedure WMDetails(var Message: TWidgetMessage); virtual; procedure WMDeleteWidget(var Message: TWidgetMessage); virtual; public constructor Create(AOwner: TComponent); override; destructor Destroy; override; procedure CreateForm; override; procedure CreateMenu; procedure UpdateTrayMenu; procedure UpdateLangsMenu; procedure UpdateWidgtesMenu; procedure ModifyLanguage; procedure ModifyMenuLanguage; procedure CreateTray; procedure LoaderTimerExecute(Sender: TObject); procedure Initialize; procedure TrayMouseUp(Sender: TObject; Keys: Integer; X, Y: Integer); procedure TrayDblClick(Sender: TObject); function ProcessMessage(var Msg: TMsg): Boolean; procedure ProcessMessages; procedure SaveChanges; procedure CheckTracker; procedure CheckVersion; procedure ClickAboutMenu(Sender: TObject); procedure ClickExitMenu(Sender: TObject); procedure ClickHideMenu(Sender: TObject); procedure ClickShowMenu(Sender: TObject); procedure ClickAddWidgetMenu(Sender: TObject); procedure ClickWidgetsMenu(Sender: TObject; const MenuIndex: Integer); procedure ClickLangsMenu(Sender: TObject; const MenuIndex: Integer); procedure RightButtonClick(Sender: TObject); procedure HideForms; procedure ShowForms; function Add(WidgetForm: TWidgetMainForm): Integer; function Delete(WidgetForm: TWidgetMainForm): Integer; function AddAmungus(const ASection, ATitle: WideString; const AInitDelay: Integer): Integer; function GetByHandle(const AHandle: HWND): TWidgetMainForm; function GetByAmungusId(const AmungusId: WideString): TWidgetMainForm; procedure DeleteAmungus(const AmungusId: WideString); procedure DeleteByHandle(const AHandle: HWND); property Count: Integer read GetCount; property FormList: TFormList read FFormList; property Items[Index: Integer]: TWidgetMainForm read GetItem; property MultiThread: Boolean read FMultiThread write FMultiThread; property DialogHandle: HWND read FDialogHandle write FDialogHandle; end; { TWidgetApplication } TWidgetApplication = class private FRunning: Boolean; FMutex: THandle; FTimeCaps: TTimeCaps; FTitle: WideString; function GetRunning: Boolean; function GetHandle: HWND; public constructor Create; destructor Destroy; override; procedure Initialize; procedure Finalize; procedure Run; procedure InitializeMutex; procedure FinalizeMutex; property Handle: HWND read GetHandle; property Running: Boolean read GetRunning; property Title: WideString read FTitle write FTitle; end; { TWidgetLanguage } TWidgetLanguage = class(TObject) private FIniFile: TWMemIniFile; FID: WideString; FName: WideString; function GetText(const Ident: Integer): WideString; procedure SetText(const Ident: Integer; const Value: WideString); public constructor Create(const AID: WideString; IniFile: TWMemIniFile); destructor Destroy; override; property ID: WideString read FID; property Name: WideString read FName; property Text[const Ident: Integer]: WideString read GetText write SetText; default; end; { TWidgetLanguages } TWidgetLanguages = class(TComponent) private FItems: TObjectList; FNames: TWStringList; FCurrent: TWidgetLanguage; function GetText(const Ident: Integer): WideString; procedure SetText(const Ident: Integer; const Value: WideString); public constructor Create(AOwner: TComponent); override; destructor Destroy; override; procedure Initialize; procedure Add(const FileName: WideString); procedure Release; procedure Change(const ID: WideString); function Find(const ID: WideString): TWidgetLanguage; property Text[const Ident: Integer]: WideString read GetText write SetText; default; end; var WidgetManager: TWidgetManager; WidgetApplication: TWidgetApplication = nil; WLang: TWidgetLanguages; { OpenInternet } function OpenInternet: Boolean; { CloseInternet } procedure CloseInternet; implementation uses Variants, DialogRes, SettingsDlg, AddWidgetDlg; const WidgetVersion = '1.50'; WidgetAppName = 'Amungus' + WidgetVersion; WidgetMutexName = WidgetAppName + '_Widget_Manager_Mutex_Name'; WidgetClassName = WidgetAppName + '_Widget_Manager_Class_Name'; WidgetWindowName = WidgetAppName + '_Widget_Manager_Window_Name'; WidgetAppFolder = '\Shenturk\Amungus'; const IDT_REFRESHTIMER = 1001; IDT_LOADERTIMER = 1002; var FInternet: HINTERNET = nil; FCallbackProc: INTERNET_STATUS_CALLBACK = nil; { OpenInternet } function OpenInternet: Boolean; begin CloseInternet; FInternet := InternetOpen('Amungus Explorer 0.31', INTERNET_OPEN_TYPE_PRECONFIG, nil, nil, 0); Result := FInternet <> nil; if Result and Assigned(FCallbackProc) then InternetSetStatusCallback(FInternet, FCallbackProc); end; { CloseInternet } procedure CloseInternet; begin if FInternet <> nil then if InternetCloseHandle(FInternet) then FInternet := nil; end; { GetTempFolderPath } function GetTempFolderPath: WideString; begin SetLength(Result, MAX_PATH); GetTempPathW(MAX_PATH, PWideChar(Result)); Result := PWideChar(Result); end; { GetSpecialFolderPath } function GetSpecialFolderPath(nFolder: Integer): WideString; begin SetLength(Result, MAX_PATH); if SHGetSpecialFolderPathW(GetDesktopWindow(), PWideChar(Result), nFolder, False) then Result := PWideChar(Result) else Result := ''; end; { GetUserAppDataPath } function GetUserAppDataPath: WideString; begin Result := GetSpecialFolderPath(CSIDL_APPDATA) + WidgetAppFolder; end; { SetMenuText } procedure SetMenuText(Menu: HMENU; const Index: Integer; const Text: WideString); var mii: MENUITEMINFOW; begin FillChar(mii, SizeOf(MENUITEMINFOW), 0); mii.cbSize := SizeOf(MENUITEMINFOW); mii.fMask := MIIM_STRING; mii.dwTypeData := PWideChar(Text); mii.cch := Length(Text); SetMenuItemInfoW(Menu, Index, False, mii); end; { ParseVersionXML } function ParseVersionXML(const strXML: WideString): string; var xmlPage, Elem: OleVariant; begin Result := ''; xmlPage := CreateOleObject('Microsoft.XMLDOM'); try if not VarIsClear(xmlPage) then begin if xmlPage.LoadXml(strXML) then begin // /data/version Elem := xmlPage.documentElement.selectSingleNode('/data/version'); try if not VarIsClear(Elem) then Result := Elem.Text; finally Elem := Unassigned; end; end; end; finally xmlPage := Unassigned; end; end; { WidgetThreadFunc } function WidgetThreadFunc(Parameter: Pointer): Integer; var Msg: TMsg; WidgetForm: TWidgetMainForm; begin Result := -1; WidgetForm := TWidgetMainForm(Parameter); WidgetForm.HandleNeeded; if WidgetForm.Handle <> 0 then begin try InitCommonControls; // Call coinitialize on this thread if (CoInitFlags = -1) and (IsMultiThread) then CoInitFlags := COINIT_MULTITHREADED; // Required for multithreaded if Assigned(ComObj.CoInitializeEx) and (CoInitFlags <> -1) then ComObj.CoInitializeEx(nil, CoInitFlags) else CoInitialize(nil); WidgetForm.Visible := True; WidgetForm.ShowForm; WidgetForm.Update; Result := 0; while GetMessage(Msg, 0, 0, 0) do begin TranslateMessage(Msg); DispatchMessage(Msg); end; CoUninitialize; finally //OutputDebugString('End of Message Loop'); end; end; EndThread(0); end; { TWidgetMainForm } procedure TWidgetMainForm.ChangeAlwaysTop(const Value: Boolean); const CTopMost: array[Boolean] of Cardinal= (HWND_NOTOPMOST, HWND_TOPMOST); begin FAlwaysTop := Value; SetWindowPos(Self.Handle, CTopMost[Value], 0, 0, 0, 0, SWP_NOMOVE or SWP_NOSIZE or SWP_FRAMECHANGED); SetForegroundWindow(Self.Handle); SetActiveWindow(Self.Handle); Self.Update; end; procedure TWidgetMainForm.ChangeIgnoreMouse(const Value: Boolean); begin FIgnoreMouse := Value; if FIgnoreMouse then begin if Self.ExStyle and WS_EX_TRANSPARENT = 0 then Self.ExStyle := Self.ExStyle or WS_EX_TRANSPARENT; end else begin if Self.ExStyle and WS_EX_TRANSPARENT <> 0 then Self.ExStyle := Self.ExStyle and not WS_EX_TRANSPARENT; end; end; procedure TWidgetMainForm.ChangePreventDragging(const Value: Boolean); begin FPreventDragging := Value; end; procedure TWidgetMainForm.ChangeRefresh(const Value: Integer); begin FInterval := Value; end; procedure TWidgetMainForm.ChangeShowHide(const Value: Boolean); begin if Value then ShowForm else HideForm; end; procedure TWidgetMainForm.ClickAboutMenu(Sender: TObject); var S: WideString; begin S := WLang[MC_ABOUT]; if S[1] = '&' then Delete(S, 1, 1); MessageBoxW(Self.Handle, 'Amung.us Desktop Widget v1.50'#13#10#13#10 + 'Copyright (c) 2008 Shenturk.com', PWideChar(S), MB_OK); end; procedure TWidgetMainForm.ClickAlwaysTopMenu(Sender: TObject); begin FAlwaysTop := not FAlwaysTop; ChangeAlwaysTop(FAlwaysTop); end; procedure TWidgetMainForm.ClickDeleteMenu(Sender: TObject); begin DeleteSelf; end; procedure TWidgetMainForm.ClickDetailsMenu(Sender: TObject); begin SendMessageW(WidgetManager.Handle, WM_DETAILS, 0, Self.Handle); end; procedure TWidgetMainForm.ClickExitMenu(Sender: TObject); begin PostMessageW(WidgetManager.Handle, WM_CLOSE, 0, 0); end; procedure TWidgetMainForm.ClickHibernateMenu(Sender: TObject); begin FIgnoreMouse := not FIgnoreMouse; ChangeIgnoreMouse(FIgnoreMouse); end; procedure TWidgetMainForm.ClickOptionsMenu(Sender: TObject); begin if FDialogHandle = 0 then DialogBoxParamW(MainInstance, MakeIntResourceW(IDD_SETTINGS_DLG), Self.Handle, @SettingsDlgProc, Integer(Self)) else begin SetActiveWindow(FDialogHandle); SetForegroundWindow(FDialogHandle); end; end; procedure TWidgetMainForm.ClickShowHideMenu(Sender: TObject); begin FShowHide := not FShowHide; ChangeShowHide(FShowHide); end; procedure TWidgetMainForm.ClickUpdateMenu(Sender: TObject); begin RefreshTracker; end; procedure TWidgetMainForm.ControlHide(Control: TWidgetControl); const Step = 8; Wait = 4; begin while Control.Opacity > 0 do begin if Control.Opacity - Step <= 0 then begin Control.Opacity := 0; Self.Update; Break; end; Control.Opacity := Control.Opacity - Step; Self.Update; Sleep(Wait); end; Control.Hide; end; procedure TWidgetMainForm.ControlShow(Control: TWidgetControl); begin Control.Show; Control.Opacity := 255; Self.Update; end; constructor TWidgetMainForm.Create(AOwner: TComponent); begin inherited Create(AOwner); Width := 79; Height := 74; Left := Desktop.DesktopWidth - Width; Top := Desktop.WorkAreaHeight - Height; OnMouseDown := DoMouseDown; FInterval := 20000; FOpacityMax := $FF; FShowHide := True; with Canvas do begin Pen.Color := $FFFFFFFF; Brush.Color := $40000000; end; end; procedure TWidgetMainForm.CreateControls; begin Background := TWidgetImageControl.Create(Self); with Background do begin Parent := Self; OnMouseDown := DoMouseDown; FileName := 'SHADOW.PNG'; Width := 79; Height := 74; Left := 0; Top := 0; ColorizeImage(ColorRefToARGB(FBackColor)); Opacity := 255; Visible := True; end; TrackerLabel := TWidgetLabel.Create(Self); with TrackerLabel do begin Parent := Self; Width := 79; Height := 29; Left := 0; Top := Self.Height - Height - 20; Enabled := False; Cursor := LoadCursor(0, IDC_HAND); with Canvas do begin Pen.Color := $FFFFFFFF; Font.Format.Alignment := StringAlignmentCenter; Font.Format.LineAlignment := StringAlignmentCenter; Font.Name := 'Trebuchet MS'; Font.Size := 18; //Font.Style := FontStyleBold; Font.Color := $FFFFFFFF; end; Caption := FormatTracker(FTracker); Enabled := False; Visible := True; end; FPreviousLabel := TWidgetLabel.Create(Self); with FPreviousLabel do begin Parent := Self; Width := 70; Height := 14; Left := 8; Top := Self.Height - Height - 8; Enabled := False; Cursor := LoadCursor(0, IDC_HAND); with Canvas do begin Pen.Color := $FFFFFFFF; Font.Format.Alignment := StringAlignmentNear; Font.Format.LineAlignment := StringAlignmentCenter; Font.Name := 'Trebuchet MS';//'Tahoma';// Font.Size := 9; //Font.Style := FontStyleBold; Font.Color := $FFA0A0A0; end; Caption := FormatPrevious(FPrevious, FTracker); Enabled := False; Visible := True; end; FChangeControl := TWidgetImageControl.Create(Self); with FChangeControl do begin Parent := Self; Width := 12; Height := 12; Left := Self.Width - Width - 4; Top := 23; FileName := FormatChangeImage(FPrevious, FTracker); Enabled := False; Visible := True; end; Overlay := TWidgetImageControl.Create(Self); with Overlay do begin Parent := Self; OnMouseDown := DoMouseDown; FileName := 'OVERLAY.PNG'; Width := 79; Height := 74; Left := 0; Top := 0; Enabled := False; Visible := True; end; TitleLabel := TWidgetLabel.Create(Self); with TitleLabel do begin Parent := Self; Left := 0; Top := 0; Width := Self.Width; Height := 18; with Canvas do begin Font.Format.Alignment := StringAlignmentCenter; Font.Format.LineAlignment := StringAlignmentCenter; Font.Name := 'Trebuchet MS';//'Arial Unicode MS';// Font.Size := 8; Font.Color := $FFFFFFFF; end; Caption := FTitle; Enabled := False; Visible := True; end; FCloseLabel := TWidgetLabel.Create(Self); with FCloseLabel do begin Parent := Self; OnClick := DoCloseButtonClick; Width := 12; Height := 12; Left := Self.Width - Width - 5; Top := 4; Cursor := LoadCursor(0, IDC_HAND); with Canvas do begin Font.Format.Alignment := StringAlignmentCenter; Font.Format.LineAlignment := StringAlignmentCenter; Font.Name := 'Wingdings 2'; Font.Size := 13; Font.Color := $FFFF8000; Font.Style := FontStyleBold; end; Caption := #$004F; end; FBusyControl := TWidgetImageControl.Create(Self); with FBusyControl do begin Parent := Self; FileName := CStateImages[False]; Width := 6; Height := 6; Left := Self.Width - 2 * Width; Top := Self.Height - 2 * Height - 1; Enabled := False; //Border := True; Visible := True; end; end; procedure TWidgetMainForm.CreateForm; begin inherited CreateForm; FMainMenu := LoadMenuW(SysInit.HInstance, MakeIntResource(IDM_MAINMENU)); ModifyMenuLanguage; ChangeAlwaysTop(FAlwaysTop); ChangeIgnoreMouse(FIgnoreMouse); ChangePreventDragging(FPreventDragging); ChangeRefresh(FInterval); CreateControls; SetTimer(Self.Handle, IDT_LOADERTIMER, FInitDelay, nil); end; procedure TWidgetMainForm.DeleteSelf; begin if MessageBoxW(Self.Handle, PWideChar(WLang[IDS_TEXT_1006]), PWideChar(WLang[IDS_TEXT_1003]), MB_YESNO or MB_ICONWARNING) = IDYES then PostMessageW(WidgetManager.Handle, WM_DELETEWIDGET, 0, Self.Handle); end; destructor TWidgetMainForm.Destroy; begin inherited Destroy; end; procedure TWidgetMainForm.DialogCloseButtonClick(Sender: TObject; Keys, X, Y: Integer); begin Self.Opacity := FOpacityMax; Self.UpdateForm; end; procedure TWidgetMainForm.DoCloseButtonClick(Sender: TObject; Keys, X, Y: Integer); begin ClickExitMenu(Sender); end; procedure TWidgetMainForm.DoMouseDown(Sender: TObject; Keys, X, Y: Integer); var AcceptDragging: Boolean; begin AcceptDragging := (Keys and MK_LBUTTON <> 0); if PreventDragging then AcceptDragging := (Keys and MK_CONTROL <> 0); if Keys and MK_LBUTTON <> 0 then begin if AcceptDragging then begin FDragging := True; ReleaseCapture; SendMessageW(Self.Handle, WM_SYSCOMMAND, SC_DRAGMOVE, 0); FDragging := False; end; end else if Keys and MK_RBUTTON <> 0 then RightButtonClick(Self); end; function TWidgetMainForm.FormatChangeImage(const Value1, Value2: Integer): WideString; begin if Value1 > Value2 then Result := CChangeImages[-1] else if Value1 < Value2 then Result := CChangeImages[1] else Result := CChangeImages[0]; end; function TWidgetMainForm.FormatPrevious(const Value1, Value2: Integer): WideString; begin if Value1 < 0 then Result := '?' else Result := IntToStr(Value1); end; function TWidgetMainForm.FormatTracker(const Value: Integer): WideString; begin if Value < 0 then Result := '?' else Result := IntToStr(Value); end; procedure TWidgetMainForm.HideForm; const Step = 8; Wait = 4; begin FShowHide := False; CheckMenuItem(FMainMenu, MC_HIDE, MF_BYCOMMAND or CChecks[not FShowHide]); while Self.Opacity > 0 do begin if Self.Opacity - Step <= 0 then begin Self.Opacity := 0; Self.UpdateForm; Break; end; Self.Opacity := Self.Opacity - Step; Self.UpdateForm; Self.ProcessMessages; Sleep(Wait); end; Self.Hide; end; procedure TWidgetMainForm.LoaderTimerExecute(Sender: TObject); begin KillTimer(Self.Handle, IDT_LOADERTIMER); if FEnableTracker then begin if FInterval >= INTERVAL_MIN then SetTimer(Self.Handle, IDT_REFRESHTIMER, 100, nil); end; end; procedure TWidgetMainForm.ModifyLanguage; begin ModifyMenuLanguage; Self.Update; end; procedure TWidgetMainForm.ModifyMenuLanguage; var Menu: HMENU; begin Menu := GetSubMenu(FMainMenu, 0); SetMenuText(Menu, MC_OPTIONS, WLang[MC_OPTIONS]); SetMenuText(Menu, MC_REFRESH, WLang[MC_REFRESH]); SetMenuText(Menu, MC_HIDE, WLang[MC_HIDE]); SetMenuText(Menu, MC_DELETE, WLang[MC_DELETE]); SetMenuText(Menu, MC_DETAILS, WLang[MC_DETAILS]); end; function TWidgetMainForm.ProcessMessage(var Msg: TMsg): Boolean; begin Result := False; if PeekMessage(Msg, 0, 0, 0, PM_REMOVE) then begin Result := True; if Msg.Message <> WM_QUIT then begin TranslateMessage(Msg); DispatchMessage(Msg); end; //else FTerminated := True; end //else WaitMessage; // WaitMessage olmazsa islemci kullanimi %100 e vurur. end; procedure TWidgetMainForm.ProcessMessages; var Msg: TMsg; begin while ProcessMessage(Msg) do {loop}; end; procedure TWidgetMainForm.RefreshTimerExecute(Sender: TObject); begin if FEnableTracker then begin KillTimer(Self.Handle, IDT_REFRESHTIMER); RefreshTracker; if FInterval >= INTERVAL_MIN then SetTimer(Self.Handle, IDT_REFRESHTIMER, FInterval, nil); end; end; procedure TWidgetMainForm.RefreshTracker; begin if not Assigned(FThread) then begin FThread := TInetThread.Create(Self.Handle, WM_THREADDONE, FInternet); try with FThread.Request do begin Host := 'whos.amung.us'; {FWidgetURL := '/ajax/ffcount.php?k=' + FAmungusID;} { v1.0 } FWidgetURL := '/sitecount/' + FAmungusID; { v1.50 } URL := FWidgetURL; end; FThread.Resume; FBusyControl.FileName := CStateImages[True]; except FreeAndNil(FThread); FBusyControl.FileName := CStateImages[False]; end; Self.Update; end; end; procedure TWidgetMainForm.RightButtonClick(Sender: TObject); var P: TPoint; begin if FMainMenu <> 0 then begin GetCursorPos(P); TrackPopupMenuEx(GetSubMenu(FMainMenu, 0), TPM_LEFTALIGN or TPM_LEFTBUTTON or TPM_VERTICAL, P.x, P.y, Self.Handle, nil); end; end; procedure TWidgetMainForm.ShowForm; const Step = 8; Wait = 4; begin Self.Show; SetForegroundWindow(Self.Handle); SetActiveWindow(Self.Handle); Self.Update; FShowHide := True; CheckMenuItem(FMainMenu, MC_HIDE, MF_BYCOMMAND or CChecks[not FShowHide]); while Self.Opacity < FOpacityMax do begin if Self.Opacity + Step >= FOpacityMax then begin Self.Opacity := FOpacityMax; Self.UpdateForm; Break; end; Self.Opacity := Self.Opacity + Step; Self.UpdateForm; Self.ProcessMessages; Sleep(Wait); end; end; procedure TWidgetMainForm.WMAlwaysTop(var Message: TWidgetMessage); begin ClickAlwaysTopMenu(Self); end; procedure TWidgetMainForm.WMChangeLang(var Message: TWidgetMessage); begin ModifyLanguage; if IsWindow(Self.FDialogHandle) then SendMessageW(Self.FDialogHandle, WM_CHANGELANG, 0, 0); end; procedure TWidgetMainForm.WMClose(var Message: TWidgetMessage); begin if IsWindow(FDialogHandle) then SendMessageW(FDialogHandle, WM_CLOSE, 0, 0); HideForm; inherited WMClose(Message); end; procedure TWidgetMainForm.WMCommand(var Message: TWidgetMessage); begin with Message do if HIWORD(wParam) = 0 then // from Menu begin case LOWORD(wParam) of MC_ABOUT: ClickAboutMenu(Self); MC_EXIT: ClickExitMenu(Self); MC_REFRESH: ClickUpdateMenu(Self); MC_DELETE: ClickDeleteMenu(Self); MC_DETAILS: ClickDetailsMenu(Self); MC_HIDE: ClickShowHideMenu(Self); MC_OPTIONS: ClickOptionsMenu(Self); end; end; end; procedure TWidgetMainForm.WMDestroy(var Message: TWidgetMessage); begin KillTimer(Self.Handle, IDT_LOADERTIMER); KillTimer(Self.Handle, IDT_REFRESHTIMER); if Assigned(FThread) then begin if not FThread.Terminated then FThread.WaitFor; FreeAndNil(FThread); end; if FMainMenu <> 0 then DestroyMenu(FMainMenu); inherited WMDestroy(Message); if WidgetManager.MultiThread then PostQuitMessage(0); end; procedure TWidgetMainForm.WMHideForm(var Message: TWidgetMessage); begin Self.HideForm; end; procedure TWidgetMainForm.WMShowForm(var Message: TWidgetMessage); begin Self.ShowForm; end; procedure TWidgetMainForm.WMThreadDone(var Message: TWidgetMessage); begin if Assigned(FThread) then begin with FThread.Request do begin FPrevious := FTracker; FTracker := StrToIntDef(Trim(Response.Content), -1); TrackerLabel.Caption := FormatTracker(FTracker); FPreviousLabel.Caption := FormatPrevious(FPrevious, FTracker); FChangeControl.FileName := FormatChangeImage(FPrevious, FTracker); FBusyControl.FileName := CStateImages[False]; end; FreeAndNil(FThread); end; Self.Update; end; procedure TWidgetMainForm.WMTimer(var Message: TWidgetMessage); begin case Message.WParam of IDT_REFRESHTIMER: RefreshTimerExecute(Self); IDT_LOADERTIMER : LoaderTimerExecute(Self); end; end; procedure TWidgetMainForm.WMWindowPosChanging(var Message: TWidgetMessage); const SNAP_SIZE = 8; var WP: PWINDOWPOS; R, R1, R2: TRect; I: Integer; Item: TWidgetMainForm; begin inherited WMWindowPosChanging(Message); WP := PWINDOWPOS(Message.LParam); for I := 0 to WidgetManager.Count - 1 do begin Item := WidgetManager.Items[I]; if (Item <> Self) and (Item.Visible) then begin R1 := Item.WindowRect; R.Bottom := R1.Top - (WP^.y + Self.Height); if (R.Bottom > -SNAP_SIZE) and (R.Bottom < SNAP_SIZE) then WP^.y := R1.Top - Self.Height; R.Bottom := R1.Bottom - (WP^.y + Self.Height); if (R.Bottom > -SNAP_SIZE) and (R.Bottom < SNAP_SIZE) then WP^.y := R1.Bottom - Self.Height; R.Top := WP^.y - R1.Bottom; if (R.Top > -SNAP_SIZE) and (R.Top < SNAP_SIZE) then WP^.y := R1.Bottom; R.Top := WP^.y - R1.Top; if (R.Top > -SNAP_SIZE) and (R.Top < SNAP_SIZE) then WP^.y := R1.Top; R.Right := R1.Left - (WP^.x + Self.Width); if (R.Right > -SNAP_SIZE) and (R.Right < SNAP_SIZE) then WP^.x := R1.Left - Self.Width; R.Right := R1.Right - (WP^.x + Self.Width); if (R.Right > -SNAP_SIZE) and (R.Right < SNAP_SIZE) then WP^.x := R1.Right - Self.Width; R.Left := WP^.x - R1.Right; if (R.Left > -SNAP_SIZE) and (R.Left < SNAP_SIZE) then WP^.x := R1.Right; R.Left := WP^.x - R1.Left; if (R.Left > -SNAP_SIZE) and (R.Left < SNAP_SIZE) then WP^.x := R1.Left end; end; R2 := Desktop.WorkAreaRect; R.Bottom := R2.Bottom - (WP^.y + Self.Height); if (R.Bottom > -SNAP_SIZE) and (R.Bottom < SNAP_SIZE) then WP^.y := R2.Bottom - Self.Height; R.Top := WP^.y - R2.Top; if (R.Top > -SNAP_SIZE) and (R.Top < SNAP_SIZE) then WP^.y := R2.Top; R.Right := R2.Right - (WP^.x + Self.Width); if (R.Right > -SNAP_SIZE) and (R.Right < SNAP_SIZE) then WP^.x := R2.Right - Self.Width; R.Left := WP^.x - R2.Left; if (R.Left > -SNAP_SIZE) and (R.Left < SNAP_SIZE) then WP^.x := R2.Left; end; procedure TWidgetMainForm.WndProc(var Message: TWidgetMessage); begin case Message.Msg of WM_TIMER: WMTimer(Message); WM_THREADDONE: WMThreadDone(Message); WM_COMMAND: WMCommand(Message); WM_HIDEFORM: WMHideForm(Message); WM_SHOWFORM: WMShowForm(Message); WM_ALWAYSTOP: WMAlwaysTop(Message); WM_CHANGELANG: WMChangeLang(Message); else inherited WndProc(Message); end; end; { TWidgetImageControl } procedure TWidgetImageControl.AllocateImage; begin { if FileExists(FFileName) then FImage := TWidgetImage.Create(FFileName) else } FImage := TWidgetImage.Create(FFileName, wifResource); FCached := TGPCachedBitmap.Create(FImage.Handle, Canvas.Graphics); end; procedure TWidgetImageControl.ChangeImage(ABitmap: TGPBitmap; Color: Cardinal; Opacity: Byte); var Data: TBitmapData; R: TGPRect; begin if not IsAlphaPixelFormat(ABitmap.GetPixelFormat) then Exit; R := MakeRect(Rect(0, 0, ABitmap.GetWidth, ABitmap.GetHeight)); ABitmap.LockBits(R, ImageLockModeRead or ImageLockModeWrite, PixelFormat32bppARGB, Data); try ChangeImageData(Data, Color, Opacity); finally ABitmap.UnlockBits(Data); end; end; procedure TWidgetImageControl.ChangeImageData(Data: TBitmapData; Color: Cardinal; Opacity: Byte); var X, Y: Cardinal; Pixel: Widgets.PARGB; R, G, B: Byte; begin R := GetRValue(Color); G := GetGValue(Color); B := GetBValue(Color); for Y := 0 to Data.Height - 1 do begin Pixel := Widgets.PARGB(Cardinal(Data.Scan0) + Data.Width * 4 * Y); for X := 0 to Data.Width - 1 do begin { Pixel^.R := Pixel^.R * R shr $07; Pixel^.G := Pixel^.G * G shr $07; Pixel^.B := Pixel^.B * B shr $07; } Pixel^.R := R; Pixel^.G := G; Pixel^.B := B; //Pixel^.A := Pixel^.A * Opacity shr $08; Inc(Pixel); end; end; end; procedure TWidgetImageControl.ColorizeImage(const Color: TGPColor); begin if Assigned(FImage) then ChangeImage(FImage.Handle, Color, $FF); end; constructor TWidgetImageControl.Create(AOwner: TComponent); begin inherited Create(AOwner); end; procedure TWidgetImageControl.CreateHandle; begin inherited CreateHandle; end; procedure TWidgetImageControl.CreateParams(var Params: TCreateParamsW); begin inherited CreateParams(Params); CreateSubClass(Params, 'STATIC'); with Params do Style := Style or SS_LEFT or SS_NOPREFIX or SS_NOTIFY; end; destructor TWidgetImageControl.Destroy; begin ReleaseImage; inherited Destroy; end; procedure TWidgetImageControl.OpacityImage(const AImageOpacity: Byte); begin { if Assigned(FImage) then FImage.OpacityImage(AImageOpacity); } end; procedure TWidgetImageControl.PaintWindow; { var Attr: TGPImageAttributes; ColorMap: TColorMap; } begin inherited PaintWindow; with Canvas.Graphics do begin if Visible and Assigned(FImage) then begin { if Assigned(FCached) then; DrawCachedBitmap(FCached, 0, 0); } { Attr := TGPImageAttributes.Create; try ColorMap.oldColor := MakeColor(255, 128, 128, 128); ColorMap.newColor := MakeColor(128, 255, 255, 0); Attr.SetRemapTable(1, @ColorMap, ColorAdjustTypeBitmap); DrawImage(FImage.Handle, MakeRect(0, 0, Self.Width, Self.Height), 0, 0, Self.Width, Self.Height, UnitPixel, Attr); finally Attr.Free; end; } DrawImage(FImage.Handle, 0, 0, Self.Width, Self.Height); { DrawImage(FImage.Handle, 0, 0, Self.Width, Self.Height); DrawImage(FImage.Handle, 0, 0, Self.Width, Self.Height); DrawImage(FImage.Handle, 0, 0, Self.Width, Self.Height); DrawImage(FImage.Handle, 0, 0, Self.Width, Self.Height); } end; end; end; procedure TWidgetImageControl.ReleaseImage; begin if Assigned(FCached) then FreeAndNil(FCached); if Assigned(FImage) then FreeAndNil(FImage); end; procedure TWidgetImageControl.SetFileName(const Value: string); begin ReleaseImage; FFileName := Value; AllocateImage; end; { TWidgetLabel } constructor TWidgetLabel.Create(AOwner: TComponent); begin inherited Create(AOwner); FShadow := True; FTransparent := True; end; procedure TWidgetLabel.CreateParams(var Params: TCreateParamsW); begin inherited CreateParams(Params); CreateSubClass(Params, 'STATIC'); with Params do Style := Style or SS_LEFT or SS_NOPREFIX or SS_NOTIFY; end; destructor TWidgetLabel.Destroy; begin inherited Destroy; end; procedure TWidgetLabel.PaintWindow; var R: TRect; SaveColor: TGPColor; begin inherited PaintWindow; with Canvas do begin R := ClientRect; if not FTransparent then FillRectangle(R); if FShadow then begin OffsetRect(R, 1, 1); SaveColor := Font.Color; Font.Color := Font.Color and $40000000 or $0; DrawString(Caption, R); Font.Color := SaveColor; OffsetRect(R, -1, -1); end; DrawString(Caption, R); if FBorder then begin InflateRect(R, -1, -1); OffsetRect(R, 1, 1); DrawRectangle(R); end; end; end; { TWidgetManager } function TWidgetManager.Add(WidgetForm: TWidgetMainForm): Integer; begin Result := -1; if FFormList.IndexOf(WidgetForm) < 0 then Result := FFormList.Add(WidgetForm); end; function TWidgetManager.AddAmungus(const ASection, ATitle: WideString; const AInitDelay: Integer): Integer; var WidgetForm: TWidgetMainForm; Thread: THandle; dwThreadId: DWORD; begin Result := -1; WidgetForm := TWidgetMainForm.Create(Self); with WidgetForm do begin Name := 'WidgetMainForm' + ASection; if Self.FMultiThread then ParentWindow := GetDesktopWindow() { Must be Desktop } else Parent := Self; Left := FIniFile.ReadInteger(ASection, 'Left', Desktop.WorkAreaRect.Right - 79); Top := FIniFile.ReadInteger(ASection, 'Top', Desktop.WorkAreaRect.Bottom - 74); Opacity := 0; Section := ASection; Interval := FIniFile.ReadInteger(ASection, 'Interval', 15000); AmungusID := ASection; Title := ATitle; WidgetURL := '/sitecount/' + ASection; { v1.50 } Tracker := FIniFile.ReadInteger(ASection, 'Tracker', -1); Previous := FIniFile.ReadInteger(ASection, 'Previous', -1); AlwaysTop := FIniFile.ReadBool(ASection, 'AlwaysTop', True); InitDelay := AInitDelay; OpacityMax := FIniFile.ReadInteger(ASection, 'Opacity', 255); EnableTracker := FIniFile.ReadBool(ASection, 'Enable', True); IgnoreMouse := FIniFile.ReadBool(ASection, 'IgnoreMouse', False); PreventDragging := FIniFile.ReadBool(ASection, 'PreventDragging', False); BackColor := FIniFile.ReadInteger(Section, 'BackColor', $000000); if Self.FMultiThread then begin Thread := BeginThread(nil, 0, WidgetThreadFunc, WidgetForm, CREATE_SUSPENDED, dwThreadId); if Thread <> 0 then begin Result := Self.Add(WidgetForm); ResumeThread(Thread); end; Sleep(20); end else begin Visible := True; ShowForm; Result := Self.Add(WidgetForm); end; end; end; procedure TWidgetManager.CheckTracker; begin if not Assigned(FThread) then begin FThread := TInetThread.Create(Self.Handle, WM_THREADDONE, FInternet); try with FThread.Request do begin Host := 'whos.amung.us'; URL := '/widget/75t8h6jqah6v.png'; end; FThread.Resume; except FreeAndNil(FThread); end; end; end; procedure TWidgetManager.CheckVersion; begin if not Assigned(FVersionThread) then begin FVersionThread := TInetThread.Create(Self.Handle, WM_VERSIONDONE, FInternet); try with FVersionThread.Request do begin Host := 'www.shenturk.com'; URL := '/amungus.xml'; end; FVersionThread.Resume; except FreeAndNil(FVersionThread); end; end; end; procedure TWidgetManager.ClickAboutMenu(Sender: TObject); begin if not Assigned(FAboutForm) then begin FAboutForm := TAboutForm.Create(Self); FAboutForm.Parent := Self; FAboutForm.Opacity := 0; end; FAboutForm.ShowForm; FAboutForm.Update; end; procedure TWidgetManager.ClickAddWidgetMenu(Sender: TObject); begin if FDialogHandle = 0 then DialogBoxParamW(MainInstance, MakeIntResourceW(IDD_ADDWIDGET_DLG), Self.Handle, @AddWidgetDlgProc, Integer(Self)) else begin SetActiveWindow(FDialogHandle); SetForegroundWindow(FDialogHandle); end; end; procedure TWidgetManager.ClickExitMenu(Sender: TObject); begin SendMessageW(Handle, WM_CLOSE, 0, 0); end; procedure TWidgetManager.ClickHideMenu(Sender: TObject); begin HideForms; end; procedure TWidgetManager.ClickLangsMenu(Sender: TObject; const MenuIndex: Integer); var Index: Integer; Language: TWidgetLanguage; I: Integer; Widget: TWidgetMainForm; begin if MenuIndex >= MC_LANGUAGE_START then begin Index := MenuIndex - MC_LANGUAGE_START; if (Index >= 0) and (Index < WLang.FItems.Count) then begin Language := WLang.FItems[Index] as TWidgetLanguage; WLang.Change(Language.ID); ModifyLanguage; if IsWindow(Self.FDialogHandle) then SendMessageW(Self.FDialogHandle, WM_CHANGELANG, 0, 0); for I := 0 to Self.Count - 1 do begin Widget := Self.GetItem(I); PostMessageW(Widget.Handle, WM_CHANGELANG, 0, 0); end; end; end; end; procedure TWidgetManager.ClickShowMenu(Sender: TObject); begin ShowForms; end; procedure TWidgetManager.ClickWidgetsMenu(Sender: TObject; const MenuIndex: Integer); var Index: Integer; Widget: TWidgetMainForm; begin if MenuIndex >= MC_WIDGETS_START then begin Index := MenuIndex - MC_WIDGETS_START; if Index >= 0 then begin Widget := Self.GetItem(Index); PostMessageW(Widget.Handle, WM_COMMAND, MC_OPTIONS, 0); end; end; end; constructor TWidgetManager.Create(AOwner: TComponent); begin inherited Create(AOwner); FFormList := TFormList.Create(False); FConfigFolder := GetUserAppDataPath(); ForceDirectories(FConfigFolder); FMultiThread := True; end; procedure TWidgetManager.CreateForm; begin inherited CreateForm; Caption := WidgetWindowName; CreateMenu; CreateTray; SetTimer(Self.Handle, IDT_LOADERTIMER, 500, nil); end; procedure TWidgetManager.CreateMenu; begin if FMainMenu <> 0 then DestroyMenu(FMainMenu); FMainMenu := LoadMenuW(SysInit.HInstance, MakeIntResource(IDM_TRAYMENU)); UpdateTrayMenu; ModifyLanguage; end; procedure TWidgetManager.CreateParams(var Params: TCreateParamsW); begin inherited CreateParams(Params); CreateSubClass(Params, WidgetClassName); end; procedure TWidgetManager.CreateTray; begin FWidgetTray := TWidgetTray.Create(Self); with FWidgetTray do begin ParentWindow := GetDesktopWindow(); Icon := LoadIcon(MainInstance, MakeIntResource(101)); OnDblClick := TrayDblClick; OnMouseUp := TrayMouseUp; HintText := WidgetApplication.Title; HandleNeeded; VisibleTray := True; end; end; function TWidgetManager.Delete(WidgetForm: TWidgetMainForm): Integer; begin Result := FFormList.IndexOf(WidgetForm); if Result >= 0 then begin FIniFile.EraseSection(WidgetForm.AmungusID); Result := FFormList.Remove(WidgetForm); FreeAndNil(WidgetForm); end; end; procedure TWidgetManager.DeleteAmungus(const AmungusId: WideString); var Widget: TWidgetMainForm; begin Widget := GetByAmungusId(AmungusId); if Widget <> nil then begin SendMessageW(Widget.Handle, WM_CLOSE, 0, 0); Self.Delete(Widget); end; end; procedure TWidgetManager.DeleteByHandle(const AHandle: HWND); var Widget: TWidgetMainForm; begin Widget := GetByHandle(AHandle); if Widget <> nil then begin SendMessageW(Widget.Handle, WM_CLOSE, 0, 0); Self.Delete(Widget); end; end; destructor TWidgetManager.Destroy; begin if Assigned(WLang) then WLang.Free; FIniFile.Free; FFormList.Free; inherited Destroy; end; function TWidgetManager.GetByAmungusId( const AmungusId: WideString): TWidgetMainForm; var I: Integer; WidgetForm: TWidgetMainForm; begin Result := nil; for I := Self.Count - 1 downto 0 do begin WidgetForm := Self.Items[I]; if Assigned(WidgetForm) and (WidgetForm.AmungusID = AmungusId) then Result := WidgetForm; end; end; function TWidgetManager.GetByHandle(const AHandle: HWND): TWidgetMainForm; var I: Integer; WidgetForm: TWidgetMainForm; begin Result := nil; for I := Self.Count - 1 downto 0 do begin WidgetForm := Self.Items[I]; if Assigned(WidgetForm) and WidgetForm.HandleAllocated and (WidgetForm.Handle = AHandle) then Result := WidgetForm; end; end; function TWidgetManager.GetCount: Integer; begin Result := FFormList.Count; end; function TWidgetManager.GetItem(Index: Integer): TWidgetMainForm; begin Result := FFormList.Items[Index] as TWidgetMainForm; end; procedure TWidgetManager.HideForms; var I: Integer; WidgetForm: TWidgetMainForm; begin for I := Self.Count - 1 downto 0 do begin WidgetForm := Self.Items[I]; if Assigned(WidgetForm) then PostMessageW(WidgetForm.Handle, WM_HIDEFORM, 0, 0); //Sleep(10); end; end; procedure TWidgetManager.Initialize; var FileName: WideString; ASection, ATitle: WideString; AInitDelay: Integer; ALanguage: WideString; Values: TWStrings; I: Integer; begin FileName := FConfigFolder + '\amungus.ini'; Self.FFirstTime := not FileExists(FileName); FIniFile := TWMemIniFile.Create(FileName); ALanguage := FIniFile.ReadString('Config', 'Language', 'EN-US.INI'); WLang.Change(ALanguage); AInitDelay := 250; Values := TWStringList.Create; try FIniFile.ReadSectionValues('Trackers', Values); for I := 0 to Values.Count - 1 do begin ASection := Values.Values[Values.Names[I]]; if FIniFile.SectionExists(ASection) then begin ATitle := FIniFile.ReadString(ASection, 'Title', 'Amungus'); AddAmungus(ASection, ATitle, AInitDelay); Inc(AInitDelay, 200); Sleep(20); end; end; finally Values.Free; end; UpdateWidgtesMenu; if Self.FFirstTime then ClickAddWidgetMenu(Self); end; procedure TWidgetManager.LoaderTimerExecute(Sender: TObject); begin KillTimer(Self.Handle, IDT_LOADERTIMER); CheckVersion; CheckTracker; end; procedure TWidgetManager.ModifyLanguage; begin ModifyMenuLanguage; end; procedure TWidgetManager.ModifyMenuLanguage; var Menu: HMENU; begin Menu := GetSubMenu(FMainMenu, 0); SetMenuText(Menu, MC_ABOUT, WLang[MC_ABOUT]); SetMenuText(Menu, MC_SHOW, WLang[MC_SHOW]); SetMenuText(Menu, MC_HIDE, WLang[MC_HIDE]); SetMenuText(Menu, MC_LANGUAGES, WLang[MC_LANGUAGES]); SetMenuText(Menu, MC_ADDWIDGET, WLang[MC_ADDWIDGET]); SetMenuText(Menu, MC_EXIT, WLang[MC_EXIT]); end; function TWidgetManager.ProcessMessage(var Msg: TMsg): Boolean; begin Result := False; if PeekMessage(Msg, 0, 0, 0, PM_REMOVE) then begin Result := True; if Msg.Message <> WM_QUIT then begin TranslateMessage(Msg); DispatchMessage(Msg); end; //else FTerminated := True; end else WaitMessage; // WaitMessage olmazsa islemci kullanimi %100 e vurur. end; procedure TWidgetManager.ProcessMessages; var Msg: TMsg; begin while ProcessMessage(Msg) do {loop}; end; procedure TWidgetManager.RightButtonClick(Sender: TObject); var P: TPoint; begin CreateMenu; if FMainMenu <> 0 then begin GetCursorPos(P); TrackPopupMenuEx(GetSubMenu(FMainMenu, 0), TPM_LEFTALIGN or TPM_LEFTBUTTON or TPM_VERTICAL, P.x, P.y, Self.Handle, nil); end; end; procedure TWidgetManager.SaveChanges; var I: Integer; WidgetForm: TWidgetMainForm; begin FIniFile.WriteString('Config', 'Language', WLang.FCurrent.ID); FIniFile.EraseSection('Trackers'); for I := 0 to Self.Count - 1 do begin WidgetForm := Self.Items[I]; if Assigned(WidgetForm) then with WidgetForm, FIniFile do begin EraseSection(Section); WriteString('Trackers', Format('Key%d', [I]), AmungusID); WriteInteger(Section, 'Left', Left); WriteInteger(Section, 'Top', Top); WriteBool(Section, 'AlwaysTop', AlwaysTop); WriteBool(Section, 'IgnoreMouse', IgnoreMouse); WriteBool(Section, 'PreventDragging', PreventDragging); WriteString(Section, 'Title', Title); WriteString(Section, 'AmungusID', AmungusID); WriteInteger(Section, 'Interval', Interval); WriteInteger(Section, 'Tracker', Tracker); WriteInteger(Section, 'Previous', Previous); WriteInteger(Section, 'Opacity', OpacityMax); WriteBool(Section, 'Enable', FEnableTracker); WriteString(Section, 'BackColor', Format('0x%0.8x', [BackColor])); end; end; FIniFile.UpdateFile; end; procedure TWidgetManager.ShowForms; var I: Integer; WidgetForm: TWidgetMainForm; begin for I := 0 to Self.Count - 1 do begin WidgetForm := Self.Items[I]; if Assigned(WidgetForm) then PostMessageW(WidgetForm.Handle, WM_SHOWFORM, 0, 0); //Sleep(10); end; end; procedure TWidgetManager.TrayDblClick(Sender: TObject); begin //WidgetForm.ClickShowHideMenu(Sender); end; procedure TWidgetManager.TrayMouseUp(Sender: TObject; Keys, X, Y: Integer); begin if Keys and MK_RBUTTON <> 0 then begin SetActiveWindow(Self.Handle); SetForegroundWindow(Self.Handle); RightButtonClick(Self); end; end; procedure TWidgetManager.UpdateLangsMenu; var I: Integer; Language: TWidgetLanguage; Text: WideString; SubMenu: HMENU; Checked: Boolean; begin if FLangsMenu <> 0 then DestroyMenu(FLangsMenu); FLangsMenu := CreatePopupMenu(); for I := 0 to WLang.FItems.Count - 1 do begin Language := WLang.FItems[I] as TWidgetLanguage; Text := Language.Name; AppendMenuW(FLangsMenu, MF_STRING, MC_LANGUAGE_START + I, PWideChar(Text)); Checked := Language.ID = WLang.FCurrent.ID; CheckMenuItem(FLangsMenu, MC_LANGUAGE_START + I, MF_BYCOMMAND or CChecks[Checked]); end; SubMenu := GetSubMenu(FMainMenu, 0); ModifyMenuW(SubMenu, 2, MF_POPUP or MF_BYPOSITION or MF_STRING, FLangsMenu, PWideChar(WLang[MC_LANGUAGES])); end; procedure TWidgetManager.UpdateTrayMenu; begin UpdateLangsMenu; UpdateWidgtesMenu; end; procedure TWidgetManager.UpdateWidgtesMenu; var I: Integer; Widget: TWidgetMainForm; Text: WideString; SubMenu: HMENU; begin if FWidgetsMenu <> 0 then DestroyMenu(FWidgetsMenu); FWidgetsMenu := CreatePopupMenu(); if Self.Count > 0 then begin for I := 0 to Self.Count - 1 do begin Widget := Self.GetItem(I) as TWidgetMainForm; Text := Widget.Title; if Length(Text) = 0 then Text := WLang[IDS_TEXT_1007]; Text := Text + WideFormat(' - (%s)', [Widget.AmungusID]); AppendMenuW(FWidgetsMenu, MF_STRING, MC_WIDGETS_START + I, PWideChar(Text)); end; end else begin Text := WLang[IDS_TEXT_1008]; AppendMenuW(FWidgetsMenu, MF_STRING, MC_WIDGETS_START, PWideChar(Text)); EnableMenuItem(FWidgetsMenu, 0, MF_BYPOSITION or MF_GRAYED); end; SubMenu := GetSubMenu(FMainMenu, 0); ModifyMenuW(SubMenu, 5, MF_POPUP or MF_BYPOSITION or MF_STRING, FWidgetsMenu, PWideChar(WLang[MC_PREFRENCES])); end; procedure TWidgetManager.WMClose(var Message: TWidgetMessage); begin FWidgetTray.VisibleTray := False; SaveChanges; HideForms; SendMessageW(FWidgetTray.Handle, WM_CLOSE, 0, 0); inherited WMClose(Message); end; procedure TWidgetManager.WMCommand(var Message: TWidgetMessage); begin with Message do if HIWORD(wParam) = 0 then // from Menu begin case LOWORD(wParam) of MC_ABOUT: ClickAboutMenu(Self); MC_EXIT: ClickExitMenu(Self); MC_HIDE: ClickHideMenu(Self); MC_SHOW: ClickShowMenu(Self); MC_ADDWIDGET: ClickAddWidgetMenu(Self); else if LOWORD(wParam) >= MC_WIDGETS_START then ClickWidgetsMenu(Self, LOWORD(wParam)) else ClickLangsMenu(Self, LOWORD(wParam)); end; end; end; procedure TWidgetManager.WMDeleteWidget(var Message: TWidgetMessage); begin DeleteByHandle(Message.LParam); end; procedure TWidgetManager.WMDestroy(var Message: TWidgetMessage); var I: Integer; Form: TWidgetMainForm; begin KillTimer(Self.Handle, IDT_LOADERTIMER); for I := 0 to Self.Count - 1 do begin Form := Self.Items[I]; if Assigned(Form) then begin SendMessageW(Form.Handle, WM_CLOSE, 0, 0); Sleep(10); end; end; if Assigned(FThread) then begin if not FThread.Terminated then FThread.WaitFor; FreeAndNil(FThread); end; DestroyMenu(FLangsMenu); DestroyMenu(FWidgetsMenu); if FMainMenu <> 0 then DestroyMenu(FMainMenu); inherited WMDestroy(Message); PostQuitMessage(0); end; procedure TWidgetManager.WMDetails(var Message: TWidgetMessage); var URL: WideString; WidgetForm: TWidgetMainForm; begin WidgetForm := GetByHandle(Message.LParam); if Assigned(WidgetForm) then begin URL := 'http://whos.amung.us/stats/' + WidgetForm.AmungusID + '/'; ShellExecuteW(Self.Handle, 'open', PWideChar(URL), nil, nil, SW_SHOW); end; end; procedure TWidgetManager.WMThreadDone(var Message: TWidgetMessage); begin if Assigned(FThread) then begin //FThread.Request.Response.ContentStream.SaveToFile('tracker.png'); FreeAndNil(FThread); end; end; procedure TWidgetManager.WMTimer(var Message: TWidgetMessage); begin case Message.WParam of IDT_LOADERTIMER: LoaderTimerExecute(Self); end; end; procedure TWidgetManager.WMVersionDone(var Message: TWidgetMessage); var XMLText: WideString; VersionText: string; MessageText: WideString; URL: WideString; begin if Assigned(FVersionThread) then begin XMLText := FVersionThread.Request.Response.Content; FreeAndNil(FVersionThread); end; VersionText := ParseVersionXML(XMLText); if VersionText > WidgetVersion then begin MessageText := WLang[IDS_TEXT_1011]; if MessageBoxW(Self.Handle, PWideChar(MessageText), 'Amungus Desktop Widget', MB_YESNO or MB_ICONQUESTION) = IDYES then begin URL := 'http://www.shenturk.com/indir'; ShellExecuteW(Self.Handle, 'open', PWideChar(URL), nil, nil, SW_SHOW); end; end; end; procedure TWidgetManager.WndProc(var Message: TWidgetMessage); begin case Message.Msg of WM_TIMER: WMTimer(Message); WM_THREADDONE: WMThreadDone(Message); WM_VERSIONDONE: WMVersionDone(Message); WM_QUERYENDSESSION: Message.Result := 1; WM_ENDSESSION: if BOOL(Message.WParam) then SaveChanges; WM_COMMAND: WMCommand(Message); WM_DETAILS: WMDetails(Message); WM_DELETEWIDGET: WMDeleteWidget(Message); else inherited WndProc(Message); end; end; { TWidgetApplication } constructor TWidgetApplication.Create; begin inherited Create; FTitle := 'Amungus Desktop Widget'; end; destructor TWidgetApplication.Destroy; begin inherited Destroy; end; procedure TWidgetApplication.Finalize; begin Desktop.Free; CloseInternet; CoUninitialize; timeEndPeriod(FTimeCaps.wPeriodMin); end; procedure TWidgetApplication.FinalizeMutex; begin if FMutex <> 0 then begin WaitForSingleObject(FMutex, 0); CloseHandle(FMutex); end; end; function TWidgetApplication.GetHandle: HWND; begin Result := 0; if Assigned(WidgetManager) then Result := WidgetManager.Handle; end; function TWidgetApplication.GetRunning: Boolean; begin Result := FRunning; end; procedure TWidgetApplication.Initialize; begin InitCommonControls; // Call coinitialize on this thread if (CoInitFlags = -1) and (IsMultiThread) then CoInitFlags := COINIT_MULTITHREADED; // Required for multithreaded if Assigned(ComObj.CoInitializeEx) and (CoInitFlags <> -1) then ComObj.CoInitializeEx(nil, CoInitFlags) else CoInitialize(nil); timeGetDevCaps(@FTimeCaps, SizeOf(FTimeCaps)); timeBeginPeriod(FTimeCaps.wPeriodMin); { Required for Sleep() function } SetCurrentDir(ExtractFilePath(ParamStr(0))); WLang := TWidgetLanguages.Create(Desktop); OpenInternet; Desktop := TWidgetDesktop.Create(nil); with Desktop do Name := 'Desktop'; WidgetManager := TWidgetManager.Create(Desktop); WidgetManager.Name := 'WidgetManager'; WidgetManager.ParentWindow := GetDesktopWindow(); WidgetManager.HandleNeeded; WidgetManager.Initialize; end; procedure TWidgetApplication.InitializeMutex; var LastError: DWORD; begin FMutex := CreateMutexW(nil, False, WidgetMutexName); LastError := GetLastError; FRunning := LastError = ERROR_ALREADY_EXISTS; end; procedure TWidgetApplication.Run; var Msg: TMsg; Window: HWND; begin try InitializeMutex; try if not Running then begin Initialize; try //WidgetManager.Show; while GetMessage(Msg, 0, 0, 0) do begin TranslateMessage(Msg); DispatchMessage(Msg); end; finally Finalize; end; end else begin Window := FindWindowW(WidgetClassName, WidgetWindowName); if Window <> 0 then SendMessageW(Window, CM_RESTOREAPP, 0, 0); end; finally FinalizeMutex; end; except end; end; { TWidgetLanguage } constructor TWidgetLanguage.Create(const AID: WideString; IniFile: TWMemIniFile); begin inherited Create; FID := AID; FIniFile := IniFile; FName := FIniFile.ReadString('Language', 'Display', ''); end; destructor TWidgetLanguage.Destroy; begin FIniFile.Free; inherited Destroy; end; function TWidgetLanguage.GetText(const Ident: Integer): WideString; begin Result := FIniFile.ReadString('Language', WideFormat('%d', [Ident]), ''); end; procedure TWidgetLanguage.SetText(const Ident: Integer; const Value: WideString); begin FIniFile.WriteString('Language', WideFormat('%d', [Ident]), Value); end; { TWidgetLanguages } procedure TWidgetLanguages.Add(const FileName: WideString); var WideText: WideString; WidgetLanguage: TWidgetLanguage; Strings: TWStringList; MemFile: TWMemIniFile; Stream: TResourceStream; //Stream: TMemoryStream; UniCode: WideChar; begin Strings := TWStringList.Create; try Stream := TResourceStream.Create(MainInstance, FileName, 'LANGS'); //Stream := TMemoryStream.Create; try //Stream.LoadFromFile('.\Amungus 1.50\' + FileName); Stream.Read(UniCode, SizeOf(WideChar)); if UniCode <> BOM_LSB_FIRST then Stream.Seek(0, soFromBeginning); Strings.LoadFromStream(Stream); MemFile := TWMemIniFile.Create(FileName); MemFile.SetStrings(Strings); WideText := MemFile.ReadString('Language', 'Display', ''); WidgetLanguage := TWidgetLanguage.Create(FileName, MemFile); FItems.Add(WidgetLanguage); FNames.Add(WideText + '=' + FileName); FCurrent := WidgetLanguage; finally Stream.Free; end; finally Strings.Free; end; end; procedure TWidgetLanguages.Change(const ID: WideString); var Temp: TWidgetLanguage; begin Temp := Find(ID); if Temp <> nil then FCurrent := Temp; end; constructor TWidgetLanguages.Create(AOwner: TComponent); begin inherited Create(AOwner); FItems := TObjectList.Create(False); FNames := TWStringList.Create; FNames.Sorted := True; Initialize; end; destructor TWidgetLanguages.Destroy; begin Release; FNames.Free; FItems.Free; inherited Destroy; end; function TWidgetLanguages.Find(const ID: WideString): TWidgetLanguage; var I: Integer; begin for I := 0 to FItems.Count - 1 do begin Result := FItems.Items[I] as TWidgetLanguage; if Result.ID = ID then Exit; end; Result := nil; end; function TWidgetLanguages.GetText(const Ident: Integer): WideString; begin Result := ''; if Assigned(FCurrent) then Result := FCurrent[Ident]; end; procedure TWidgetLanguages.Initialize; begin Add('EN-US.INI'); Add('TR-TR.INI'); end; procedure TWidgetLanguages.Release; var I: Integer; begin for I := 0 to FItems.Count - 1 do FItems[I].Free; end; procedure TWidgetLanguages.SetText(const Ident: Integer; const Value: WideString); begin end; { TAboutForm } procedure TAboutForm.ControlHide(Control: TWidgetControl); const Step = 8; Wait = 4; begin while Control.Opacity > 0 do begin if Control.Opacity - Step <= 0 then begin Control.Opacity := 0; Self.Update; Break; end; Control.Opacity := Control.Opacity - Step; Self.Update; Sleep(Wait); end; Control.Hide; end; procedure TAboutForm.ControlShow(Control: TWidgetControl); const Step = 8; Wait = 4; begin Control.Show; while Control.Opacity < 255 do begin if Control.Opacity + Step >= 255 then begin Control.Opacity := 255; Self.Update; Break; end; Control.Opacity := Control.Opacity + Step; Self.Update; Sleep(Wait); end; end; constructor TAboutForm.Create(AOwner: TComponent); begin inherited Create(AOwner); Name := 'AboutForm'; Width := 343; Height := 197; Left := (Desktop.WorkAreaWidth - Width) div 2; Top := (Desktop.WorkAreaHeight - Height) div 2; end; procedure TAboutForm.CreateControls; begin Background := TWidgetImageControl.Create(Self); with Background do begin Parent := Self; OnMouseDown := DoMouseDown; FileName := 'ABOUT.PNG'; Width := 343; Height := 197; Left := 0; Top := 0; Opacity := 255; Visible := True; end; TitleLabel := TWidgetLabel.Create(Self); with TitleLabel do begin Parent := Self; Width := (Self.Width div 5) * 4; Height := Self.Height div 2; Left := Self.Width - Width - 20; Top := 20;//(Self.Height - Height) div 2; with Canvas do begin Font.Format.Alignment := StringAlignmentFar; Font.Format.LineAlignment := StringAlignmentCenter; Font.Name := 'Impact';//'Arial Unicode MS';//'Trebuchet MS'// Font.Size := 26; Font.Color := $EFFFFFFF; end; Caption := 'Amung.us Desktop Widget'; Enabled := False; //Border := True; Shadow := True; Visible := True; end; VersionLabel := TWidgetLabel.Create(Self); with VersionLabel do begin Parent := Self; Width := (Self.Width div 5) * 4; Height := 20; Left := Self.Width - Width - 20; Top := TitleLabel.Top + TitleLabel.Height - 8; with Canvas do begin Font.Format.Alignment := StringAlignmentFar; Font.Format.LineAlignment := StringAlignmentCenter; Font.Name := 'Trebuchet MS';//'Impact';//'Arial Unicode MS';// Font.Size := 8; Font.Color := $EFFFFFFF; end; Caption := 'Version ' + WidgetVersion; Enabled := False; //Border := True; Shadow := True; Visible := True; end; CopyrightLabel := TWidgetLabel.Create(Self); with CopyrightLabel do begin Parent := Self; Width := (Self.Width div 5) * 4; Height := 20; Left := Self.Width - Width - 20; Top := VersionLabel.Top + VersionLabel.Height; with Canvas do begin Font.Format.Alignment := StringAlignmentFar; Font.Format.LineAlignment := StringAlignmentCenter; Font.Name := 'Trebuchet MS';//'Impact';//'Arial Unicode MS';// Font.Size := 8; Font.Color := $EFFFFFFF; end; Caption := 'Copyright © 2008 freedelphi'; Enabled := False; //Border := True; Shadow := True; Visible := True; end; HomepageLabel := TWidgetLabel.Create(Self); with HomepageLabel do begin Parent := Self; OnClick := HomepageLabelClick; Width := (Self.Width div 5) * 4; Height := 20; Left := Self.Width - Width - 20; Top := CopyrightLabel.Top + CopyrightLabel.Height; with Canvas do begin Font.Format.Alignment := StringAlignmentFar; Font.Format.LineAlignment := StringAlignmentCenter; Font.Name := 'Trebuchet MS';//'Impact';//'Arial Unicode MS';// Font.Size := 8; Font.Color := $EFFFFF00; end; Caption := 'http://www.shenturk.com'; Cursor := LoadCursor(0, IDC_HAND); Shadow := True; Visible := True; end; end; procedure TAboutForm.CreateForm; begin inherited CreateForm; CreateControls; end; destructor TAboutForm.Destroy; begin inherited Destroy; end; procedure TAboutForm.DoMouseDown(Sender: TObject; Keys, X, Y: Integer); begin HideForm; end; procedure TAboutForm.HideForm; const Step = 8; Wait = 4; begin while Self.Opacity > 0 do begin if Self.Opacity - Step <= 0 then begin Self.Opacity := 0; Self.UpdateForm; Break; end; Self.Opacity := Self.Opacity - Step; Self.UpdateForm; Sleep(Wait); end; Self.Hide; end; procedure TAboutForm.HomepageLabelClick(Sender: TObject; Keys, X, Y: Integer); var URL: WideString; begin HideForm; URL := 'http://www.shenturk.com/?ref=amungus'; ShellExecuteW(WidgetManager.Handle, 'open', PWideChar(URL), nil, nil, SW_SHOW); end; procedure TAboutForm.PaintWindow; begin inherited PaintWindow; //Canvas.FillRectangle(Self.ClientRect); end; procedure TAboutForm.ShowForm; const Step = 8; Wait = 4; begin Self.Show; TitleLabel.Opacity := 0; VersionLabel.Opacity := 0; CopyrightLabel.Opacity := 0; HomepageLabel.Opacity := 0; SetForegroundWindow(Self.Handle); SetActiveWindow(Self.Handle); Self.Update; while Self.Opacity < 255 do begin if Self.Opacity + Step >= 255 then begin Self.Opacity := 255; Self.UpdateForm; Break; end; Self.Opacity := Self.Opacity + Step; Self.UpdateForm; Sleep(Wait); end; Sleep(50); ControlShow(TitleLabel); ControlShow(VersionLabel); ControlShow(CopyrightLabel); ControlShow(HomepageLabel); end; end.