Repository navigation
Expand file tree
/
Copy pathDN.PackageOverview.pas
More file actions
255 lines (229 loc) · 7.71 KB
/
Copy pathDN.PackageOverview.pas
File metadata and controls
255 lines (229 loc) · 7.71 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
{
#########################################################
# Copyright by Alexander Benikowski #
# This unit is part of the Delphinus project hosted on #
# https://github.com/Memnarch/Delphinus #
#########################################################
}
unit DN.PackageOverview;
interface
uses
Classes,
Types,
Messages,
Controls,
Forms,
Generics.Collections,
DN.Package.Intf,
DN.Preview;
type
TCheckIsPackageInstalled = reference to function(const APackage: IDNPackage): string;
TPackageEvent = reference to procedure(const APackage: IDNPackage);
TPackageOverView = class(TScrollBox)
private
FPreviews: TObjectList<TPreview>;
FUnusedPreviews: TObjectList<TPreview>;
FPackages: TList<IDNPackage>;
FSelectedPackage: IDNPackage;
FOnSelectedPackageChanged: TNotifyEvent;
FOnCheckIsPackageInstalled: TCheckIsPackageInstalled;
FOnCheckHasPackageUpdate: TCheckIsPackageInstalled;
FOnInstallPackage: TPackageEvent;
FOnUninstallPackage: TPackageEvent;
FOnUpdatePackage: TPackageEvent;
FOnInfoPackage: TPackageEvent;
procedure HandlePackagesChanged(Sender: TObject; const Item: IDNPackage; Action: TCollectionNotification);
procedure AddPreview(const APackage: IDNPackage);
procedure RemovePreview(const APackage: IDNPackage);
procedure HandlePreviewClicked(Sender: TObject);
procedure ChangeSelectedPackage(const APackage: IDNPackage);
function GetPreviewForPackage(const APackage: IDNPackage): TPreview;
function GetInstalledVersion(const APackage: IDNPackage): string;
function GetUpdateVersion(const APackage: IDNPackage): string;
procedure InstallPackage(const APackage: IDNPackage);
procedure UninstallPackage(const APackage: IDNPackage);
procedure UpdatePackage(const APackage: IDNPackage);
procedure InfoPackage(const APackage: IDNPackage);
public
constructor Create(AOwner: TComponent); override;
destructor Destroy(); override;
procedure Clear();
procedure Refresh();
property Packages: TList<IDNPackage> read FPackages;
property SelectedPackage: IDNPackage read FSelectedPackage;
property OnSelectedPackageChanged: TNotifyEvent read FOnSelectedPackageChanged write FOnSelectedPackageChanged;
property OnCheckIsPackageInstalled: TCheckIsPackageInstalled read FOnCheckIsPackageInstalled write FOnCheckIsPackageInstalled;
property OnCheckHasPackageUpdate: TCheckIsPackageInstalled read FOnCheckHasPackageUpdate write FOnCheckHasPackageUpdate;
property OnInstallPackage: TPackageEvent read FOnInstallPackage write FOnInstallPackage;
property OnUninstallPackage: TPackageEvent read FOnUninstallPackage write FOnUninstallPackage;
property OnUpdatePackage: TPackageEvent read FOnUpdatePackage write FOnUpdatePackage;
property OnInfoPackage: TPackageEvent read FOnInfoPackage write FOnInfoPackage;
end;
implementation
{ TPackageOverView }
const
CColumns = 4;
CSpace = 10;
procedure TPackageOverView.AddPreview(const APackage: IDNPackage);
var
LPreview: TPreview;
begin
if FUnusedPreviews.Count > 0 then
LPreview := FUnusedPreviews.Extract(FUnusedPreviews[0])
else
LPreview := TPreview.Create(nil);
LPreview.Package := APackage;
LPreview.Parent := Self;
LPreview.Top := (FPreviews.Count div CColumns) * (LPreview.Height + CSpace);
LPreview.Left := (FPreviews.Count mod CColumns) * (LPreview.Width + CSpace);
LPreview.InstalledVersion := GetInstalledVersion(APackage);
LPreview.UpdateVersion := GetUpdateVersion(APackage);
LPreview.OnClick := HandlePreviewClicked;
LPreview.OnInstall := procedure(Sender: TObject) begin InstallPackage(TPreview(Sender).Package) end;
LPreview.OnUninstall := procedure(Sender: TObject) begin UninstallPackage(TPreview(Sender).Package) end;
LPreview.OnUpdate := procedure(Sender: TObject) begin UpdatePackage(TPreview(Sender).Package) end;
LPreview.OnInfo := procedure(Sender: TObject) begin InfoPackage(TPreview(Sender).Package) end;
FPreviews.Add(LPreview)
end;
procedure TPackageOverView.Clear;
begin
FPackages.Clear();
end;
constructor TPackageOverView.Create(AOwner: TComponent);
begin
inherited;
FPreviews := TObjectList<TPreview>.Create(True);
FUnusedPreviews := TObjectList<TPreview>.Create(True);
FPackages := TList<IDNPackage>.Create();
FPackages.OnNotify := HandlePackagesChanged;
BorderStyle := bsNone;
VertScrollBar.Smooth := True;
VertScrollBar.Tracking := True;
end;
destructor TPackageOverView.Destroy;
begin
FPreviews.Free();
FUnusedPreviews.Free;
FPackages.Free();
inherited;
end;
function TPackageOverView.GetPreviewForPackage(
const APackage: IDNPackage): TPreview;
var
LPreview: TPreview;
begin
Result := nil;
for LPreview in FPreviews do
begin
if LPreview.Package = APackage then
begin
Result := LPreview;
Break;
end;
end;
end;
procedure TPackageOverView.HandlePackagesChanged(Sender: TObject;
const Item: IDNPackage; Action: TCollectionNotification);
begin
case Action of
cnAdded: AddPreview(Item);
cnRemoved, cnExtracted: RemovePreview(Item);
end;
end;
procedure TPackageOverView.HandlePreviewClicked(Sender: TObject);
begin
ChangeSelectedPackage((Sender as TPreview).Package);
end;
function TPackageOverView.GetUpdateVersion(const APackage: IDNPackage): string;
begin
if Assigned(FOnCheckHasPackageUpdate) then
begin
Result := FOnCheckHasPackageUpdate(APackage);
end
else
begin
Result := '';
end;
end;
procedure TPackageOverView.InfoPackage(const APackage: IDNPackage);
begin
if Assigned(FOnInfoPackage) then
FOnInfoPackage(APackage);
end;
procedure TPackageOverView.InstallPackage(const APackage: IDNPackage);
begin
if Assigned(FOnInstallPackage) then
FOnInstallPackage(APackage);
end;
function TPackageOverView.GetInstalledVersion(
const APackage: IDNPackage): string;
begin
if Assigned(FOnCheckIsPackageInstalled) then
begin
Result := FOnCheckIsPackageInstalled(APackage);
end
else
begin
Result := '';
end;
end;
procedure TPackageOverView.Refresh;
var
LPreview: TPreview;
begin
for LPreview in FPreviews do
begin
LPreview.InstalledVersion := GetInstalledVersion(LPreview.Package);
LPreview.UpdateVersion := GetUpdateVersion(LPreview.Package);
end;
end;
procedure TPackageOverView.RemovePreview(const APackage: IDNPackage);
var
i: Integer;
begin
for i := FPreviews.Count - 1 downto 0 do
begin
if FPreviews[i].Package = APackage then
begin
FPreviews[i].Parent := nil;
FPreviews[i].Package := nil;
FUnusedPreviews.Add(FPreviews.Extract(FPreviews[i]));
Break;
end;
end;
if FSelectedPackage = APackage then
begin
ChangeSelectedPackage(nil);
end;
end;
procedure TPackageOverView.UninstallPackage(const APackage: IDNPackage);
begin
if Assigned(FOnUninstallPackage) then
FOnUninstallPackage(APackage);
end;
procedure TPackageOverView.UpdatePackage(const APackage: IDNPackage);
begin
if Assigned(FOnUpdatePackage) then
FOnUpdatePackage(APackage);
end;
procedure TPackageOverView.ChangeSelectedPackage;
var
LPreview: TPreview;
begin
if Assigned(FSelectedPackage) then
begin
LPreview := GetPreviewForPackage(FSelectedPackage);
if Assigned(LPreview) then
LPreview.Selected := False;
end;
FSelectedPackage := APackage;
if Assigned(FSelectedPackage) then
begin
LPreview := GetPreviewForPackage(FSelectedPackage);
if Assigned(LPreview) then
LPreview.Selected := True;
end;
if Assigned(FOnSelectedPackageChanged) then
FOnSelectedPackageChanged(Self);
end;
end.