Skip to content

Commit 8a48919

Browse files
Documentation for Redesign Gantt Popup Editing Form (#1591)
* docs(gantt): revamp the Popup edit form article * docs(gantt-data-binding): add missing data binding features * docs(gantt-data-binding): order the features in alphabetical order * docs(gantt): add popup form template article * docs(gantt): remove unneeded lines * Update components/gantt/gantt-tree/data-binding/overview.md Co-authored-by: Yordan <[email protected]> * Update components/gantt/gantt-tree/editing/popup.md Co-authored-by: Yordan <[email protected]> * Update components/gantt/gantt-tree/data-binding/overview.md Co-authored-by: Yordan <[email protected]> * Update components/gantt/gantt-tree/editing/popup.md Co-authored-by: Yordan <[email protected]> * Update components/gantt/gantt-tree/editing/popup.md Co-authored-by: Yordan <[email protected]> * Update components/gantt/gantt-tree/editing/popup.md Co-authored-by: Yordan <[email protected]> * Update components/gantt/gantt-tree/templates/popup-form-template.md Co-authored-by: Yordan <[email protected]> * Update components/gantt/gantt-tree/templates/popup-form-template.md Co-authored-by: Yordan <[email protected]> --------- Co-authored-by: Yordan <[email protected]>
1 parent 47981fc commit 8a48919

File tree

3 files changed

+574
-41
lines changed

3 files changed

+574
-41
lines changed

components/gantt/gantt-tree/data-binding/overview.md

Lines changed: 13 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -33,19 +33,28 @@ The Blazor Gantt Tree provides various parameters to configure its items. Also c
3333

3434
| Parameter | Description |
3535
| --- | --- |
36+
| `EndField` | Defines the end date of a task. |
37+
| `HasChildren` | Whether the item has children. Determines whether an expand arrow is rendered next to the item in an Expandable column. Required when loading data on-demand—if you don't set it to `true`, an expand arrow will not appear and the user will not be able to expand the item and load its children. With hierarchical data, the Gantt Tree will render the icon based on the existence of child items, but `HasChildren` will take precedence. You do not have to set or use its field unless you want to load data on demand or override the arrow for some items. |
38+
| `Id` | A unique identifier for the item. Required only for binding to flat data. |
3639
| `Items` | The collection of child items that will be rendered under the current item. Required only when binding to hierarchical data. |
37-
| `Id` | A unique identifier for the item. |
40+
3841
| `ParentId` | Identifies the parent to whom the item belongs. Required only when binding to flat data. All items with the same `ParentId` will be rendered at the same level. For a root level item, `ParentId` needs to be `null`. There needs to be at least one node with a `null` value for the `ParentId`. |
39-
| `HasChildren` | Whether the item has children. Determines whether an expand arrow is rendered next to the item in an Expandable column. Required for loading data on-demand - if you don't set it to `true`, there will be no expand arrow and so there will be no way for the user to expand the item and load its children. With hierarchical data, the Gantt Tree will render the icon based on the existence of child items, but `HasChildren` will take precedence. You do not have to set or use its field unless you want to load data on demand, or override the arrow for some items. |
42+
| `PercentCompleteField` | Defines the level of completion of a task in percentages. |
43+
| `StartField` | Defines the start date of a task. |
44+
| `TitleField` | Defines whats the title of a task in percentages. |
4045

4146
## Data Bindings
4247

4348
The properties of a Gantt Tree item match directly to a field of the model the treelist is bound to. Provide that relationship by providing the name of the field from which the corresponding information is to be taken. To do this, in the main `TelerikGantt` tag, use the parameters described below:
4449

45-
* IdField => Id
46-
* ParentIdField => ParentId
50+
* EndField => End
4751
* HasChildrenField => HasChildren
52+
* IdField => Id
4853
* ItemsField => Items
54+
* ParentIdField => ParentId
55+
* PercentCompleteField => PercentComplete
56+
* StartField => Start
57+
* TitleField => Title
4958

5059
## Notes
5160

components/gantt/gantt-tree/editing/popup.md

Lines changed: 204 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -19,90 +19,166 @@ In this article:
1919

2020
Popup editing lets the user click an [Edit command button]({%slug components/grid/columns/command%}) on the row, and a popup shows up with the editable fields associated with a Gantt Task. They can then click the `Save` button in the dialog to submit the changes to the model. This fires the `OnUpdate` event where your code receives the updated model so you can work with the data (for example, to call the appropriate method of your service).
2121

22-
In a similar fashion, the `Cancel`, `Delete` command buttons and the `Add` toolbar button fire events to let you handle the data source operations.
22+
In a similar fashion, the `Cancel` and `Delete` command buttons and the `Add` toolbar button fire events to let you handle the data source operations.
2323

2424
You can also cancel the events by setting the `IsCancelled` property of the event arguments to `true`. This lets you prevent the user from editing certain records, inserting or deleting items, based on your application logic.
2525

2626
To enable Popup editing in the Gantt Tree, set its `TreeListEditMode` property to `GanttTreeListEditMode.Popup`, then handle the CRUD events as shown in the example below.
2727

28+
The popup editing dialog renders up to four tabs that allow you to edit:
29+
30+
* `General`—The fields that are used in the [data-binding schema]({%slug gantt-data-binding-overview%}#gantt-tree-item-features).
31+
* `Other`—The fields that are not included in the [data-binding schema]({%slug gantt-data-binding-overview%}#gantt-tree-item-features) but are present in the bound model.
32+
* `Predecessor` and `Successor` - render if you have defined [dependencies]({%slug gantt-dependencies-overview%}) in the Gantt component. You can use these tabs as an alternative to the standard [dependency editing]({%slug gantt-dependencies-editing%})
33+
34+
## Event Arguments
35+
36+
In Telerik UI for Blazor version 4.5.0, the `GanttUpdateEventArgs` received three new collections as fields. They are populated when you define [Dependencies]({%slug gantt-dependencies-overview%}) in the Gantt.
37+
38+
| Field | Type | Description |
39+
|----------|----------|----------|
40+
| `CreatedDependencies` | `List<GanttDependencyDescriptor>` | A collection of the newly created dependencies. |
41+
| `UpdatedDependencies` | `List<GanttDependencyDescriptor>` | A collection of the updated dependencies. |
42+
| `DeletedDependencies` | `List<GanttDependencyDescriptor>` | A collection of the deleted dependencies. |
43+
44+
### GanttDependencyDescriptor
45+
46+
The `GanttDependencyDescriptor` exposes four fields that describe the mutated dependency:
47+
48+
| Field | Type | Description |
49+
|----------|----------|----------|
50+
| `PredecessorId` | `object` | The Id of the predecessor of the mutated dependency. |
51+
| `SuccessorId` | `object` | The Id of the successor of the mutated dependency. |
52+
| `Type` | `int` | The [Type]({%slug gantt-dependencies-types%}) of the dependency. |
53+
| `DataItem` | `object` | The model associated with this dependency. |
2854

2955
>caption The Command buttons and the Gantt events let you handle data operations in Popup edit mode.
3056
3157
````CSHTML
32-
<TelerikGantt Data="@Data"
33-
Width="1200px"
58+
@using System.Collections.Generic
59+
@using System.ComponentModel.DataAnnotations;
60+
61+
<TelerikGantt @ref="@GanttRef"
62+
Data="@Data"
63+
Width="100%"
3464
Height="600px"
3565
IdField="Id"
3666
ParentIdField="ParentId"
3767
TreeListEditMode="@GanttTreeListEditMode.Popup"
3868
OnUpdate="@UpdateItem"
3969
OnDelete="@DeleteItem"
40-
OnCreate="@CreateItem">
70+
OnCreate="@CreateItem"
71+
Sortable="true"
72+
SortMode="@SortMode.Multiple"
73+
FilterMode="@GanttFilterMode.FilterMenu"
74+
FilterMenuType="@FilterMenuType.Menu">
75+
<GanttToolBarTemplate>
76+
<GanttCommandButton Command="Add" Icon="@SvgIcon.Plus">Add</GanttCommandButton>
77+
</GanttToolBarTemplate>
4178
<GanttViews>
42-
<GanttDayView></GanttDayView>
4379
<GanttWeekView></GanttWeekView>
4480
<GanttMonthView></GanttMonthView>
4581
<GanttYearView></GanttYearView>
4682
</GanttViews>
83+
@*If you remove/comment the dependencies the Predecessor and Successor tabs in the popup editing dialog will dissapear.*@
84+
<GanttDependenciesSettings>
85+
<GanttDependencies Data="@Dependencies"
86+
PredecessorIdField="PredecessorId"
87+
SuccessorIdField="SuccessorId"
88+
TypeField="Type"
89+
OnCreate="@CreateDependency"
90+
OnDelete="@DeleteDependency">
91+
</GanttDependencies>
92+
</GanttDependenciesSettings>
4793
<GanttColumns>
48-
<GanttCommandColumn Width="110px">
49-
<GanttCommandButton Command="Add" Icon="@FontIcon.Plus"></GanttCommandButton>
50-
<GanttCommandButton Command="Edit" Icon="@FontIcon.Pencil"></GanttCommandButton>
51-
<GanttCommandButton Command="Delete" Icon="@FontIcon.Trash"></GanttCommandButton>
94+
<GanttCommandColumn Width="120px">
95+
<GanttCommandButton Command="Add" Icon="@SvgIcon.Plus"></GanttCommandButton>
96+
<GanttCommandButton Command="Edit" Icon="@SvgIcon.Pencil"></GanttCommandButton>
97+
<GanttCommandButton Command="Delete" Icon="@SvgIcon.Trash"></GanttCommandButton>
5298
</GanttCommandColumn>
53-
<GanttColumn Field="Id"
54-
Visible="false">
99+
<GanttColumn Field="@nameof(FlatModel.Id)"
100+
Editable="false"
101+
Width="40px">
55102
</GanttColumn>
56-
<GanttColumn Field="Title"
103+
<GanttColumn Field="@nameof(FlatModel.Title)"
57104
Expandable="true"
58105
Width="160px"
59-
Title="Task Title" >
106+
Title="Task Title">
60107
</GanttColumn>
61-
<GanttColumn Field="PercentComplete"
62-
Width="60px">
108+
<GanttColumn Field="@nameof(FlatModel.PercentComplete)"
109+
Width="100px">
63110
</GanttColumn>
64-
<GanttColumn Field="Start"
111+
<GanttColumn Field="@nameof(FlatModel.Start)"
65112
Width="100px"
66113
TextAlign="@ColumnTextAlign.Right">
67114
</GanttColumn>
68-
<GanttColumn Field="End"
115+
<GanttColumn Field="@nameof(FlatModel.End)"
69116
DisplayFormat="End: {0:d}"
70117
Width="100px">
71118
</GanttColumn>
119+
<GanttColumn Field="@nameof(FlatModel.Text)"
120+
Width="100px">
121+
</GanttColumn>
122+
<GanttColumn Field="@nameof(FlatModel.Bool)"
123+
Width="100px">
124+
</GanttColumn>
125+
<GanttColumn Field="@nameof(FlatModel.Number)"
126+
Width="100px">
127+
</GanttColumn>
128+
<GanttColumn Field="@nameof(FlatModel.Date)"
129+
Width="100px">
130+
</GanttColumn>
72131
</GanttColumns>
73132
</TelerikGantt>
74133
75134
@code {
135+
private TelerikGantt<FlatModel> GanttRef;
76136
public DateTime SelectedDate { get; set; } = new DateTime(2019, 11, 11, 6, 0, 0);
77137
78138
class FlatModel
79139
{
140+
//Fields editable in the General tab
80141
public int Id { get; set; }
81142
public int? ParentId { get; set; }
143+
[Required]
82144
public string Title { get; set; }
83145
public double PercentComplete { get; set; }
84146
public DateTime Start { get; set; }
85147
public DateTime End { get; set; }
148+
//Fields editable in the Others tab
149+
public string Text { get; set; }
150+
public bool Bool { get; set; }
151+
public int Number { get; set; }
152+
public DateTime Date { get; set; }
153+
}
154+
155+
class DependencyModel
156+
{
157+
public int Id { get; set; }
158+
public int PredecessorId { get; set; }
159+
public int SuccessorId { get; set; }
160+
public int Type { get; set; }
86161
}
87162
88163
public int LastId { get; set; } = 1;
164+
public int LastDependencyId { get; set; } = 1;
89165
List<FlatModel> Data { get; set; }
166+
List<DependencyModel> Dependencies { get; set; } = new List<DependencyModel>();
90167
91168
protected override void OnInitialized()
92169
{
93170
Data = new List<FlatModel>();
94-
var random = new Random();
95171
96172
for (int i = 1; i < 6; i++)
97173
{
98174
var newItem = new FlatModel()
99-
{
100-
Id = LastId,
101-
Title = "Employee " + i.ToString(),
102-
Start = new DateTime(2020, 12, 6 + i),
103-
End = new DateTime(2020, 12, 11 + i),
104-
PercentComplete = Math.Round(random.NextDouble(), 2)
105-
};
175+
{
176+
Id = LastId,
177+
Title = "Employee " + i.ToString(),
178+
Start = new DateTime(2020, 12, 6 + i),
179+
End = new DateTime(2020, 12, 11 + i),
180+
PercentComplete = i * 0.125
181+
};
106182
107183
Data.Add(newItem);
108184
var parentId = LastId;
@@ -111,23 +187,57 @@ To enable Popup editing in the Gantt Tree, set its `TreeListEditMode` property t
111187
for (int j = 0; j < 5; j++)
112188
{
113189
Data.Add(new FlatModel()
114-
{
115-
Id = LastId,
116-
ParentId = parentId,
117-
Title = " Employee " + i + " : " + j.ToString(),
118-
Start = new DateTime(2020, 12, 6 + i + j),
119-
End = new DateTime(2020, 12, 7 + i + j),
120-
PercentComplete = Math.Round(random.NextDouble(), 2)
121-
});
190+
{
191+
Id = LastId,
192+
ParentId = parentId,
193+
Title = " Employee " + i + " : " + j.ToString(),
194+
Start = new DateTime(2020, 12, 6 + i + j),
195+
End = new DateTime(2020, 12, 7 + i + j),
196+
PercentComplete = j * 0.225
197+
});
122198
123199
LastId++;
124200
}
125201
}
126202
203+
Dependencies.Add(new DependencyModel()
204+
{
205+
Id = LastDependencyId++,
206+
PredecessorId = 3,
207+
SuccessorId = 4,
208+
Type = 0
209+
});
210+
211+
Dependencies.Add(new DependencyModel()
212+
{
213+
Id = LastDependencyId++,
214+
PredecessorId = 2,
215+
SuccessorId = 5,
216+
Type = 2
217+
});
218+
127219
base.OnInitialized();
128220
}
129221
130-
private async Task CreateItem(GanttCreateEventArgs args)
222+
private void CreateDependency(GanttDependencyCreateEventArgs args)
223+
{
224+
var dependency = new DependencyModel()
225+
{
226+
Id = LastDependencyId++,
227+
PredecessorId = (int)args.PredecessorId,
228+
SuccessorId = (int)args.SuccessorId,
229+
Type = args.Type
230+
};
231+
232+
Dependencies.Add(dependency);
233+
}
234+
235+
private void DeleteDependency(GanttDependencyDeleteEventArgs args)
236+
{
237+
Dependencies.RemoveAll(d => d.Id.Equals((args.Item as DependencyModel).Id));
238+
}
239+
240+
private void CreateItem(GanttCreateEventArgs args)
131241
{
132242
var argsItem = args.Item as FlatModel;
133243
@@ -146,11 +256,12 @@ To enable Popup editing in the Gantt Tree, set its `TreeListEditMode` property t
146256
CalculateParentRangeRecursive(argsItem);
147257
}
148258
149-
private async Task UpdateItem(GanttUpdateEventArgs args)
259+
private void UpdateItem(GanttUpdateEventArgs args)
150260
{
151261
var item = args.Item as FlatModel;
152-
262+
var parentItem = args.ParentItem as FlatModel;
153263
var foundItem = Data.FirstOrDefault(i => i.Id.Equals(item.Id));
264+
var foundParent = Data.FirstOrDefault(i => i.Id.Equals(parentItem?.Id));
154265
155266
if (foundItem != null)
156267
{
@@ -164,13 +275,69 @@ To enable Popup editing in the Gantt Tree, set its `TreeListEditMode` property t
164275
foundItem.Start = item.Start;
165276
foundItem.End = item.End;
166277
foundItem.PercentComplete = item.PercentComplete;
278+
279+
// update parent
280+
if (foundItem.ParentId != foundParent?.Id)
281+
{
282+
foundItem.ParentId = foundParent?.Id;
283+
}
284+
285+
//update custom properties
286+
foundItem.Text = item.Text;
287+
foundItem.Bool = item.Bool;
288+
foundItem.Number = item.Number;
289+
foundItem.Date = item.Date;
167290
}
168291
292+
// update dependencies
293+
UpdateDependencies(args);
294+
169295
CalculateParentPercentRecursive(foundItem);
170296
CalculateParentRangeRecursive(foundItem);
171297
}
172298
173-
private async Task DeleteItem(GanttDeleteEventArgs args)
299+
private void UpdateDependencies(GanttUpdateEventArgs args)
300+
{
301+
// add newly created dependencies
302+
args?.CreatedDependencies?.ForEach(x =>
303+
{
304+
var dependency = new DependencyModel()
305+
{
306+
Id = LastDependencyId++,
307+
PredecessorId = (int)x.PredecessorId,
308+
SuccessorId = (int)x.SuccessorId,
309+
Type = x.Type
310+
};
311+
312+
Dependencies.Add(dependency);
313+
});
314+
315+
// update modified dependencies
316+
args?.UpdatedDependencies?.ForEach(x =>
317+
{
318+
var dependency = GetDependencyDataItemByDescriptor(x);
319+
320+
dependency.SuccessorId = (int)x.SuccessorId;
321+
dependency.PredecessorId = (int)x.PredecessorId;
322+
dependency.Type = x.Type;
323+
324+
});
325+
326+
// remove deleted dependencies
327+
args?.DeletedDependencies?.ForEach(x =>
328+
{
329+
var dependency = GetDependencyDataItemByDescriptor(x);
330+
331+
Dependencies.Remove(dependency);
332+
});
333+
334+
DependencyModel GetDependencyDataItemByDescriptor(DependencyDescriptor descriptor)
335+
{
336+
return Dependencies.FirstOrDefault(dep => dep.Id == (descriptor.DataItem as DependencyModel).Id);
337+
}
338+
}
339+
340+
private void DeleteItem(GanttDeleteEventArgs args)
174341
{
175342
var item = Data.FirstOrDefault(i => i.Id.Equals((args.Item as FlatModel).Id));
176343

0 commit comments

Comments
 (0)