display summary of unsaved content on exit

This commit is contained in:
Basile Burg 2017-01-18 09:36:46 +01:00
parent 8ef75e82b0
commit 6d48342da0
No known key found for this signature in database
GPG Key ID: 1868039F415CB8CF
4 changed files with 81 additions and 27 deletions

View File

@ -161,8 +161,8 @@ type
function getDocument(index: Integer): TCESynMemo;
function findDocument(const fname: string): TCESynMemo;
procedure openDocument(const fname: string);
function closeDocument(index: Integer): boolean;
function closeDocument(doc: TCESynMemo): boolean;
function closeDocument(index: Integer;promptOnChanged: boolean = true): boolean;
function closeDocument(doc: TCESynMemo;promptOnChanged: boolean = true): boolean;
public
constructor create(aOwner: TComponent); override;
destructor destroy; override;
@ -509,14 +509,14 @@ begin
end;
end;
function TCEEditorWidget.closeDocument(index: Integer): boolean;
function TCEEditorWidget.closeDocument(index: Integer; promptOnChanged: boolean = true): boolean;
var
doc: TCESynMemo;
begin
doc := getDocument(index);
if doc.isNil then
exit(false);
if (doc.modified or (doc.fileName = doc.tempFilename)) and
if promptOnChanged and (doc.modified or (doc.fileName = doc.tempFilename)) and
(dlgFileChangeClose(doc.fileName, UnsavedFile) = mrCancel) then
exit(false);
showWidget;
@ -526,14 +526,14 @@ begin
result := true;
end;
function TCEEditorWidget.closeDocument(doc: TCESynMemo): boolean;
function TCEEditorWidget.closeDocument(doc: TCESynMemo;promptOnChanged: boolean = true): boolean;
var
page: TCEPage = nil;
begin
page := TCEPage(doc.Parent);
if page.isNil then
exit(false);
exit(closeDocument(page.index));
exit(closeDocument(page.index, promptOnChanged));
end;
{$ENDREGION}

View File

@ -275,9 +275,9 @@ type
// opens or set the focus on the document matching aFilename.
procedure openDocument(const fname: string);
// closes the nth document.
function closeDocument(index: Integer): boolean;
function closeDocument(index: Integer; promptOnChanged: boolean = true): boolean;
// closes a particular document.
function closeDocument(doc: TCESynMemo): boolean;
function closeDocument(doc: TCESynMemo; promptOnChanged: boolean = true): boolean;
// conveniance property.
property document[index: integer]: TCESynMemo read getDocument;
end;
@ -306,6 +306,8 @@ type
function getProjectIndex: integer;
// returns the nth project.
function getProject(index: Integer): ICECommonProject;
// returns true if the nth project is modified
function projectModified(index: integer): boolean;
// tries to find the project named fname.
function findProject(const fname: string): ICECommonProject;
// selects the nth project of the group.
@ -336,8 +338,6 @@ type
end;
// TODO-cOptions: widgets that expose options can use ICEOptionsEditor in their ctxt menu
(**
* Single service provided by the options editor.
*)

View File

@ -1836,6 +1836,17 @@ end;
procedure TCEMainForm.FormCloseQuery(Sender: TObject; var CanClose: boolean);
var
i: Integer;
files: string = '';
projs: string = '';
group: string = #9'no';
chang: boolean = false;
d: TCESynMemo;
const
s: string = 'The following content is modified and changes will be lost'#10#10 +
'- Modified files:'#10' %s '#10 +
'- Modified projects:'#10' %s '#10 +
'- Project group modified:'#10' %s'#10#10 +
'Close without saving ?';
begin
canClose := false;
SaveLastDocsAndProj;
@ -1844,22 +1855,54 @@ begin
(dlgOkCancel('A project is still being compiled, close anyway ?') <> mrOK) then
exit;
if assigned(fFreeProj) then
if assigned(fFreeProj) and fFreeProj.modified then
begin
if fFreeProj.modified and
(dlgFileChangeClose(fFreeProj.filename, UnsavedProj) = mrCancel) then
exit;
fFreeProj.getProject.Free;
fFreeProj := nil;
projs += #9 + fFreeProj.filename + LineEnding;
chang := true;
end;
for i := fMultidoc.documentCount-1 downto 0 do
if not fMultidoc.closeDocument(i) then
exit;
if fProjectGroup.groupModified and
(dlgFileChangeClose(fProjectGroup.groupFilename, UnsavedPGrp) = mrCancel) then
exit;
canClose := true;
for i := 0 to fMultidoc.documentCount-1 do
begin
d := fMultidoc.getDocument(i);
if d.modified then
begin
files += #9 + shortenPath(d.filename) + LineEnding;
chang := true;
end;
end;
for i:= 0 to fProjectGroup.projectCount-1 do
begin
if not fProjectGroup.projectModified(i) then
continue;
projs += #9 + shortenPath(fProjectGroup.getProject(i).filename) + LineEnding;
chang := true;
end;
if fProjectGroup.groupModified then
begin
group := #9'yes';
chang := true;
end;
if chang then
begin
if projs.isEmpty then
projs := '(no modified projects)'#10;
if files.isEmpty then
files := '(no modified files)'#10;
if MessageDlg('Modified content', format(s, [files, projs, group]),
TMsgDlgType.mtConfirmation, [mbOk, mbCancel], '') <> mrOk then
exit;
end;
CanClose:= true;
fProjectGroup.closeGroup;
if assigned(fFreeProj) then
fFreeProj.getProject.Free;
for i:= fMultidoc.documentCount-1 downto 0 do
fMultidoc.closeDocument(i, false);
end;
procedure TCEMainForm.updateDocumentBasedAction(sender: TObject);

View File

@ -85,7 +85,8 @@ type
function getProject(ix: Integer): ICECommonProject;
function findProject(const fname: string): ICECommonProject;
procedure setProjectIndex(value: Integer);
function projectIsAsync(index: integer): boolean;
function projectIsAsync(ix: integer): boolean;
function projectModified(ix: integer): boolean;
//
function addItem(const fname: string): TProjectGroupItem;
property item[ix: integer]: TProjectGroupItem read getItem; default;
@ -245,9 +246,9 @@ begin
end;
end;
function TProjectGroup.projectIsAsync(index: integer): boolean;
function TProjectGroup.projectIsAsync(ix: integer): boolean;
begin
exit(item[index].asyncMode = amParallel);
exit(item[ix].asyncMode = amParallel);
end;
function TProjectGroup.addItem(const fname: string): TProjectGroupItem;
@ -284,6 +285,16 @@ begin
result.setActiveConfigurationIndex(item[ix].configurationIndex);
end;
function TProjectGroup.projectModified(ix: integer): boolean;
var
p: ICECommonProject;
begin
result := false;
p := item[ix].project;
if assigned(p) and (p.modified) then
result := true
end;
function TProjectGroup.findProject(const fname: string): ICECommonProject;
var
i: integer;
@ -407,7 +418,7 @@ var
b: boolean = false;
begin
for i:= 0 to fItems.Count-1 do
if (getItem(i).fProj <> nil) and getItem(i).fProj.modified then
if projectModified(i) then
begin
b := true;
break;