Add support for Windows 7 task button progress. Unify all callers of ProgressBarStatus in a set of 5 functions in main unit instead of helpers, as this is where the progress bar is placed and also we need the handle of the main window.

This commit is contained in:
Ansgar Becker
2011-11-08 22:27:52 +00:00
parent f9e896fede
commit a69041d17d
7 changed files with 139 additions and 46 deletions

View File

@ -4,7 +4,7 @@ interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls, ExtCtrls, Menus, VirtualTrees, SynExportHTML;
Dialogs, StdCtrls, ExtCtrls, Menus, ComCtrls, VirtualTrees, SynExportHTML;
type
TGridExportFormat = (efExcel, efCSV, efHTML, efXML, efSQLInsert, efSQLReplace, efLaTeX, efWiki);
@ -391,7 +391,7 @@ begin
NodeCount := Grid.SelectedCount
else
NodeCount := Grid.RootNodeCount;
EnableProgressBar(NodeCount);
MainForm.EnableProgress(NodeCount);
TableName := BestTableName(GridData);
if radioOutputCopyToClipboard.Checked then
@ -522,7 +522,7 @@ begin
Mainform.ShowStatusMsg('Exporting row '+FormatNumber(Node.Index+1)+' of '+FormatNumber(NodeCount)+
' ('+IntToStr(Trunc((Node.Index+1) / NodeCount *100))+'%, '+FormatByteNumber(S.Size)+')'
);
Mainform.ProgressBarStatus.Position := Node.Index+1;
MainForm.ProgressStep;
end;
RowNum := Grid.GetNodeData(Node);
GridData.RecNo := RowNum^;
@ -681,12 +681,13 @@ begin
on E:EFCreateError do begin
// Keep form open if file cannot be created
ModalResult := mrNone;
MainForm.SetProgressState(pbsError);
ErrorDialog(E.Message);
end;
end;
end;
Mainform.ProgressBarStatus.Visible := False;
Mainform.DisableProgress;
Mainform.ShowStatusMsg('Freeing data...');
FreeAndNil(S);
Mainform.ShowStatusMsg;

View File

@ -153,7 +153,6 @@ type
function GetRegValue( valueName: String; defaultValue: Boolean; Session: String = '' ) : Boolean; Overload;
function GetRegValue( valueName: String; defaultValue: String; Session: String = '' ) : String; Overload;
procedure DeInitializeVTNodes(Sender: TBaseVirtualTree);
procedure EnableProgressBar(MaxValue: Integer);
function CompareNumbers(List: TStringList; Index1, Index2: Integer): Integer;
function ListIndexByRegExpr(List: TStrings; Expression: String): Integer;
function FindNode(VT: TVirtualStringTree; idx: Cardinal; ParentNode: PVirtualNode): PVirtualNode;
@ -1678,15 +1677,6 @@ begin
end;
procedure EnableProgressBar(MaxValue: Integer);
begin
Mainform.ProgressBarStatus.State := pbsNormal;
Mainform.ProgressBarStatus.Visible := True;
Mainform.ProgressBarStatus.Max := MaxValue;
Mainform.ProgressBarStatus.Position := 0;
end;
function CompareNumbers(List: TStringList; Index1, Index2: Integer): Integer;
var
Number1, Number2 : Extended;

View File

@ -612,7 +612,7 @@ var
begin
// Insert files
Screen.Cursor := crHourglass;
EnableProgressBar(ListFiles.RootNodeCount);
MainForm.EnableProgress(ListFiles.RootNodeCount);
Node := ListFiles.GetFirst;
while Assigned(Node) do begin
@ -670,11 +670,11 @@ begin
sql := sql + ')';
try
FConnection.Query(sql);
Mainform.ProgressBarStatus.StepIt;
Mainform.ProgressBarStatus.Repaint;
Mainform.ProgressStep;
except
on E:EDatabaseError do begin
Screen.Cursor := crDefault;
MainForm.SetProgressState(pbsError);
ErrorDialog(E.Message);
ModalResult := mrNone;
break;
@ -685,7 +685,7 @@ begin
ListFiles.DeleteNode(DoneNode);
end;
Screen.Cursor := crDefault;
Mainform.ProgressBarStatus.Hide;
MainForm.DisableProgress;
end;

View File

@ -85,6 +85,8 @@ uses Main, helpers;
{$R *.DFM}
const
ProgressBarSteps=100;
procedure Tloaddataform.FormCreate(Sender: TObject);
@ -275,6 +277,7 @@ var
begin
Screen.Cursor := crHourglass;
StartTickCount := GetTickCount;
MainForm.EnableProgress(ProgressBarSteps);
ColumnCount := 0;
for i:=0 to chkListColumns.Items.Count-1 do begin
@ -320,11 +323,13 @@ begin
on E:EDatabaseError do begin
Screen.Cursor := crDefault;
ModalResult := mrNone;
MainForm.SetProgressState(pbsError);
ErrorDialog(E.Message);
end;
end;
Mainform.ShowStatusMsg;
MainForm.DisableProgress;
Screen.Cursor := crDefault;
end;
@ -405,15 +410,13 @@ var
IsEncl, IsTerm, IsLineTerm: Boolean;
InEncl: Boolean;
OutStream: TMemoryStream;
const
ProgressBarSteps=100;
procedure NextChar;
begin
Inc(P);
Inc(ProgressChars);
if ProgressChars >= ProgressCharsPerStep then begin
Mainform.ProgressBarStatus.StepIt;
Mainform.ProgressStep;
Mainform.ShowStatusMsg('Importing textfile, row '+FormatNumber(RowCount-IgnoreLines)+', '+IntToStr(Mainform.ProgressBarStatus.Position)+'%');
ProgressChars := 0;
end;
@ -504,8 +507,6 @@ const
end;
begin
EnableProgressBar(ProgressBarSteps);
TermLen := Length(Term);
EnclLen := Length(Encl);
LineTermLen := Length(LineTerm);
@ -567,7 +568,6 @@ begin
Contents := '';
FreeAndNil(OutStream);
RowCount := Max(RowCount-IgnoreLines, 0);
Mainform.ProgressBarStatus.Hide;
end;

View File

@ -14,7 +14,7 @@ uses
Messages, ExtCtrls, ComCtrls, StdActns, ActnList, ImgList, ToolWin, Clipbrd, SynMemo,
SynEdit, SynEditTypes, SynEditKeyCmds, VirtualTrees, DateUtils, SyncObjs,
ShlObj, SynEditMiscClasses, SynEditSearch, SynEditRegexSearch, SynCompletionProposal, SynEditHighlighter,
SynHighlighterSQL, Tabs, SynUnicode, SynRegExpr, ExtActns, IOUtils, Types, Themes,
SynHighlighterSQL, Tabs, SynUnicode, SynRegExpr, ExtActns, IOUtils, Types, Themes, ComObj,
CommCtrl, Contnrs, Generics.Collections, SynEditExport, SynExportHTML, Math, ExtDlgs, Registry, AppEvnts,
routine_editor, trigger_editor, event_editor, options, EditVar, helpers, createdatabase, table_editor,
TableTools, View, Usermanager, SelectDBObject, connections, sqlhelp, dbconnection,
@ -70,6 +70,34 @@ type
destructor Destroy; override;
end;
ITaskbarList = interface(IUnknown)
[SID_ITaskbarList]
function HrInit: HRESULT; stdcall;
function AddTab(hwnd: HWND): HRESULT; stdcall;
function DeleteTab(hwnd: HWND): HRESULT; stdcall;
function ActivateTab(hwnd: HWND): HRESULT; stdcall;
function SetActiveAlt(hwnd: HWND): HRESULT; stdcall;
end;
ITaskbarList2 = interface(ITaskbarList)
[SID_ITaskbarList2]
function MarkFullscreenWindow(hwnd: HWND; fFullscreen: BOOL): HRESULT; stdcall;
end;
ITaskbarList3 = interface(ITaskbarList2)
[SID_ITaskbarList3]
function SetProgressValue(hwnd: HWND; ullCompleted: ULONGLONG; ullTotal: ULONGLONG): HRESULT; stdcall;
function SetProgressState(hwnd: HWND; tbpFlags: Integer): HRESULT; stdcall;
function RegisterTab(hwndTab: HWND; hwndMDI: HWND): HRESULT; stdcall;
function UnregisterTab(hwndTab: HWND): HRESULT; stdcall;
function SetTabOrder(hwndTab: HWND; hwndInsertBefore: HWND): HRESULT; stdcall;
function SetTabActive(hwndTab: HWND; hwndMDI: HWND; tbatFlags: Integer): HRESULT; stdcall;
function ThumbBarAddButtons(hwnd: HWND; cButtons: UINT; pButton: PThumbButton): HRESULT; stdcall;
function ThumbBarUpdateButtons(hwnd: HWND; cButtons: UINT; pButton: PThumbButton): HRESULT; stdcall;
function ThumbBarSetImageList(hwnd: HWND; himl: HIMAGELIST): HRESULT; stdcall;
function SetOverlayIcon(hwnd: HWND; hIcon: HICON; pszDescription: LPCWSTR): HRESULT; stdcall;
function SetThumbnailTooltip(hwnd: HWND; pszTip: LPCWSTR): HRESULT; stdcall;
function SetThumbnailClip(hwnd: HWND; var prcClip: TRect): HRESULT; stdcall;
end;
TMainForm = class(TForm)
MainMenu1: TMainMenu;
File1: TMenuItem;
@ -947,6 +975,12 @@ type
AppVersion: String;
AppDescription: String;
// Task button interface
TaskbarList: ITaskbarList;
TaskbarList2: ITaskbarList2;
TaskbarList3: ITaskbarList3;
TaskbarList4: ITaskbarList4;
property Connections: TDBConnectionList read FConnections;
property Delimiter: String read FDelimiter write SetDelimiter;
procedure PaintColorBar(Value, Max: Extended; TargetCanvas: TCanvas; CellRect: TRect);
@ -990,6 +1024,11 @@ type
procedure BeforeQueryExecution(Thread: TQueryThread);
procedure AfterQueryExecution(Thread: TQueryThread);
procedure FinishedQueryExecution(Thread: TQueryThread);
procedure EnableProgress(MaxValue: Integer);
procedure DisableProgress;
procedure SetProgressPosition(Value: Integer);
procedure ProgressStep;
procedure SetProgressState(State: TProgressbarState);
end;
@ -1295,6 +1334,15 @@ begin
FIsWine := Assigned(wine_nt_to_unix_file_name);
FreeLibrary(NTHandle);
// Taskbar button interface for Windows 7
if CheckWin32Version(6, 1) then begin
TaskbarList := CreateComObject(CLSID_TaskbarList) as ITaskbarList;
TaskbarList.HrInit;
Supports(TaskbarList, IID_ITaskbarList2, TaskbarList2);
Supports(TaskbarList, IID_ITaskbarList3, TaskbarList3);
Supports(TaskbarList, IID_ITaskbarList4, TaskbarList4);
end;
// "All users" folder for HeidiSQL's data (All Users\Application Data)
FDirnameCommonAppData := GetShellFolder(CSIDL_COMMON_APPDATA) + '\' + APPNAME + '\';
@ -2174,7 +2222,7 @@ begin
Batch := SplitSQL(Text);
Text := '';
EnableProgressBar(Batch.Count);
EnableProgress(Batch.Count);
Tab.ResultTabs.Clear;
Tab.tabsetQuery.Tabs.Clear;
FreeAndNil(Tab.QueryProfile);
@ -2207,7 +2255,7 @@ begin
if Thread.QueriesInPacket > 1 then
Text := 'queries #' + FormatNumber(Thread.BatchPosition+1) + ' to #' + FormatNumber(Thread.BatchPosition+Thread.QueriesInPacket);
ShowStatusMsg('Executing '+Text+' of '+FormatNumber(Thread.Batch.Count)+' ...');
ProgressBarStatus.Position := Thread.BatchPosition;
SetProgressPosition(Thread.BatchPosition);
end;
@ -2298,7 +2346,7 @@ begin
// Error handling
if IsNotEmpty(Thread.ErrorMessage) then begin
ProgressBarStatus.State := pbsError;
SetProgressState(pbsError);
GoToErrorPos(Thread.ErrorMessage);
ErrorDialog(Thread.ErrorMessage);
end;
@ -2335,7 +2383,7 @@ begin
end;
// Clean up
ProgressBarStatus.Hide;
DisableProgress;
Tab.QueryRunning := False;
ValidateControls(Thread);
OperationRunning(False);
@ -2947,15 +2995,14 @@ begin
if MessageDialog('Delete '+IntToStr(Grid.SelectedCount)+' row(s)?',
mtConfirmation, [mbOK, mbCancel]) = mrOK then begin
FocusAfterDelete := nil;
EnableProgressBar(Grid.SelectedCount);
EnableProgress(Grid.SelectedCount);
Node := GetNextNode(Grid, nil, True);
while Assigned(Node) do begin
RowNum := Grid.GetNodeData(Node);
ShowStatusMsg('Deleting row #'+FormatNumber(ProgressBarStatus.Position+1)+' of '+FormatNumber(ProgressBarStatus.Max)+' ...');
Results.RecNo := RowNum^;
if Results.DeleteRow then begin
ProgressBarStatus.StepIt;
ProgressBarStatus.Repaint;
ProgressStep;
SetLength(Nodes, Length(Nodes)+1);
Nodes[Length(Nodes)-1] := Node;
FocusAfterDelete := Node;
@ -2978,11 +3025,11 @@ begin
ValidateControls(Sender);
end;
except on E:EDatabaseError do begin
ProgressBarStatus.State := pbsError;
SetProgressState(pbsError);
ErrorDialog('Grid editing error', E.Message);
end;
end;
Mainform.ProgressBarStatus.Visible := False;
DisableProgress;
ShowStatusMsg();
end;
@ -3048,24 +3095,24 @@ begin
if MessageDialog('Empty '+IntToStr(Objects.count)+' table(s) and/or view(s) ?', Names,
mtConfirmation, [mbOk, mbCancel]) = mrOk then begin
Screen.Cursor := crHourglass;
EnableProgressBar(Objects.Count);
EnableProgress(Objects.Count);
try
for TableOrView in Objects do begin
case TableOrView.Connection.Parameters.NetTypeGroup of
ngMySQL: TableOrView.Connection.Query('TRUNCATE ' + TableOrView.QuotedName);
ngMSSQL: TableOrView.Connection.Query('DELETE FROM ' + TableOrView.QuotedName);
end;
ProgressBarStatus.StepIt;
ProgressStep;
end;
actRefresh.Execute;
except
on E:EDatabaseError do begin
ProgressBarStatus.State := pbsError;
SetProgressState(pbsError);
ErrorDialog(E.Message);
end;
end;
Objects.Free;
ProgressBarStatus.Hide;
DisableProgress;
Screen.Cursor := crDefault;
end;
end;
@ -10073,6 +10120,61 @@ begin
end;
procedure TMainForm.EnableProgress(MaxValue: Integer);
begin
// Initialize progres bar and button
SetProgressPosition(0);
SetProgressState(pbsNormal);
ProgressBarStatus.Visible := True;
ProgressBarStatus.Max := MaxValue;
end;
procedure TMainForm.DisableProgress;
begin
// Hide global progress bar
SetProgressPosition(0);
ProgressBarStatus.Hide;
if Assigned(TaskBarList3) then
TaskBarList3.SetProgressState(Application.MainForm.Handle, 0);
end;
procedure TMainForm.SetProgressPosition(Value: Integer);
begin
// Advance progress bar and task progress position
ProgressBarStatus.Position := Value;
ProgressBarStatus.Repaint;
if Assigned(TaskBarList3) then
TaskBarList3.SetProgressValue(Application.MainForm.Handle, Value, ProgressBarStatus.Max);
end;
procedure TMainForm.ProgressStep;
begin
SetProgressPosition(ProgressBarStatus.Position+1);
end;
procedure TMainForm.SetProgressState(State: TProgressbarState);
var
Flag: Integer;
begin
// Set error or pause state in progress bar or task button
ProgressBarStatus.State := State;
ProgressBarStatus.Repaint;
if Assigned(TaskBarList3) then begin
case State of
pbsNormal: Flag := 2;
pbsError: Flag := 4;
pbsPaused: Flag := 8;
else Flag := 0;
end;
TaskBarList3.SetProgressState(Application.MainForm.Handle, Flag);
end;
end;
{ TQueryTab }

View File

@ -542,11 +542,11 @@ begin
end;
// Update columns
EnableProgressBar(FColumns.Count + DeletedKeys.Count + FKeys.Count);
MainForm.EnableProgress(FColumns.Count + DeletedKeys.Count + FKeys.Count);
Node := listColumns.GetFirst;
PreviousCol := nil;
while Assigned(Node) do begin
Mainform.ProgressBarStatus.StepIt;
Mainform.ProgressStep;
Col := listColumns.GetNodeData(Node);
if Col.Status <> esUntouched then begin
ColSpec := DBObject.Connection.QuoteIdent(Col.Name);
@ -602,7 +602,7 @@ begin
// Drop indexes, also changed indexes, which will be readded below
for i:=0 to DeletedKeys.Count-1 do begin
Mainform.ProgressBarStatus.StepIt;
Mainform.ProgressStep;
if DeletedKeys[i] = PKEY then
IndexSQL := 'PRIMARY KEY'
else
@ -611,7 +611,7 @@ begin
end;
// Add changed or added indexes
for i:=0 to FKeys.Count-1 do begin
Mainform.ProgressBarStatus.StepIt;
Mainform.ProgressStep;
if FKeys[i].Modified and (not FKeys[i].Added) then begin
if FKeys[i].OldIndexType = PKEY then
IndexSQL := 'PRIMARY KEY'
@ -634,7 +634,7 @@ begin
FreeAndNil(Specs);
Mainform.ShowStatusMsg;
Mainform.ProgressBarStatus.Hide;
MainForm.DisableProgress;
Screen.Cursor := crDefault;
end;

View File

@ -537,7 +537,7 @@ begin
FCancelled := False;
FObjectSizesDone := 0;
FObjectSizesDoneExact := 0;
EnableProgressBar(100);
MainForm.EnableProgress(100);
SessionNode := TreeObjects.GetFirstChild(nil);
while Assigned(SessionNode) do begin
DBNode := TreeObjects.GetFirstChild(SessionNode);
@ -607,7 +607,7 @@ begin
btnCloseOrCancel.Caption := 'Close';
btnCloseOrCancel.ModalResult := mrCancel;
Mainform.ProgressBarStatus.Hide;
MainForm.DisableProgress;
tabsTools.Enabled := True;
treeObjects.Enabled := True;
ValidateControls(Sender);
@ -793,7 +793,7 @@ begin
Percent := 100 / Max(FObjectSizes,1) * FObjectSizesDoneExact;
lblCheckedSize.Caption := 'Selected objects size: '+FormatByteNumber(FObjectSizes)+'. '+
FormatNumber(Percent, 1) + '% done.';
Mainform.ProgressBarStatus.Position := Round(Percent);
MainForm.SetProgressPosition(Round(Percent));
Application.ProcessMessages;
end;