vega图表tickCount小于设定值

问题描述 投票:0回答:1

我在 Vega 中制作了一个条形图,每个类别有两列。这些列可以有正值或负值。我已将tickCount设置为以下值:

tickCount: 4
,但根据数据,tickCount有时小于4。对于下面的示例数据,tickCount仅为2。我对 Vega 如何计算和显示 tickCount 感到很困惑。

这是预期的行为吗?无论传递的数据如何,图表的 tickCount 是否可能始终为 4?

这是当前输出,我预计有 4 个刻度计数,最小值为 -400,最大值为 400。

chart result

{
  "$schema": "https://vega.github.io/schema/vega/v5.json",
  "width": 817,
  "height": 278,
  "autosize": {"type": "fit", "contains": "padding"},
  "padding": {"bottom": 2, "right": 9, "left": 5},
  "config": {
    "axis": {
      "labelFont": "HelveticaNeueLTW01-55Roman",
      "titleFont": "HelveticaNeueLTW01-55Roman"
    }
  },
  "data": [
    {
      "name": "capital_flows",
      "values": [
        {"label": "Aug 2023", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "Sep 2023", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "Oct 2023", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "Nov 2023", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "Dec 2023", "capital_inflow": 0, "capital_outflow": -317.18},
        {"label": "Jan 2024", "capital_inflow": 0, "capital_outflow": -117.19},
        {"label": "Feb 2024", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "Mar 2024", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "Apr 2024", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "May 2024", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "Jun 2024", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "Jul 2024", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "Aug 2024", "capital_inflow": 0, "capital_outflow": 0}
      ],
      "transform": [
        {"type": "formula", "expr": "split(datum.label, ' ')", "as": "label"}
      ]
    },
    {
      "name": "parsed",
      "source": ["capital_flows"],
      "transform": [
        {
          "type": "aggregate",
          "fields": [
            "capital_inflow",
            "capital_inflow",
            "capital_outflow",
            "capital_outflow"
          ],
          "ops": ["min", "max", "min", "max"],
          "as": ["min_value1", "max_value1", "min_value2", "max_value2"]
        },
        {
          "type": "formula",
          "expr": "datum.max_value1 == 0 && datum.max_value2 == 0 ? 1 : datum.max_value1 > datum.max_value2 ? abs(datum.max_value1) : abs(datum.max_value2)",
          "as": "mergedMax"
        },
        {
          "type": "formula",
          "expr": "datum.min_value1 == 0 && datum.min_value2 == 0 ? -1 : datum.min_value1 < datum.min_value2 ? abs(datum.min_value1) : abs(datum.min_value2)",
          "as": "mergedMin"
        },
        {
          "type": "formula",
          "expr": "datum.mergedMax > datum.mergedMin ? datum.mergedMax : datum.mergedMin",
          "as": "max"
        },
        {"type": "formula", "expr": "-(datum.max)", "as": "min"}
      ]
    }
  ],
  "scales": [
    {
      "name": "x",
      "type": "band",
      "range": "width",
      "domain": {"data": "capital_flows", "field": "label"}
    },
    {
      "name": "y",
      "type": "linear",
      "range": "height",
      "nice": true,
      "zero": false,
      "domain": {"data": "parsed", "field": "limit"},
      "domainMin": {"signal": "pluck(data('parsed'), 'min')"},
      "domainMax": {"signal": "pluck(data('parsed'), 'max')"}
    }
  ],
  "axes": [
    {
      "orient": "bottom",
      "scale": "x",
      "zindex": 1,
      "labelFontSize": 12,
      "labelColor": "#85868C",
      "labelAlign": "center",
      "labelLineHeight": 16.8,
      "labelFontWeight": "normal",
      "labelPadding": 8,
      "labelOpacity": 1,
      "domain": false,
      "domainColor": "#e5e5e5",
      "domainWidth": 1,
      "ticks": false
    },
    {
      "orient": "left",
      "scale": "y",
      "zindex": 0,
      "labelFontSize": 12,
      "labelColor": "#85868C",
      "labelLineHeight": 16.8,
      "labelFontWeight": "normal",
      "labelPadding": 8,
      "labelOpacity": 1,
      "domain": false,
      "domainColor": "#e5e5e5",
      "grid": true,
      "gridOpacity": 0.5,
      "ticks": false,
      "tickCount": 4,
      "gridDash": {"signal": "datum.value == 0 ? [0,0] : [4,4]"},
      "encode": {
        "labels": {
          "update": {
            "text": {
              "signal": "if(abs(datum.value) >= 1e9, format(datum.value/1e9, '$,.1~f') + 'B', if(abs(datum.value) >= 1e6, format(datum.value/1e6, '$,.1~f') + 'M', if(abs(datum.value) >= 1e3, format(datum.value/1e3, '$,.1~f') + 'K', format(datum.value, '$,.2~f'))))"
            }
          }
        }
      }
    }
  ],
  "marks": [
    {
      "name": "inflow",
      "type": "rect",
      "from": {"data": "capital_flows"},
      "encode": {
        "enter": {
          "xc": {"scale": "x", "field": "label", "band": 0.5},
          "width": {"value": 14},
          "y": {"scale": "y", "field": "capital_inflow"},
          "y2": {
            "scale": "y",
            "value": 0,
            "offset": {"signal": "datum.capital_inflow < 0 ? 1.5: 0"}
          },
          "fill": {"value": "#68c487"},
          "cornerRadiusTopLeft": {
            "signal": "datum.capital_inflow > 0 ? '1' : '0'"
          },
          "cornerRadiusTopRight": {
            "signal": "datum.capital_inflow > 0 ? '1' : '0'"
          },
          "cornerRadiusBottomLeft": {
            "signal": "datum.capital_inflow > 0 ? '0' : '1'"
          },
          "cornerRadiusBottomRight": {
            "signal": "datum.capital_inflow > 0 ? '0' : '1'"
          },
          "stroke": {"signal": "datum.capital_inflow !== 0 ? '#68c487': null"},
          "strokeWidth": {"value": 1.5},
          "fillOpacity": {"signal": "datum.capital_inflow !== 0 ? 1 : 0"}
        }
      }
    },
    {
      "name": "outflow",
      "type": "rect",
      "from": {"data": "capital_flows"},
      "encode": {
        "enter": {
          "xc": {"scale": "x", "field": "label", "band": 0.5, "offset": 17},
          "width": {"value": 14},
          "y": {"scale": "y", "field": "capital_outflow"},
          "y2": {
            "scale": "y",
            "value": 0,
            "offset": {"signal": "datum.capital_outflow < 0 ? 1.5: 0"}
          },
          "fill": {"value": "#FFB066"},
          "cornerRadiusTopLeft": {
            "signal": "datum.capital_outflow > 0 ? '1' : '0'"
          },
          "cornerRadiusTopRight": {
            "signal": "datum.capital_outflow > 0 ? '1' : '0'"
          },
          "cornerRadiusBottomLeft": {
            "signal": "datum.capital_outflow > 0 ? '0' : '1'"
          },
          "cornerRadiusBottomRight": {
            "signal": "datum.capital_outflow > 0 ? '0' : '1'"
          },
          "stroke": {"signal": "datum.capital_outflow !== 0 ? '#FFB066': null"},
          "strokeWidth": {"value": 1.5},
          "fillOpacity": {"signal": "datum.capital_outflow !== 0 ? 1 : 0"}
        }
      }
    }
  ]
}
json charts visualization vega-lite vega
1个回答
0
投票

tickCount 使用一些内部逻辑和启发式方法,因此不幸的是,它不能总是保证您会看到指定的刻度数。如果您想完全控制,您可以使用values属性来控制它。在您的情况下,您将通过使用domainMin(-317)和domainMax(317)来覆盖。例如:

enter image description here

由以下人员制作。您需要确保您的域最小值和最大值的计算是适当的。

{
  "$schema": "https://vega.github.io/schema/vega/v5.json",
  "width": 817,
  "height": 278,
  "autosize": {"type": "fit", "contains": "padding"},
  "padding": {"bottom": 2, "right": 9, "left": 5},
  "config": {
    "axis": {
      "labelFont": "HelveticaNeueLTW01-55Roman",
      "titleFont": "HelveticaNeueLTW01-55Roman"
    }
  },
  "data": [
    {
      "name": "capital_flows",
      "values": [
        {"label": "Aug 2023", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "Sep 2023", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "Oct 2023", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "Nov 2023", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "Dec 2023", "capital_inflow": 0, "capital_outflow": -317.18},
        {"label": "Jan 2024", "capital_inflow": 0, "capital_outflow": -117.19},
        {"label": "Feb 2024", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "Mar 2024", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "Apr 2024", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "May 2024", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "Jun 2024", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "Jul 2024", "capital_inflow": 0, "capital_outflow": 0},
        {"label": "Aug 2024", "capital_inflow": 0, "capital_outflow": 0}
      ],
      "transform": [
        {"type": "formula", "expr": "split(datum.label, ' ')", "as": "label"}
      ]
    },
    {
      "name": "parsed",
      "source": ["capital_flows"],
      "transform": [
        {
          "type": "aggregate",
          "fields": [
            "capital_inflow",
            "capital_inflow",
            "capital_outflow",
            "capital_outflow"
          ],
          "ops": ["min", "max", "min", "max"],
          "as": ["min_value1", "max_value1", "min_value2", "max_value2"]
        },
        {
          "type": "formula",
          "expr": "datum.max_value1 == 0 && datum.max_value2 == 0 ? 1 : datum.max_value1 > datum.max_value2 ? abs(datum.max_value1) : abs(datum.max_value2)",
          "as": "mergedMax"
        },
        {
          "type": "formula",
          "expr": "datum.min_value1 == 0 && datum.min_value2 == 0 ? -1 : datum.min_value1 < datum.min_value2 ? abs(datum.min_value1) : abs(datum.min_value2)",
          "as": "mergedMin"
        },
        {
          "type": "formula",
          "expr": "datum.mergedMax > datum.mergedMin ? datum.mergedMax : datum.mergedMin",
          "as": "max"
        },
        {"type": "formula", "expr": "-(datum.max)", "as": "min"}
      ]
    }
  ],
  "scales": [
    {
      "name": "x",
      "type": "band",
      "range": "width",
      "domain": {"data": "capital_flows", "field": "label"}
    },
    {
      "name": "y",
      "type": "linear",
      "range": "height",
      "nice": true,
      "zero": false,
      "domain": {"data": "parsed", "field": "limit"},
      "domainMin": {"signal": "-400"},
      "domainMax": {"signal": "400"}
    }
  ],
  "axes": [
    {
      "orient": "bottom",
      "scale": "x",
      "zindex": 1,
      "labelFontSize": 12,
      "labelColor": "#85868C",
      "labelAlign": "center",
      "labelLineHeight": 16.8,
      "labelFontWeight": "normal",
      "labelPadding": 8,
      "labelOpacity": 1,
      "domain": false,
      "domainColor": "#e5e5e5",
      "domainWidth": 1,
      "ticks": false
    },
    {
      "orient": "left",
      "scale": "y",
      "zindex": 0,
      "labelFontSize": 12,
      "labelColor": "#85868C",
      "labelLineHeight": 16.8,
      "labelFontWeight": "normal",
      "labelPadding": 8,
      "labelOpacity": 1,
      "domain": false,
      "domainColor": "#e5e5e5",
      "grid": true,
      "gridOpacity": 0.5,
      "ticks": false,
      "tickCount": 4,
      "gridDash": {"signal": "datum.value == 0 ? [0,0] : [4,4]"},
      "encode": {
        "labels": {
          "update": {
            "text": {
              "signal": "if(abs(datum.value) >= 1e9, format(datum.value/1e9, '$,.1~f') + 'B', if(abs(datum.value) >= 1e6, format(datum.value/1e6, '$,.1~f') + 'M', if(abs(datum.value) >= 1e3, format(datum.value/1e3, '$,.1~f') + 'K', format(datum.value, '$,.2~f'))))"
            }
          }
        }
      }
    }
  ],
  "marks": [
    {
      "name": "inflow",
      "type": "rect",
      "from": {"data": "capital_flows"},
      "encode": {
        "enter": {
          "xc": {"scale": "x", "field": "label", "band": 0.5},
          "width": {"value": 14},
          "y": {"scale": "y", "field": "capital_inflow"},
          "y2": {
            "scale": "y",
            "value": 0,
            "offset": {"signal": "datum.capital_inflow < 0 ? 1.5: 0"}
          },
          "fill": {"value": "#68c487"},
          "cornerRadiusTopLeft": {
            "signal": "datum.capital_inflow > 0 ? '1' : '0'"
          },
          "cornerRadiusTopRight": {
            "signal": "datum.capital_inflow > 0 ? '1' : '0'"
          },
          "cornerRadiusBottomLeft": {
            "signal": "datum.capital_inflow > 0 ? '0' : '1'"
          },
          "cornerRadiusBottomRight": {
            "signal": "datum.capital_inflow > 0 ? '0' : '1'"
          },
          "stroke": {"signal": "datum.capital_inflow !== 0 ? '#68c487': null"},
          "strokeWidth": {"value": 1.5},
          "fillOpacity": {"signal": "datum.capital_inflow !== 0 ? 1 : 0"}
        }
      }
    },
    {
      "name": "outflow",
      "type": "rect",
      "from": {"data": "capital_flows"},
      "encode": {
        "enter": {
          "xc": {"scale": "x", "field": "label", "band": 0.5, "offset": 17},
          "width": {"value": 14},
          "y": {"scale": "y", "field": "capital_outflow"},
          "y2": {
            "scale": "y",
            "value": 0,
            "offset": {"signal": "datum.capital_outflow < 0 ? 1.5: 0"}
          },
          "fill": {"value": "#FFB066"},
          "cornerRadiusTopLeft": {
            "signal": "datum.capital_outflow > 0 ? '1' : '0'"
          },
          "cornerRadiusTopRight": {
            "signal": "datum.capital_outflow > 0 ? '1' : '0'"
          },
          "cornerRadiusBottomLeft": {
            "signal": "datum.capital_outflow > 0 ? '0' : '1'"
          },
          "cornerRadiusBottomRight": {
            "signal": "datum.capital_outflow > 0 ? '0' : '1'"
          },
          "stroke": {"signal": "datum.capital_outflow !== 0 ? '#FFB066': null"},
          "strokeWidth": {"value": 1.5},
          "fillOpacity": {"signal": "datum.capital_outflow !== 0 ? 1 : 0"}
        }
      }
    }
  ]
}
© www.soinside.com 2019 - 2024. All rights reserved.