ApexCharts card - A highly customizable graph card

@RomRider

Hello,

I am trying to change the color of a area when the value is negative.
Tried it with the experimental color theresold.

But i get something weird when using 3 sensors:

Code:

type: custom:apexcharts-card
experimental:
  color_threshold: true
update_interval: 1min
header:
  title: Oplevering Zonnepanelen
  show: true
  show_states: true
  colorize_states: false
graph_span: 6hours
series:
  - entity: sensor.power_consumption_w
    name: Energie verbruik
    type: area
    color: '#2291be'
    opacity: 0.5
  - entity: sensor.solaredge_current_power
    name: Z
    type: area
    color: green
    opacity: 0.5
  - entity: sensor.power_consumption_grid
    color_threshold:
      - value: -1000
        color: blue
      - value: -100
        color: blue
      - value: 0
        color: grey
      - value: 100
        color: grey
      - value: 10000
        color: grey
    fill_raw: last
    type: area
apex_config:
  stroke:
    show: true
  legend:
    show: false
  yaxis:
    show: true
  chart:
    height: 575px

Is there maybe any other way to give negative values a different color?

I need som help joining two series on a common timeline.

I got ‘today’ and ‘tomorrow’ in separate series with the following data_generation.

          return entity.attributes.today.map((item) => {
            return [new Date(item.startsAt), item.total]
          });

          return entity.attributes.tomorrow.map((item) => {
            return [new Date(item.startsAt), item.total]
          });

This gives a gap between the end of today and start of tomorrow on the graph.
I guess its because of “startsAt” ends at 23:00 on Today and starts at 00:00 on Tomorrow.

How do I interpolate/join them?

Skärmavbild 2021-12-03 kl. 15.46.51

So sensor.power_consumption_grid is the red line and you are wondering why it is red?
If so, because you can only use threshold on line OR area. It is not applied to both.
Create the same entry twice and set stroke_width to 0 for the area and to 2 (or whatever) for the duplicate with type:line. This will create two curves that will combine to what you want.

If I misunderstood, please explain further.

P.S.: I am on my mobile but can post an example of mine tomorrow if unclear :slight_smile:

Did you try the offset function?

Yes. The series still doesn’t join even though the offset sets them to meet at the same point on the x axis. Since the last value in today is not the same as the first value for tomorrow on the Y axis.

I guess the best way would be to strip and join the two objects in the array to get one series containing the data for today and tomorrow.

JavaScript is not my strong suit so I have no idea of how to manipulate json arrays in js.

Sorry, I understand now. Is there a reason why today’s data ends at 23:50 and not 24:00?
Where is the data coming from?

I also think you would need to merge both data sets into one. That way the line would be without the interruption.
But not sure how to merge to data sets in side Apexcharts.

P.S.: fill_raw: last probably doesn’t do anything, does it?

Never mind the data set. I got it working with joining the objects in the array with the concat function:


    var output = entity.attributes.today.concat(entity.attributes.tomorrow);
      return output.map((item) => {
        return [new Date(item.startsAt), item.total]

3 Likes

I’m trying to achieve something similar based on a weather entity. What I would like to display:

  • Temperature history
  • Temperature forecast high
  • Temperature forecast low

The graph spans 14 days (7 in the past, 7 in the future), and the idea would be to set temp forecast high to noon and temp forecast low to midnight, as well as join the temperature history (currently grouped by 2h average) via the data generator.

At the moment, I have the following for temp forecast high:

          return entity.attributes.forecast.map((entry) => {
            return [new Date(entry.datetime).getTime(), entry.temperature];
          });

This works perfectly, based on the following data from the weather entity (Openweathermap, one such entry per day in the forecast):

forecast:
  - datetime: '2021-12-05T11:00:00+00:00'
    precipitation: 7.57
    precipitation_probability: 100
    pressure: 1005
    wind_speed: 5.88
    wind_bearing: 234
    condition: snowy-rainy
    clouds: 100
    temperature: 2.6
    templow: -0.3

I’m not exactly a JS expert, so any help to get further ahead is much appreciated.

I’m using apexchart to show energy price and grid tariffs for today and tomorrow. The following code works well:

series:
  - entity: sensor.nordpool_kwh_oslo_nok_3_10_025
    name: Kraftpris
    type: line
    curve: stepline
    float_precision: 3
    extend_to_end: false
    show:
      legend_value: false
    data_generator: |
      return entity.attributes.raw_today.map((entry) => {
        return [new Date(entry.start), entry.value];
      });
  - entity: sensor.nordpool_kwh_oslo_nok_3_10_025
    name: Kraftpris
    type: line
    curve: stepline
    float_precision: 3
    color: blue
    extend_to_end: false
    show:
      legend_value: false
    data_generator: |
      return entity.attributes.raw_tomorrow.map((entry) => {
        return [new Date(entry.start), entry.value];
      });
  - entity: sensor.nettleie_hjemme_nede_forbruksledd
    name: Nettleie forbruksledd
    type: line
    curve: stepline
    float_precision: 3
    extend_to_end: false
    show:
      legend_value: false
    data_generator: |
      return entity.attributes.raw_today.map((entry) => {
        return [new Date(entry.start), entry.value];
      });
  - entity: sensor.nettleie_hjemme_nede_forbruksledd
    name: Nettleie forbruksledd
    type: line
    curve: stepline
    float_precision: 3
    color: blue
    extend_to_end: false
    show:
      legend_value: false
    data_generator: |
      return entity.attributes.raw_tomorrow.map((entry) => {
        return [new Date(entry.start), entry.value];
      });

I would like to show the sum of the two as well (since that is, in the end, what I’m going to have to pay in total). Is there a way to add the energy price (“kraftpris”) and grid tariff (“nettleie”) directly in the chart, or should I rather set up another sensor for the sum?

Hi all,

please , can somebody explain me, how can I setup bar chart with day energy consumption?
From entity I can get total consumption and I think, i must use transform to compute consumption difference for every day.

Thank you a lot

graph hw

type: 'custom:apexcharts-card'
graph_span: 31d
update_interval: 1hour
cache: true
span:
  end: day
header:
  title: Hot water
  show: true
  show_states: true
  colorize_states: true
apex_config:
  xaxis:
    labels:
      format: dd
      show: true
      showAlways: true
  yaxis:
    forceNiceScale: false
    decimalsInFloat: 0
  chart:
    type: area
    height: 300
  stroke:
    show: true
    width: 1
  legend:
    show: false
  dataLabels:
    enabled: false
    distributed: true
  fill:
    type: fill
    gradient:
      shadeIntensity: 0.1
      opacityFrom: 0.25
      opacityTo: 1
      inverseColors: true
      stops:
        - 0
        - 90
        - 100
series:
  - entity: sensor.shelly1pm_e8db84d27644_energy
    transform: return x ;  
    type: column
    name: HW
    float_precision: 1
    group_by:
      func: last
      duration: 1d

I have the same problem. A dashbord with a lot of apexcharts cards, and it turned even slower with the latest update…
Any solutions to this?

Here is my solution for a bar chart with day energy consumption derived from a total consumption sensor:


Described here.

What I’m still struggeling with, is floating daily consumption average line in the same graph.

You might want to add this to manipulate the font size of the status values:

style: |
  ha-card {
    font-size: 20px;
  }

They do work. Did you enable the experimental feature?

You need to edit the legend part also.

For 1. use card-mod
For 2. datalabels are to be set in show for each series.

Not possible for 1 entity unfortunately, that’s a limitation of the library I use.

You can use as_duration from the documentation. But if I remember correctly, it doesn’t apply to the datalabels (that is something I can add)

You should be able to use EVAL for that (check the documentation). I don’t remember if the hass object is available though… I’d need to check further.

You can use card-mod for that

No trick unfortunately, that’s how the library works :frowning:

Please open a GH issue if you didn’t fix it :slight_smile:

I’m not sure I understand what the issue is. Not that if there are gaps in the values (ie. some values are null, then color_threshold doesn’t work well.)

try this:

          return entity.attributes.forecast.flatMap((entry) => {
            let noon = new Date(entry.datetime).setHours(12, 0, 0, 0);
            let midnight = new Date(entry.datetime).setHours(23, 59, 59, 99);
            return [[new Date(noon).getTime(), entry.temperature], [new Date(midnight).getTime(), entry.templow]];
          });

Use a sensor instead :slight_smile:

Can you please share your code for this one. It seems the example on the Github page for the HNT component. doesn’t work anymore as y_axis_precision: is depreciated. Thanks.

Works perfect for the forecast, thank you very much! Any way of adding temperature history with 2h avg to this data generator?

Data generator doesn’t have access to the history so that is not possible.

Is there a way to calculate the tickAmount value?

When I have more than one y-axis, the min value is allways set to 0. Therefore I experiment calculating that value by my own. my example sets the min to next 1.000 below and the max to the next 1.000 above the real values.
What I would like to to is something like set the tickAmount to the number of 1.000 between min and max.

    min: EVAL:min => 1000 * Math.floor(min/1000)
    max: EVAL:max => 1000 * (1+Math.floor(max/1000))

tickAmount = (max - min)

But even with evaluating a constant value it does not show the graph.

    tickAmount: EVAL:tickAmount => 5


vs

I was afraid of that! I’ll poke around with the regular graph options, see if I can avoid the overlap between forecast and history that I’m currently having.

Thank you @RomRider .

I will need to look into Cardmodder then.

@all: does anybody know if it is possible to display overlapping series with a small x-axis shift?

1 Like