{"spec_id":"gauge-basic","library":"echarts","language":"javascript","code":"// anyplot.ai\n// gauge-basic: Basic Gauge Chart\n// Library: echarts 5.5.1 | JavaScript 22.23.0\n// Quality: 91/100 | Created: 2026-06-30\n\n//# anyplot-orientation: square\n\nconst t = window.ANYPLOT_TOKENS;\n\n// Net Promoter Score — Q2 2026 customer satisfaction survey (scale 0–100)\nconst score = 72;\nconst zoneLabel = score >= 70 ? \"✓ Promoter Zone\"\n               : score >= 30 ? \"◎ Passive Zone\"\n               : \"✗ Detractor Zone\";\nconst zoneColor = score >= 70 ? \"#009E73\"\n               : score >= 30 ? \"#DDCC77\"\n               : \"#AE3030\";\n\nconst chart = echarts.init(document.getElementById(\"container\"));\n\nchart.setOption({\n  animation: false,\n  backgroundColor: \"transparent\",\n  title: {\n    text: \"gauge-basic · javascript · echarts · anyplot.ai\",\n    left: \"center\",\n    top: 28,\n    textStyle: { color: t.ink, fontSize: 22, fontWeight: \"normal\" },\n  },\n  series: [\n    {\n      type: \"gauge\",\n      center: [\"50%\", \"58%\"],\n      radius: \"76%\",\n      min: 0,\n      max: 100,\n      startAngle: 210,\n      endAngle: -30,\n      splitNumber: 10,\n      axisLine: {\n        lineStyle: {\n          width: 30,\n          color: [\n            [0.3, \"#AE3030\"],  // 0–30: poor (matte red)\n            [0.7, \"#DDCC77\"],  // 30–70: fair (amber)\n            [1.0, \"#009E73\"],  // 70–100: good (brand green)\n          ],\n        },\n      },\n      progress: {\n        show: true,\n        width: 14,\n        itemStyle: { color: t.palette[0] },\n      },\n      pointer: {\n        length: \"65%\",\n        width: 8,\n        itemStyle: { color: t.ink },\n      },\n      axisTick: {\n        splitNumber: 4,\n        length: 10,\n        lineStyle: { color: \"auto\", width: 2 },\n      },\n      splitLine: {\n        length: 20,\n        lineStyle: { color: \"auto\", width: 5 },\n      },\n      axisLabel: {\n        color: t.inkSoft,\n        fontSize: 14,\n        distance: 14,\n        formatter: function (value) {\n          const zones = [0, 30, 70, 100];\n          return zones.includes(Number(value)) ? value : \"\";\n        },\n      },\n      anchor: {\n        show: true,\n        showAbove: true,\n        size: 22,\n        itemStyle: {\n          borderWidth: 6,\n          borderColor: t.ink,\n          color: t.pageBg,\n        },\n      },\n      title: {\n        offsetCenter: [0, \"22%\"],\n        fontSize: 18,\n        color: t.inkSoft,\n        fontWeight: \"normal\",\n      },\n      detail: {\n        valueAnimation: false,\n        offsetCenter: [0, \"58%\"],\n        formatter: function (value) {\n          return `{val|${value}}\\n{lbl|${zoneLabel}}`;\n        },\n        rich: {\n          val: { fontSize: 60, fontWeight: \"bold\", color: t.ink, lineHeight: 80 },\n          lbl: { fontSize: 18, color: zoneColor, lineHeight: 32 },\n        },\n        color: t.ink,\n      },\n      data: [{ value: score, name: \"Net Promoter Score\" }],\n    },\n  ],\n});\n"}