stimulus-components / stimulus-chartjs

A Stimulus controller to deal with chart.js.
https://stimulus-chartjs.stimulus-components.com
MIT License
30 stars 5 forks source link

How to register ChartJs plugins #4

Open fidalgo opened 1 year ago

fidalgo commented 1 year ago

First of all, thank you for your work on these nifty plugins!

I was looking to incorporate ChartJs plugins to add more graph types.

Take the example from https://github.com/sgratzl/chartjs-chart-wordcloud

import { Chart } from 'chart.js';
import { WordCloudController, WordElement } from 'chartjs-chart-wordcloud';

Chart.register(WordCloudController, WordElement);

First, I cannot use Chart.register because Chart comes from the stimulus-controllers and not the original Chartjs package.

I sense we need to build a bridge register method between stimulus-chartjs and Chartjs, but my js-foo is not on that level.

Note: I understand that this is more of a support ticket, so feel free to close it if you think is not appropriate. I would appreciate though if you could point me to some docs, where I can achieve my goal.

marcusvy commented 1 year ago

Thank you for you work! Awesome.

How to register a ChartJS Plugin?

The Chart.register() method not working too for me. So I try to do a bridge with Stimullus and not working.

import { Controller } from '@hotwired/stimulus';

import autocolors from 'chartjs-plugin-autocolors';
// import { Chart } from "chart.js";
// Chart.register(autocolors);

/*
* The following line makes this controller "lazy": it won't be downloaded until needed
* See https://github.com/symfony/stimulus-bridge#lazy-controllers
*/
/* stimulusFetch: 'lazy' */
export default class extends Controller {
  connect() {
    this.element.addEventListener('chartjs:pre-connect', this._onPreConnect);
    this.element.addEventListener('chartjs:connect', this._onConnect);
}

disconnect() {
    // You should always remove listeners when the controller is disconnected to avoid side effects
    this.element.removeEventListener('chartjs:pre-connect', this._onPreConnect);
    this.element.removeEventListener('chartjs:connect', this._onConnect);
}

_onPreConnect(event) {
    // The chart is not yet created
    console.log(event.detail.options); // You can access the chart options using the event details

    console.log(event.detail);
    event.detail.options.plugins = [
      autocolors
    ];

    // For instance you can format Y axis
    event.detail.options.scales = {
        yAxes: [
            {
                ticks: {
                    callback: function (value, index, values) {
                        /* ... */
                    },
                },
            },
        ],
    };
}

_onConnect(event) {

    // The chart was just created
    console.log(event.detail.chart); // You can access the chart instance using the event details

    // For instance you can listen to additional events
    event.detail.chart.options.onHover = (mouseEvent) => {
        /* ... */
    };
    event.detail.chart.options.onClick = (mouseEvent) => {
        /* ... */
    };
}
}
robfarmergt commented 9 months ago

I got this to work by importing chart.js and then adding the plugin globally in the Stimulus Controller's initialize() method. I extend the stimulus-chartjs Controller. Hope this might help anyone trying to do the same. @marcusvy @fidalgo

// lib/chart.js

import annotationPlugin from "chartjs-plugin-annotation";
import { Chart as ChartJs } from "chart.js";

export default class extends Chart {
  initialize() {
    super.initialize();
    ChartJs.register(annotationPlugin);
  }
}
// controllers/application.js

import { Application } from "@hotwired/stimulus"
import Chart from "../lib/chart"

const application = Application.start();
application.register('chart', Chart);

// Configure Stimulus development experience
application.debug = false
window.Stimulus   = application

export { application }