Our state of the art Gantt chart


Post by awendt »

We tested the following code through the code editor on the Bryntum examples:

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

class MavenDependency extends DependencyModel {
    static get fields(){
        return [{ name: 'active', defaultValue: false }]
    }
}

const project = new ProjectModel({
    dependencyModelClass: MavenDependency,
    transport : {
        load : {
            url : '../_datasets/launch-saas.json'
        }
    },
});


new Gantt({
    appendTo : 'container',
    project,
    columns : [{ type : 'name' }],
});

project.load();

The line that sets dependencies to be inactive appears to cause an issue. It allows users to draw a dependency from a child task to its parent; without that line of code that situation is considered invalid.

We think that drawing a dependency from a child to its parent in this way should always be invalid.

We've attached a video of this issue.

Attachments
invalidDependency.mov
(4.76 MiB) Downloaded 82 times

Post by arcady »

This is by design inactive dependencies are pure visual things so they don't cause cycles.

Yet you can easily extend standard validation the way you want. It should be pretty trivial. Just override isValidDependency method:

class MyDependencyModel extends DependencyModel {
    static get fields() {
        return [{ name : 'active', defaultValue : false }];
    }
}

class MyDependencyStore extends DependencyStore {

    isValidDependency(from, to) {
        // always treat parent-child dependencies as invalid
        if (from.isTaskModel && to.isTaskModel && (from.contains(to) || to.contains(from))) {
            return false;
        }

        return super.isValidDependency(...arguments);
    }

};

new Gantt({
    project : {
        dependencyModelClass : MyDependencyModel,
        dependencyStoreClass : MyDependencyStore,

Post by awendt »

With the dependencies inactive if I draw a dependency from a parent to a child it still says it is invalid. Why would that be invalid but when I draw a dependency from a child to parent it is valid? Especially if as you said above: This is by design inactive dependencies are pure visual things so they don't cause cycles.

Also what if the customer decides to activate the dependencies (which we allow our users to do) wouldn't the dependencies be incorrect and cause cycles? I don't quite understand the benefit of purely visual dependencies that would never actually work.


Post by arcady »

With the dependencies inactive if I draw a dependency from a parent to a child it still says it is invalid. Why would that be invalid but when I draw a dependency from a child to parent it is valid?

First of all there is a bug in active field implementation in that version of the Gantt: the active field is not taken into account when calculating task late start/end dates. That's why you see invalid indicator at all.
And it's not symmetrical as you noted. When calculating late dates:
1) child late restrictions depend on parent late restrictions
2) if parent has an outgoing link to the child then it depends on the child restriction
That's the cycle. There is no cycle when you link child->parent ..since for calculating late dates dependencies are processed backwards:
1) child late restrictions depend on parent late restrictions
2) if child has an outgoing link to the parent then again child depends on the parent restriction

Also what if the customer decides to activate the dependencies (which we allow our users to do) wouldn't the dependencies be incorrect and cause cycles? I don't quite understand the benefit of purely visual dependencies that would never actually work.

There is a new UI coming in the next major release that will inform users on invalid cases: cycles, scheduling conflicts and calendar misconfigurations. When handling cycles it will suggest to either remove or deactivate a dependency that takes part in the cycle.


Post by awendt »

Cool, thank you!


Post by awendt »

Hello again, inactive invalid dependencies are causing an issue for us again. For context, when we load up the gantt chart we set all dependencies to be inactive by default in order to allow the dates to appear in the gantt chart matching another tool we have in the application. When a user edits/creates a dependency or edits dates on a task we then activate the associated dependencies so that the changes cascade in the way that's expected. Therefore, we need our users to be stopped from creating invalid dependencies even when the dependencies are inactive. Any suggestions on how best to do this?

I've also attached a video of the most recent bug we had reported to us related to this. When a user tries to change a predecessor to a task that would cause a cycle it appears that the UI reverts back from the users edit to the valid dependency. However after that point the user cannot edit that cell any longer, they can't even delete the dependency. Additionally when the user tries to delete that same task an error shows up in the console and on refresh it appears that the task has not been deleted.

Attachments
cyclic dependencies.mov
(11.74 MiB) Downloaded 50 times

Post by arcady »

I've already mentioned isValidDependency method which decides if a dependency is valid. So implement there a custom logic you need.

Regarding the issue in the video we need a test case so we could reproduce the problem and debug it.


Post by awendt »

From what I've been able to tell isValidDependency only gets called when you draw a dependency in the schedule view. It doesn't appear to be invoked when you edit dependencies through the predecessor/successor columns


Post by arcady »

Yes the columns use the project isValidDependency directly. Dependency store also calls this method internally.


Post Reply