Our state of the art Gantt chart


Post by Jerther »

Hi!

I tried to follow this post here to filter the resource available in the combo of the resource grid but in this event, the combo store is undefined so I can't set a filter on it:

new Gantt({
    listeners : {
        beforeTaskEditShow({ taskEdit, editor }) {
            let resourceCombo = editor.widgetMap.resourcestab.resourceCombo;
            console.debug(resourceCombo.store);  // THIS IS UNDEFINED
        }
    },
...

What I need is to have the combo present a prefiltered list of resources, that is resources that can be manually assigned. This is a custom condition which could look somethong like this:

resource.allowManualAssignment == true

Gantt v2.1.1 and 2.1.2

Thanks!


Post by mats »

Ticket opened, will be fixed for the next release. Thanks for reporting :)

https://github.com/bryntum/support/issues/567

Post by Jerther »

Thanks Mats!

Post by Jerther »

I noticed the fix was not included in 2.1.3 but I tried anyway and as expected the problem's still there.

Is there a workaround to this? I mean, the combo store has to exist somewhere so is there another way to reach it?

Post by mats »

We're still working on it, you can try listening for the 'show' event of the TaskEditor and query for the Combo instance to manipulate it. We hope to offer a clean way of doing this soon.

Post by Jerther »

class TaskEditor extends this.bryntumGantt.TaskEditor {
    onBeforeShow({source: editor}) {
        const resourcesStore = editor.widgetMap.resourcestab.resourceCombo.store;
        resourcesStore.filter(r => false);
    }
}
That should filter out everything but it doesn't.

This does not work either:
class TaskEditor extends this.bryntumGantt.TaskEditor {
    show() {
        const store = this.widgetMap.resourcestab.resourceCombo.store;

        return super.show().then(() => {
            store.filter(r => false);
        });
    }
}
filterBy() does not work either.

Should this work?

Post by mats »

Your second approach should work, it works fine for me (just tested). What version are you on? Please upload a full test case?

Post by Jerther »

Wow I just found out that the problem is caused by an onchange handler on an extra widget, where I call tab.requestPropagation(). Here's a simplified version:

class MyTaskEditor extends TaskEditor {
    onBeforeShow({source: editor}) {
        const resourcesStore = editor.widgetMap.resourcestab.resourceCombo.store;
        resourcesStore.filter(r => false);
    }
}

window.gantt = new Gantt({
    adopt : document.body,
    project : project,
    features: {
        taskEdit: { 
            editorClass: MyTaskEditor,
        }
    },
    listeners: {
        beforeTaskEditShow({taskEdit, taskRecord, editor}) {
            const tab = editor.widgetMap.resourcestab;
            const container = editor.widgetMap.resourcestab.items[0];
            const [resourceGroupUnits] = container.add([
                {
                    type  : 'number',
                    name: 'effort',
                    ref: 'effort2',
                    onChange({ source : number, value }) {
                        const project = tab.getProject();
                        if (number.isValid && project && !project.isPropagating()) {
                            tab.requestPropagation();
                        }
                    }
                }
            ]);
        }
    }

});

project.load();

All resources should be filtered out, but they aren't. If you comment out the tab.requestPropagation() line then the filter works fine.

Anyway that line shouldn't execute at loading so I just add the userAction condition:

onChange({ source : number, value, userAction }) {
    const project = tab.getProject();
    if (number.isValid && project && !project.isPropagating() && userAction) {
        tab.requestPropagation();
    }
}

and the filter works as expected UNTIL I do change the field, and then the filter goes out the window.


Post by mats »

Can you please upload something complete that we can run / inspect?


Post by Jerther »

Better yet, just load the Basic demo, and change the code to this:

import { Gantt, ProjectModel, Toast, EffectResolutionResult, TaskEditor } from '../../build/gantt.module.js?441632';
import shared from '../_shared/shared.module.js?441632';
/* eslint-disable no-unused-vars */

const project = new ProjectModel({
    transport : {
        load : {
            url : '../_datasets/launch-saas.json'
        }
    },
    listeners : {
        // let's track scheduling conflicts happened
        schedulingconflict : context => {
            // show notification to user
            Toast.show('Scheduling conflict has happened ..recent changes were reverted');
            // as the conflict resolution approach let's simply cancel the changes
            context.continueWithResolutionResult(EffectResolutionResult.Cancel);
        }
    }
});

class MyTaskEditor extends TaskEditor {
    onBeforeShow({source: editor}) {
        const resourcesStore = editor.widgetMap.resourcestab.resourceCombo.store;
        resourcesStore.filter(r => false);
    }
}

new Gantt({
    adopt : 'container',
    project : project,
    features: {
        taskEdit: { 
            editorClass: MyTaskEditor,
        }
    },
    listeners: {
        beforeTaskEditShow({taskEdit, taskRecord, editor}) {
            const tab = editor.widgetMap.resourcestab;
            const container = editor.widgetMap.resourcestab.items[0];
            const [resourceGroupUnits] = container.add([
                {
                    type  : 'number',
                    name: 'effort',
                    ref: 'effort2',
                    onChange({ source : number, value, userAction }) {
                        const project = tab.getProject();
                        if (number.isValid && project && !project.isPropagating() && userAction) {
                            tab.requestPropagation();
                        }
                    }
                }
            ]);
        }
    }

});

project.load();

And here are the steps:

  • Edit a task, go to the resources tab
  • Don't mind the extra field yet, but do add a new resource and expand the resource dropdown
  • There are no resources and that indicates the filter works.
  • Change the value of the extra field above, or just hit one of its arrows so its onChange event triggers.
  • Expand the same resource dropdown

Result:

  • All resources are shown. The filter does not work anymore

Expected:

  • No resources are shown indicating the filter still works.

Additional info:
It looks like the problem is caused by tab.requestPropagation().


Post Reply