Gantt Filtering with CustomAdapter
HI!
When using DataAdaptor filtering function
because of the the initial filtering (ParentId equal null) only top record visible the Chart.
if we disable the filtering function-> all record visibled, but the column filtering not working:
What is the best solution so that all items are visible and the filtering works?
Hi Szoke,
Greetings
from Syncfusion Support.
We are able to replicate the problem. In order to overcome this, we recommend
using a custom adapter and a FilterTemplate to achieve the desired
outcome. In your case, since the column type is string, the filter template can
be utilized. We have provided a sample filter with child records attached for
your reference.
|
<SfGantt …..> <GanttColumns> <GanttColumn Field="TaskID" HeaderText="Task ID" IsPrimaryKey="true" Width="80" TextAlign="TextAlign.Right"></TreeGridColumn> <GanttColumn Field="TaskName" HeaderText="Task Name" Width="145"> <FilterTemplate> <SfDropDownList Placeholder="TaskName" ID="TaskName" @bind-Value="@((context as PredicateModel<string?>).Value)" TItem="SelfReferenceData" TValue="string?" DataSource="@(TreeData)"> <DropDownListFieldSettings Value="TaskName" Text="TaskName"></DropDownListFieldSettings> </SfDropDownList> </FilterTemplate> </GanttColumn> …. </SfGantt>
@code { public static List<SelfReferenceData> GanttData { get; set; } public static List<SelfReferenceData> FilteredData = new List<SelfReferenceData>(); public static int? filterCount; public double ID { get; set; } = 10; protected override void OnInitialized() { // SelfReferenceData data = new SelfReferenceData(); GanttData = GetTree().ToList(); }
// Implementing custom adaptor by extending the DataAdaptor class public class CustomAdaptor : DataAdaptor { // Performs data Read operation public override object Read(DataManagerRequest dm, string key = null) { IEnumerable<SelfReferenceData> DataSource = GanttData; if (dm.Search != null && dm.Search.Count > 0) { // Searching DataSource = DataOperations.PerformSearching(DataSource, dm.Search); } if (dm.Sorted != null && dm.Sorted.Count > 0) { // Sorting DataSource = DataOperations.PerformSorting(DataSource, dm.Sorted); } if (dm.Where != null && dm.Where.Count > 0) { // Filtering if (dm.Where[0].Field != null && dm.Where[0].Field == "ParentID") {
} else { DataSource = DataOperations.PerformFiltering(DataSource, dm.Where, dm.Where[0].Operator); } } int count = DataSource.Cast<SelfReferenceData>().Count(); if (dm.Skip != 0) { //Paging DataSource = DataOperations.PerformSkip(DataSource, dm.Skip); } if (dm.Take != 0) { DataSource = DataOperations.PerformTake(DataSource, dm.Take); } if (dm.Where != null && dm.Where.Count > 0) { if (dm.Where[0].Field == null) { FilteredData.Clear();
filterCount = 0; //for filterhierarchy mode as "parent"(default mode), we need to return the parent record of the filtered record along with the actual filtered record //calling filterhierarchydata to collect the parent data of filtered data by passing filtered data and complete data source as params FilteredData = FilterHierarchyData(DataSource); DataSource = FilteredData; // assigning new list to datasource and returning } } count = filterCount != null ? FilteredData.Count : count; return dm.RequiresCounts ? new DataResult() { Result = DataSource, Count = count } : (object)DataSource; }
public List<SelfReferenceData> FilterHierarchyData(IEnumerable<SelfReferenceData> filterData) { foreach (var data in filterData) { if (data.ParentID != null) { FilteredData = FilterData(data); // calling FilterData method to add parent to new list } FilteredData.Add(data);//adding filtered data to list } return FilteredData; }
public List<SelfReferenceData> FilterData(SelfReferenceData data) { var parent = GanttData.Where(p => p.TaskID == data.ParentID).FirstOrDefault(); if (parent.ParentID != null) { FilteredData = FilterData(parent); FilteredData.Add(parent); } else { var alreadyPresent = FilteredData.FindIndex(d => d.TaskID == parent.TaskID); if (alreadyPresent == -1)// if parent is not present already, then add parent to list { FilteredData.Add(parent); filterCount++; //adding parent data to list
} } return FilteredData; } }
|
https://www.syncfusion.com/downloads/support/directtrac/general/ze/Adaptor_(1)-1527209894
Additionally, you can refer to the GitHub sample link for further information
on performing CRUD operations.
https://www.syncfusion.com/downloads/support/directtrac/general/ze/Adaptor145135410
https://github.com/SyncfusionExamples/Gantt-Chart-Custom-Adaptor-sample-using-Blazor-server-application
Please note that by implementing the custom adapter and utilizing the filter
template, you will be able to have all items visible while still maintaining
the functionality of filtering.
Regards,
Ajithkumar G
HI Ajithkumar !
Thank you for your help !
Another question:
How can I save the order of the Gantt tasks, so that they appear in that order the next time I reload?
For example:
From the task in the original order, I move task 56 below task 53.
I would like to save this order(in the database) so that it will appear this way the next time it is loaded.
What can be the solution?
Thank you in advance for your help!
Hi Szoke,
We have reviewed your query. To save the order of Gantt tasks and have them
appear in the same order upon reloading, we suggest using the dropping event.
This event can be used to update the local list of data with the new task
order. We have prepared a code snippet and sample to demonstrate this approach.
|
<GanttEvents RowDropping="RowDroppingHandler" TValue="SelfReferenceData"></GanttEvents> |
|
// Event that is triggered when a row is being dropping private void RowDroppingHandler(Syncfusion.Blazor.Grids.RowDroppingEventArgs<SelfReferenceData> args) { var position = args.Target.ID; // drop position var dropIndex = Convert.ToInt32(args.DropIndex); // drop index var targetDataID = GanttChart.GetCurrentViewRecords()[dropIndex].TaskID; // drop index data's TaskId var targetData = GanttData.Where(ds => ds.TaskID == targetDataID).FirstOrDefault(); var index = Convert.ToInt32(args.DropIndex); // drop index if (position == " e-droptop" || position == " e-dropbottom") // if a record is dropped below/above another record { if (args.Data[0].ParentID != null) // if dragged record has parent { var childCount = 0; int parent1 = (int)args.Data[0].ParentID; childCount += GetChildRecordsCount(parent1); // finding the number of child for dragged record's parent if (childCount == 1) // if the dragged record is the only child for a particular record { var i = 0; for (; i < GanttData.Count; i++) { if (GanttData[i].TaskID == parent1) { break; } if (GanttData[i].TaskID == args.Data[0].TaskID) { //set parentItem of dragged record to null GanttData[i].ParentID = null; break; } } } } var data = GanttData.Where(ds => ds.TaskID == args.Data[0].TaskID).FirstOrDefault(); //removing dragged record from list GanttData.Remove(GanttData.Where(ds => ds.TaskID == args.Data[0].TaskID).FirstOrDefault()); data.ParentID = targetData.ParentID; //setting the dropIndex data's parent as parent of dragged record
if (position == " e-dropbottom") // if a record is dropped below another record { index = GanttData.IndexOf(targetData); index = index + 1; GanttData.Insert(index, data); } else if (position == " e-droptop") // if a record is dropped above another record { index = GanttData.IndexOf(targetData); index = index + GetChildRecordsCount(targetDataID); // find the target record's children count to find drop index GanttData.Insert(index, data); } }
else if (position == " e-dropchild") // if a record is dropped as child to another record(middle segment) { var data = GanttData.Where(ds => ds.TaskID == args.Data[0].TaskID).FirstOrDefault(); var dropData = GanttData.Where(ds => ds.TaskID == targetDataID).FirstOrDefault(); // removing dragged record from list GanttData.Remove(GanttData.Where(ds => ds.TaskID == args.Data[0].TaskID).FirstOrDefault()); data.ParentID = targetDataID; //setting the dropIndex data's ID as parent of dragged record index = index + 1; GanttData.Insert(index, data); } GanttData = Gantt = GanttData.ToList(); } |
Sample link: https://www.syncfusion.com/downloads/support/directtrac/general/ze/Adaptor1071812700
If you have any further concerns or require additional details, please
feel free to share them with us.
Regards,
Ajithkumar G
Dear Ajithkumar
We use this drag&drop method.
The problem is that not only this can change the order of the Tasks, but e.g. Also on Abow, Below, Child Tasks added from the context menu.
How should these changes be handled in terms of the order set by Task?
Hi Szoke,
Query#1:
We use this drag&drop method.
Query#2: The problem is that not only this can change the order of the
Tasks, but e.g. Also on Abow, Below, Child Tasks added from the context menu.
To achieve this, we can use the actionbegin event. This event can be
used to update the local list of data with the new task order. We have prepared
a sample and attached it along with a code snippet for your reference.
|
public override object Insert(DataManager dm, object value, string key) { GanttData.Insert(0, value as SelfReferenceData); Gantt = GanttData.ToList(); return value; } |
|
<Syncfusion.Blazor.Buttons.SfButton OnClick="ReOrder">Reorder</Syncfusion.Blazor.Buttons.SfButton> { GanttChart.ReorderRowAsync(4, 3, "Above"); } |
|
public void actionBegin(GanttActionEventArgs<SelfReferenceData> args) { //Here, you can customize your code. if (args.RequestType == Syncfusion.Blazor.Gantt.Action.RowDragAndDrop) { var position = "Above"; // drop position var dropIndex = 3; // drop index var fromIndex = 4; // from index var targetDataID = GanttChart.GetCurrentViewRecords()[dropIndex].TaskID; // drop index data's TaskId var targetData = GanttData.Where(ds => ds.TaskID == targetDataID).FirstOrDefault(); var targettingID = GanttChart.GetCurrentViewRecords()[fromIndex].TaskID; // drop index data's TaskId var targettingData = GanttData.Where(ds => ds.TaskID == targettingID).FirstOrDefault(); var index = 3; // drop index if (position == "Above" || position == "Below") // if a record is dropped below/above another record { if (targettingData.ParentID != null) // if dragged record has parent { var childCount = 0; int parent1 = (int)targettingData.ParentID; childCount += GetChildRecordsCount(parent1); // finding the number of child for dragged record's parent if (childCount == 1) // if the dragged record is the only child for a particular record { var i = 0; for (; i < GanttData.Count; i++) { if (GanttData[i].TaskID == parent1) { break; } if (GanttData[i].TaskID == targettingData.TaskID) { //set parentItem of dragged record to null GanttData[i].ParentID = null; break; } } } } var data = GanttData.Where(ds => ds.TaskID == targettingData.TaskID).FirstOrDefault(); //removing dragged record from list GanttData.Remove(GanttData.Where(ds => ds.TaskID == targettingData.TaskID).FirstOrDefault()); data.ParentID = targetData.ParentID; //setting the dropIndex data's parent as parent of dragged record
if (position == "Below") // if a record is dropped below another record { index = GanttData.IndexOf(targetData); index = index + 1; GanttData.Insert(index, data); } else if (position == "Above") // if a record is dropped above another record { index = GanttData.IndexOf(targetData); index = index + GetChildRecordsCount(targetDataID); // find the target record's children count to find drop index GanttData.Insert(index, data); } }
else if (position == "Child") // if a record is dropped as child to another record(middle segment) { var data = GanttData.Where(ds => ds.TaskID == targettingData.TaskID).FirstOrDefault(); var dropData = GanttData.Where(ds => ds.TaskID == targetDataID).FirstOrDefault(); // removing dragged record from list GanttData.Remove(GanttData.Where(ds => ds.TaskID == targettingData.TaskID).FirstOrDefault()); data.ParentID = targetDataID; //setting the dropIndex data's ID as parent of dragged record index = index + 1; GanttData.Insert(index, data); } GanttData = Gantt = GanttData.ToList(); } } |
Sample link: https://www.syncfusion.com/downloads/support/directtrac/general/ze/Adaptor-1999265781
Regards,
Ajithkumar G
- 5 Replies
- 2 Participants
-
SZ Szoke
- May 25, 2023 08:08 PM UTC
- Jun 12, 2023 03:36 PM UTC