rabix/cwl-svg

Having trouble with the new API

multimeric opened this issue · 6 comments

Hi all, I've been playing around with this library and I've noticed that the API has changed significantly from the README. I'm hoping to render just a very basic workflow, and so I've got something like this:

import "cwl-svg/src/assets/styles/themes/rabix-dark/theme.scss";
import {WorkflowFactory, WorkflowModel} from "cwlts/models";
import {SVGArrangePlugin, Workflow} from "cwl-svg";

const model = WorkflowFactory.from(json['$graph'][0]);
const workflow = new Workflow({
    editingEnabled: false,
    model,
    svgRoot: element,
    plugins:[new SVGArrangePlugin()]
});
workflow.fitToViewport();
workflow.draw();

However it just renders an SVG that looks like this:
image

I'm probably missing some key steps. For starters I have no idea how to use plugins. Could I have some pointers?

Hey @TMiguelT, sorry to keep you waiting.
Yes, the API is changed for the 2.0 version, I just updated README with a new example.

Here are the key differences:

  • Rewritten to be based on plugins. Base render is now non-interactive. All interactions are made as separate plugins, so you can cherry pick, tweak or add your own. All previously existing interactions are now made as plugins and bundled with the project.
  • Theming support for both base rendering and plugins. Light theme is default, dark theme is bundled.

In your example, something like this would probably work.

import "cwl-svg/src/assets/styles/themes/rabix-dark/theme.scss";
import {WorkflowFactory, WorkflowModel} from "cwlts/models";
import {SVGArrangePlugin, Workflow} from "cwl-svg";

const model = WorkflowFactory.from(json['$graph'][0]);
const arranger = new SVGArrangePlugin();

const workflow = new Workflow({
    editingEnabled: false,
    model,
    svgRoot: element,
    plugins:[arranger] // could also be created here by new SVGArrangePlugin() as it was
});
workflow.fitToViewport();
// workflow.draw(); // not needed anymore, called automatically

// SVGArrangePlugin will check if nodes already have positions assigned through sbg:x or sbg:y custom properties, and arrange immediately otherwise.

// You can call it afterwards again if you need to
workflow.getPlugin(SVGArrangePlugin).arrange()

// Or if you have an instance of the plugin available directly
arranger.arrange()

Let me know if this helps.

Thanks for updating the README, I'm sure many people will find it useful. One suggestion I have is that you might make this example work from outside the cwl-svg module; ie import * from "cwl-svg"; rather than doing a relative import.

Unfortunately it looks like your code isn't all that different to mine, so it doesn't actually resolve the issues I was having. It still renders all this text on top of each other. And actually the SVG element is black by default, so I can't initially see anything. Could you include some sample HTML/CSS to use with the code?

In order to do import * as Something from "cwl-svg", you would need to already have cwl-svg installed as a dependency of the code that's demoing it, meaning you can't keep the demo in the same repository. Relative imports don't make a difference, and including what you need is a better practice than including everything. We are doing exactly that in https://github.com/rabix/composer/blob/b47ccbf48f067cf3c2789a04aeb427dade1c6972/src/app/workflow-editor/graph-editor/graph-editor/workflow-graph-editor.component.ts#L16, for example.

Judging by the screenshot, I'm pretty sure that the CSS isn't loaded at all.
If you did npm install, you can run npm start and see the behavior.

That command will run Webpack with configuration from webpack.config.js and compile src/demo.ts.

In that example, webpack-dev-server will automatically parse Sass imports and inject them into the generated webpage.

If you are integrating the library into another project, it depends on the rest of your configuration.

I'm sure it can be configured to work with most build systems, but if I would assume that you are using Webpack, you'd either import sass files the same way as the demo is doing it and configure webpack to interpret them properly (with loaders, like in webpack config in this repo), or import them through Sass (https://github.com/rabix/composer/blob/344cf96b0669faad2115b67b0324854f35637d3a/src/assets/sass/main.scss#L14). Third option would be to compile .scss files in a separate pipeline of your choice, and inject it into the page as compiled css.

In order to do import * as Something from "cwl-svg", you would need to already have cwl-svg installed as a dependency of the code that's demoing it, meaning you can't keep the demo in the same repository.

True, but example code is usually designed for users of the code to be able to copy and paste, even if it makes it harder to use as a test. In any case, there are plugins that let you do this. You might even be able to do it by setting the resolve.modules in webpack.

Okay, I did some digging, and found index.html, which pointed out I needed class="cwl-workflow" on the root SVG element before anything would work, and also

{
        width: 100%;
        height: 100%;
        position: absolute;
}

on the same element made it a decent size.

Could you mention the cwl-workflow class in the readme please? It seems like it's a key part of the rendering.

In any case, it seems to be working quite well now, thanks for the help!

Yes, that's important, sorry that I missed to mention it. Thanks for suggestions, I added that bit to the README.
Regarding imports, you have a good point. Having an example that you can copy and paste is a bit more complicated than removing relative imports though, because making it work depends on how you build and write the rest of the project. You might use Grunt or Gulp, might not use Typescript, might use RequireJS, postCSS, Less or no processor at all, so having an example that you can copy/paste would assume a lot of context and strict environment in which it would work.

If you have the time or an idea on how to make an approachable example, I'd gladly accept a PR contribution.