jichoi / lms_front star
PsHooN7979 2024-08-19
240819 박세훈 학부모 대시보드 교재별 진행률 및 오답률 데이터 시각화 적용
@b647a092a0b0ef413c3fee4c4f118487bf34fa2c
client/views/pages/main/Chapter/Chapter3_7.vue
--- client/views/pages/main/Chapter/Chapter3_7.vue
+++ client/views/pages/main/Chapter/Chapter3_7.vue
@@ -112,6 +112,7 @@
             prblmExpln: null,
             accessTime: null,
             answer: null,
+            prblmLogAnsCnt: 0,
         };
     },
     methods: {
@@ -169,7 +170,7 @@
                 },
                 data: {
                     prblmAns: vm.answer,
-                    prblmLogAnsCnt: 0,
+                    prblmLogAnsCnt: vm.prblmLogAnsCnt + 1,
                     stdId: "2",
                     // prblmStrtTm: formattedTime,
                     prblmId: vm.prblmId,
@@ -212,6 +213,9 @@
         this.problemSearch();
         this.created();
     },
+    beforeUnmount() {
+        sessionStorage.removeItem("previewNote");
+    },
 };
 </script>
 <style scoped>
client/views/pages/main/Chapter/Chapter4.vue
--- client/views/pages/main/Chapter/Chapter4.vue
+++ client/views/pages/main/Chapter/Chapter4.vue
@@ -2,7 +2,9 @@
     <div id="Chapter1_1" class="content-wrap">
         <div style="margin: 30px 0px 50px; width: 20%">
             <router-link to="/MyPlan.page">
-                <div class="logo mb25"><img src="../../../../resources/img/logo2.png" alt=""></div>
+                <div class="logo mb25">
+                    <img src="../../../../resources/img/logo2.png" alt="" />
+                </div>
             </router-link>
         </div>
         <div class="title-box mb25 flex align-center mt40">
@@ -21,12 +23,23 @@
                  </button>
                 </div> -->
 
-                <div class="text-ct flex justify-center" style="gap: 150px; margin: 0 auto">
+                <div
+                    class="text-ct flex justify-center"
+                    style="gap: 150px; margin: 0 auto"
+                >
                     <div class="wrap-bg">
                         <div class="title-box flex mb10 justify-between">
                             <p class="title mb20">최종 점수</p>
-                            <button type="button" class="popup-close-btn" @click="closeBtn">
-                                <svg-icon type="mdi" :path="mdiWindowClose" class="close-btn"></svg-icon>
+                            <button
+                                type="button"
+                                class="popup-close-btn"
+                                @click="closeBtn"
+                            >
+                                <svg-icon
+                                    type="mdi"
+                                    :path="mdiWindowClose"
+                                    class="close-btn"
+                                ></svg-icon>
                             </button>
                         </div>
                         <div style="width: 100%" class="flex mt30">
@@ -38,12 +51,27 @@
                     <div class="bg-gray" style="width: 980px">
                         <div class="title-box flex mb10 justify-between">
                             <p class="title mb20">오답 문제 리스트</p>
-                            <button type="button" class="popup-close-btn" @click="closeBtn">
-                                <svg-icon type="mdi" :path="mdiWindowClose" class="close-btn"></svg-icon>
+                            <button
+                                type="button"
+                                class="popup-close-btn"
+                                @click="closeBtn"
+                            >
+                                <svg-icon
+                                    type="mdi"
+                                    :path="mdiWindowClose"
+                                    class="close-btn"
+                                ></svg-icon>
                             </button>
                         </div>
-                        <article class="mb20 flex-column result-box" style="gap: 20px">
-                            <div class="flex justify-between wrap" v-for="(item, index) in dataList" :key="item.id">
+                        <article
+                            class="mb20 flex-column result-box"
+                            style="gap: 20px"
+                        >
+                            <div
+                                class="flex justify-between wrap"
+                                v-for="(item, index) in dataList"
+                                :key="item.id"
+                            >
                                 <div class="flex align-center">
                                     <div>
                                         <p class="title1 mr20">
@@ -57,13 +85,23 @@
                                     </div>
                                 </div>
                                 <div>
-                                    <div class="flex align-center" style="gap: 10px">
-                                        <button type="button" title="정답 확인" class="yellow-btn" @click="
-                                            [
-                                                handleProblemDetail(item),
-                                                goToPage(problemType),
-                                            ]
-                                            ">
+                                    <div
+                                        class="flex align-center"
+                                        style="gap: 10px"
+                                    >
+                                        <button
+                                            type="button"
+                                            title="정답 확인"
+                                            class="yellow-btn"
+                                            @click="
+                                                [
+                                                    handleProblemDetail(item),
+                                                    goToProblemPage(
+                                                        problemType
+                                                    ),
+                                                ]
+                                            "
+                                        >
                                             정답 확인
                                         </button>
                                     </div>
@@ -93,7 +131,7 @@
             showButton4: false,
 
             // 단원 평가 아이디, 추후 세션으로 받게 변경
-            evalId: "EVAL_000000000000003",
+            evalId: "EVAL_000000000000004",
 
             dataList: [],
 
@@ -106,6 +144,10 @@
         goToPage(page) {
             this.$router.push({ name: page });
         },
+        goToProblemPage(page) {
+            sessionStorage.setItem("previewNote", "true");
+            this.$router.push({ name: page });
+        },
         handleDrag(dragNumber) {
             // Drag 버튼 숨기기
             // 여기서는 상태 관리를 통해 버튼을 제어합니다.
client/views/pages/parents/Barchart.vue
--- client/views/pages/parents/Barchart.vue
+++ client/views/pages/parents/Barchart.vue
@@ -1,204 +1,334 @@
 <template>
-    <div ref="Barchart" style="width: 500px; height: 500px;"></div>
-  </template>
-  
-  <script>
-  import * as am5 from "@amcharts/amcharts5";
-  import * as am5xy from "@amcharts/amcharts5/xy";
-  import am5themes_Animated from "@amcharts/amcharts5/themes/Animated";
-  
-  export default {
+    <div ref="Barchart" style="width: 500px; height: 500px"></div>
+</template>
+
+<script>
+import * as am5 from "@amcharts/amcharts5";
+import * as am5xy from "@amcharts/amcharts5/xy";
+import am5themes_Animated from "@amcharts/amcharts5/themes/Animated";
+import axios from "axios";
+
+export default {
     name: "Barchart",
+    data() {
+        return {
+            chartData: [],
+        };
+    },
     mounted() {
-      this.createChart();
+        this.getIncorrectRate();
     },
     methods: {
-      createChart() {
-        // Initialize root
-        const root = am5.Root.new(this.$refs.Barchart);
-  
-        // Apply themes
-        const myTheme = am5.Theme.new(root);
-        myTheme.rule("Grid", ["base"]).setAll({
-          strokeOpacity: 0.1,
-        });
-        root.setThemes([
-          am5themes_Animated.new(root),
-          myTheme,
-        ]);
-  
-        // Create chart
-        let chart = root.container.children.push(
-  am5xy.XYChart.new(root, {
-    panX: false,
-    panY: false,
-    wheelX: "none",
-    wheelY: "none",
-    paddingLeft: 0
-  })
-);
+        getIncorrectRate() {
+            const vm = this;
+            axios({
+                url: "dashboard/incorrectRateData.json",
+                method: "post",
+                headers: {
+                    "Content-Type": "application/json; charset=UTF-8",
+                },
+                data: {
+                    std_id: "1",
+                },
+            })
+                .then(function (res) {
+                    console.log("Inccorect Rate - response : ", res.data);
+                    vm.chartData = res.data;
+                    // console.log(vm.chartData);
+                    vm.createChart();
+                })
+                .catch(function (error) {
+                    console.log("Incorrect Rate - error : ", error);
+                });
+        },
 
+        createChart() {
+            // Initialize root
+            const root = am5.Root.new(this.$refs.Barchart);
 
-// Create axes
-// https://www.amcharts.com/docs/v5/charts/xy-chart/axes/
-let yRenderer = am5xy.AxisRendererY.new(root, {
-  minGridDistance: 30,
-  minorGridEnabled: true
-});
-yRenderer.grid.template.set("location", 1);
+            // Apply themes
+            const myTheme = am5.Theme.new(root);
+            myTheme.rule("Grid", ["base"]).setAll({
+                strokeOpacity: 0.1,
+            });
+            root.setThemes([am5themes_Animated.new(root), myTheme]);
 
-let yAxis = chart.yAxes.push(
-  am5xy.CategoryAxis.new(root, {
-    maxDeviation: 0,
-    categoryField: "country",
-    renderer: yRenderer
-  })
-);
+            // Create chart
+            let chart = root.container.children.push(
+                am5xy.XYChart.new(root, {
+                    panX: false,
+                    panY: false,
+                    wheelX: "none",
+                    wheelY: "none",
+                    paddingLeft: 0,
+                })
+            );
 
-let xAxis = chart.xAxes.push(
-  am5xy.ValueAxis.new(root, {
-    maxDeviation: 0,
-    min: 0,
-    renderer: am5xy.AxisRendererX.new(root, {
-      visible: true,
-      strokeOpacity: 0.1,
-      minGridDistance: 80
-    })
-  })
-);
+            // Create axes
+            // https://www.amcharts.com/docs/v5/charts/xy-chart/axes/
+            let yRenderer = am5xy.AxisRendererY.new(root, {
+                minGridDistance: 30,
+                minorGridEnabled: true,
+            });
+            yRenderer.grid.template.set("location", 1);
 
+            let yAxis = chart.yAxes.push(
+                am5xy.CategoryAxis.new(root, {
+                    maxDeviation: 0,
+                    categoryField: "bookNm",
+                    renderer: yRenderer,
+                })
+            );
 
-// Create series
-// https://www.amcharts.com/docs/v5/charts/xy-chart/series/
-let series = chart.series.push(
-  am5xy.ColumnSeries.new(root, {
-    name: "Series 1",
-    xAxis: xAxis,
-    yAxis: yAxis,
-    valueXField: "value",
-    sequencedInterpolation: true,
-    categoryYField: "country"
-  })
-);
+            let xAxis = chart.xAxes.push(
+                am5xy.ValueAxis.new(root, {
+                    maxDeviation: 0,
+                    min: 0,
+                    renderer: am5xy.AxisRendererX.new(root, {
+                        visible: true,
+                        strokeOpacity: 0.1,
+                        minGridDistance: 80,
+                    }),
+                })
+            );
 
-let columnTemplate = series.columns.template;
+            // Create series
+            // https://www.amcharts.com/docs/v5/charts/xy-chart/series/
+            let series = chart.series.push(
+                am5xy.ColumnSeries.new(root, {
+                    name: "Incorrect Rate",
+                    xAxis: xAxis,
+                    yAxis: yAxis,
+                    valueXField: "incorrectRate",
+                    sequencedInterpolation: true,
+                    categoryYField: "bookNm",
+                })
+            );
 
-columnTemplate.setAll({
-  draggable: true,
-  cursorOverStyle: "pointer",
-  tooltipText: "drag to rearrange",
-  cornerRadiusBR: 10,
-  cornerRadiusTR: 10,
-  strokeOpacity: 0
-});
-columnTemplate.adapters.add("fill", (fill, target) => {
-  return chart.get("colors").getIndex(series.columns.indexOf(target));
-});
+            let columnTemplate = series.columns.template;
 
-columnTemplate.adapters.add("stroke", (stroke, target) => {
-  return chart.get("colors").getIndex(series.columns.indexOf(target));
-});
+            columnTemplate.setAll({
+                draggable: true,
+                cursorOverStyle: "pointer",
+                tooltipText: "{categoryY}: {valueX}",
+                cornerRadiusBR: 10,
+                cornerRadiusTR: 10,
+                strokeOpacity: 0,
+            });
+            columnTemplate.adapters.add("fill", (fill, target) => {
+                return chart
+                    .get("colors")
+                    .getIndex(series.columns.indexOf(target));
+            });
 
-columnTemplate.events.on("dragstop", () => {
-  sortCategoryAxis();
-});
+            columnTemplate.adapters.add("stroke", (stroke, target) => {
+                return chart
+                    .get("colors")
+                    .getIndex(series.columns.indexOf(target));
+            });
 
-// Get series item by category
-function getSeriesItem(category) {
-  for (var i = 0; i < series.dataItems.length; i++) {
-    let dataItem = series.dataItems[i];
-    if (dataItem.get("categoryY") == category) {
-      return dataItem;
-    }
-  }
-}
+            columnTemplate.events.on("dragstop", () => {
+                this.sortCategoryAxis(series, yAxis, yRenderer);
+            });
 
+            // Get series item by category
+            // function getSeriesItem(category) {
+            //     for (var i = 0; i < series.dataItems.length; i++) {
+            //         let dataItem = series.dataItems[i];
+            //         if (dataItem.get("categoryY") == category) {
+            //             return dataItem;
+            //         }
+            //     }
+            // }
 
-// Axis sorting
-function sortCategoryAxis() {
-  // Sort by value
-  series.dataItems.sort(function (x, y) {
-    return y.get("graphics").y() - x.get("graphics").y();
-  });
+            // Axis sorting
+            // function sortCategoryAxis() {
+            //     // Sort by value
+            //     series.dataItems.sort(function (x, y) {
+            //         return y.get("graphics").y() - x.get("graphics").y();
+            //     });
 
-  let easing = am5.ease.out(am5.ease.cubic);
+            //     let easing = am5.ease.out(am5.ease.cubic);
 
-  // Go through each axis item
-  am5.array.each(yAxis.dataItems, function (dataItem) {
-    // get corresponding series item
-    let seriesDataItem = getSeriesItem(dataItem.get("category"));
+            //     // Go through each axis item
+            //     am5.array.each(yAxis.dataItems, function (dataItem) {
+            //         // get corresponding series item
+            //         let seriesDataItem = getSeriesItem(
+            //             dataItem.get("category")
+            //         );
 
-    if (seriesDataItem) {
-      // get index of series data item
-      let index = series.dataItems.indexOf(seriesDataItem);
+            //         if (seriesDataItem) {
+            //             // get index of series data item
+            //             let index = series.dataItems.indexOf(seriesDataItem);
 
-      let column = seriesDataItem.get("graphics");
+            //             let column = seriesDataItem.get("graphics");
 
-      // position after sorting
-      let fy =
-        yRenderer.positionToCoordinate(yAxis.indexToPosition(index)) -
-        column.height() / 2;
+            //             // position after sorting
+            //             let fy =
+            //                 yRenderer.positionToCoordinate(
+            //                     yAxis.indexToPosition(index)
+            //                 ) -
+            //                 column.height() / 2;
 
-      // set index to be the same as series data item index
-      if (index != dataItem.get("index")) {
-        dataItem.set("index", index);
+            //             // set index to be the same as series data item index
+            //             if (index != dataItem.get("index")) {
+            //                 dataItem.set("index", index);
 
-        // current position
-        let x = column.x();
-        let y = column.y();
+            //                 // current position
+            //                 let x = column.x();
+            //                 let y = column.y();
 
-        column.set("dy", -(fy - y));
-        column.set("dx", x);
+            //                 column.set("dy", -(fy - y));
+            //                 column.set("dx", x);
 
-        column.animate({ key: "dy", to: 0, duration: 600, easing: easing });
-        column.animate({ key: "dx", to: 0, duration: 600, easing: easing });
-      } else {
-        column.animate({ key: "y", to: fy, duration: 600, easing: easing });
-        column.animate({ key: "x", to: 0, duration: 600, easing: easing });
-      }
-    }
-  });
+            //                 column.animate({
+            //                     key: "dy",
+            //                     to: 0,
+            //                     duration: 600,
+            //                     easing: easing,
+            //                 });
+            //                 column.animate({
+            //                     key: "dx",
+            //                     to: 0,
+            //                     duration: 600,
+            //                     easing: easing,
+            //                 });
+            //             } else {
+            //                 column.animate({
+            //                     key: "y",
+            //                     to: fy,
+            //                     duration: 600,
+            //                     easing: easing,
+            //                 });
+            //                 column.animate({
+            //                     key: "x",
+            //                     to: 0,
+            //                     duration: 600,
+            //                     easing: easing,
+            //                 });
+            //             }
+            //         }
+            //     });
 
-  // Sort axis items by index.
-  // This changes the order instantly, but as dx and dy is set and animated,
-  // they keep in the same places and then animate to true positions.
-  yAxis.dataItems.sort(function (x, y) {
-    return x.get("index") - y.get("index");
-  });
-}
+            // Sort axis items by index.
+            // This changes the order instantly, but as dx and dy is set and animated,
+            // they keep in the same places and then animate to true positions.
+            //     yAxis.dataItems.sort(function (x, y) {
+            //         return x.get("index") - y.get("index");
+            //     });
+            // }
 
-// Set data
-let data = [{
-  country: "USA",
-  value: 2025
-}, {
-  country: "China",
-  value: 1882
-}, {
-  country: "Japan",
-  value: 1809
-}, {
-  country: "Germany",
-  value: 1322
-}, {
-  country: "UK",
-  value: 1122
-}];
+            // Set data
+            // let data = [
+            //     {
+            //         country: "USA",
+            //         value: 2025,
+            //     },
+            //     {
+            //         country: "China",
+            //         value: 1882,
+            //     },
+            //     {
+            //         country: "Japan",
+            //         value: 1809,
+            //     },
+            //     {
+            //         country: "Germany",
+            //         value: 1322,
+            //     },
+            //     {
+            //         country: "UK",
+            //         value: 1122,
+            //     },
+            // ];
 
-yAxis.data.setAll(data);
-series.data.setAll(data);
+            // yAxis.data.setAll(data);
+            // series.data.setAll(data);
 
+            yAxis.data.setAll(this.chartData);
+            series.data.setAll(this.chartData);
 
-// Make stuff animate on load
-// https://www.amcharts.com/docs/v5/concepts/animations/
-series.appear(1000);
-chart.appear(1000, 100);
-      },
+            // Make stuff animate on load
+            // https://www.amcharts.com/docs/v5/concepts/animations/
+            series.appear(1000);
+            chart.appear(1000, 100);
+        },
+        sortCategoryAxis(series, yAxis, yRenderer) {
+            // Sort by value
+            series.dataItems.sort((x, y) => {
+                return y.get("graphics").y() - x.get("graphics").y();
+            });
+
+            let easing = am5.ease.out(am5.ease.cubic);
+
+            // Go through each axis item
+            am5.array.each(yAxis.dataItems, function (dataItem) {
+                // get corresponding series item
+                let seriesDataItem = series.dataItems.find(
+                    (dataItem) =>
+                        dataItem.get("categoryY") == dataItem.get("category")
+                );
+
+                if (seriesDataItem) {
+                    // get index of series data item
+                    let index = series.dataItems.indexOf(seriesDataItem);
+
+                    let column = seriesDataItem.get("graphics");
+
+                    // position after sorting
+                    let fy =
+                        yRenderer.positionToCoordinate(
+                            yAxis.indexToPosition(index)
+                        ) -
+                        column.height() / 2;
+
+                    // set index to be the same as series data item index
+                    if (index != dataItem.get("index")) {
+                        dataItem.set("index", index);
+
+                        // current position
+                        let x = column.x();
+                        let y = column.y();
+
+                        column.set("dy", -(fy - y));
+                        column.set("dx", x);
+
+                        column.animate({
+                            key: "dy",
+                            to: 0,
+                            duration: 600,
+                            easing: easing,
+                        });
+                        column.animate({
+                            key: "dx",
+                            to: 0,
+                            duration: 600,
+                            easing: easing,
+                        });
+                    } else {
+                        column.animate({
+                            key: "y",
+                            to: fy,
+                            duration: 600,
+                            easing: easing,
+                        });
+                        column.animate({
+                            key: "x",
+                            to: 0,
+                            duration: 600,
+                            easing: easing,
+                        });
+                    }
+                }
+            });
+            yAxis.dataItems.sort((x, y) => {
+                return x.get("index") - y.get("index");
+            });
+        },
     },
-  };
-  </script>
-  
-  <style scoped>
-  /* Add necessary styles here */
-  </style>
-  
(No newline at end of file)
+};
+</script>
+
+<style scoped>
+/* Add necessary styles here */
+</style>
client/views/pages/parents/StackedBarChart.vue
--- client/views/pages/parents/StackedBarChart.vue
+++ client/views/pages/parents/StackedBarChart.vue
@@ -1,129 +1,197 @@
 <template>
-    <div ref="StackedBarChart" style=" height: 500px;"></div>
-  </template>
-  
-  <script>
-  import * as am5 from "@amcharts/amcharts5";
-  import * as am5xy from "@amcharts/amcharts5/xy";
-  import am5themes_Animated from "@amcharts/amcharts5/themes/Animated";
-  
-  export default {
+    <div ref="StackedBarChart" style="height: 500px"></div>
+</template>
+
+<script>
+import * as am5 from "@amcharts/amcharts5";
+import * as am5xy from "@amcharts/amcharts5/xy";
+import am5themes_Animated from "@amcharts/amcharts5/themes/Animated";
+import axios from "axios";
+
+export default {
     name: "StackedBarChart",
+    data() {
+        return {
+            chartData: [],
+        };
+    },
     mounted() {
-      this.createChart();
+        this.getProgressRate();
     },
     methods: {
-      createChart() {
-        // Initialize root
-        const root = am5.Root.new(this.$refs.StackedBarChart);
-  
-        // Apply themes
-        const myTheme = am5.Theme.new(root);
-        myTheme.rule("Grid", ["base"]).setAll({
-          strokeOpacity: 0.1,
-        });
-        root.setThemes([
-          am5themes_Animated.new(root),
-          myTheme,
-        ]);
-  
-        // Create chart
-        const chart = root.container.children.push(
-          am5xy.XYChart.new(root, {
-            panX: false,
-            panY: false,
-            wheelX: "panY",
-            wheelY: "zoomY",
-            paddingLeft: 0,
-            layout: root.verticalLayout,
-          })
-        );
-  
-        // Define data
-        const data = [
-          { year: "2021", europe: 2.5, namerica: 2.5, asia: 2.1, lamerica: 1, meast: 0.8, africa: 0.4 },
-        ];
-  
-        // Create Y Axis
-        const yRenderer = am5xy.AxisRendererY.new(root, {});
-        const yAxis = chart.yAxes.push(am5xy.CategoryAxis.new(root, {
-          categoryField: "year",
-          renderer: yRenderer,
-          tooltip: am5.Tooltip.new(root, {}),
-        }));
-        yRenderer.grid.template.setAll({
-          location: 1,
-        });
-        yAxis.data.setAll(data);
-  
-        // Create X Axis
-        const xAxis = chart.xAxes.push(am5xy.ValueAxis.new(root, {
-          min: 0,
-          maxPrecision: 0,
-          renderer: am5xy.AxisRendererX.new(root, {
-            minGridDistance: 40,
-            strokeOpacity: 0.1,
-          }),
-        }));
-  
-        // Create legend
-        const legend = chart.children.push(am5.Legend.new(root, {
-          centerX: am5.p50,
-          x: am5.p50,
-        }));
-  
-        // Function to create series
-        const createSeries = (name, fieldName) => {
-          const series = chart.series.push(am5xy.ColumnSeries.new(root, {
-            name,
-            stacked: true,
-            xAxis,
-            yAxis,
-            baseAxis: yAxis,
-            valueXField: fieldName,
-            categoryYField: "year",
-          }));
-  
-          series.columns.template.setAll({
-            tooltipText: "{name}, {categoryY}: {valueX}",
-            tooltipY: am5.percent(90),
-          });
-          series.data.setAll(data);
-  
-          series.appear();
-  
-          series.bullets.push(() =>
-            am5.Bullet.new(root, {
-              sprite: am5.Label.new(root, {
-                text: "{valueX}",
-                fill: root.interfaceColors.get("alternativeText"),
-                centerY: am5.p50,
-                centerX: am5.p50,
-                populateText: true,
-              }),
+        getProgressRate() {
+            const vm = this;
+            axios({
+                url: "dashboard/progressRate.json",
+                method: "post",
+                headers: {
+                    "Content-Type": "application/json; charset=UTF-8",
+                },
+                data: {
+                    stdId: "1",
+                },
             })
-          );
-          
-  
-          legend.data.push(series);
-        };
-   
-        // Create series
-        createSeries("Europe", "europe");
-        createSeries("North America", "namerica");
-        createSeries("Asia", "asia");
-        createSeries("Latin America", "lamerica");
-        createSeries("Middle East", "meast");
-        createSeries("Africa", "africa");
-  
-        // Chart animation
-        chart.appear(1000, 100);
-      },
+                .then(function (res) {
+                    // console.log("Progress Rate - response : ", res.data);
+                    vm.chartData = res.data;
+                    // console.log(vm.chartData);
+                    vm.createChart();
+                })
+                .catch(function (error) {
+                    console.log("Progress Rate - error : ", error);
+                });
+        },
+
+        createChart() {
+            // Initialize root
+            const root = am5.Root.new(this.$refs.StackedBarChart);
+
+            // Apply themes
+            const myTheme = am5.Theme.new(root);
+            myTheme.rule("Grid", ["base"]).setAll({
+                strokeOpacity: 0.1,
+            });
+            root.setThemes([am5themes_Animated.new(root), myTheme]);
+
+            // Create chart
+            const chart = root.container.children.push(
+                am5xy.XYChart.new(root, {
+                    panX: false,
+                    panY: false,
+                    wheelX: "panY",
+                    wheelY: "zoomY",
+                    paddingLeft: 0,
+                    layout: root.verticalLayout,
+                })
+            );
+
+            // Define data
+            // const data = [
+            //     {
+            //         year: "2021",
+            //         europe: 2.5,
+            //         namerica: 2.5,
+            //         asia: 2.1,
+            //         lamerica: 1,
+            //         meast: 0.8,
+            //         africa: 0.4,
+            //     },
+            // ];
+
+            // Create Y Axis
+            const yRenderer = am5xy.AxisRendererY.new(root, {});
+            const yAxis = chart.yAxes.push(
+                am5xy.CategoryAxis.new(root, {
+                    categoryField: "bookNm",
+                    renderer: yRenderer,
+                    tooltip: am5.Tooltip.new(root, {}),
+                })
+            );
+            yRenderer.grid.template.setAll({
+                location: 1,
+            });
+            yAxis.data.setAll(this.chartData);
+
+            // Create X Axis
+            const xAxis = chart.xAxes.push(
+                am5xy.ValueAxis.new(root, {
+                    min: 0,
+                    maxPrecision: 0,
+                    renderer: am5xy.AxisRendererX.new(root, {
+                        minGridDistance: 40,
+                        strokeOpacity: 0.1,
+                    }),
+                })
+            );
+
+            // Create legend
+            // const legend = chart.children.push(
+            //     am5.Legend.new(root, {
+            //         centerX: am5.p50,
+            //         x: am5.p50,
+            //     })
+            // );
+
+            // Function to create series
+            // const createSeries = (name, fieldName) => {
+            //     const series = chart.series.push(
+            //         am5xy.ColumnSeries.new(root, {
+            //             name,
+            //             stacked: true,
+            //             xAxis,
+            //             yAxis,
+            //             baseAxis: yAxis,
+            //             valueXField: fieldName,
+            //             categoryYField: "year",
+            //         })
+            //     );
+
+            //     series.columns.template.setAll({
+            //         // tooltipText: "{name}, {categoryY}: {valueX}",
+            //         tooltipY: am5.percent(90),
+            //     });
+            //     series.data.setAll(this.chartData);
+
+            //     series.appear();
+
+            //     series.bullets.push(() =>
+            //         am5.Bullet.new(root, {
+            //             sprite: am5.Label.new(root, {
+            //                 text: "{valueX}",
+            //                 fill: root.interfaceColors.get("alternativeText"),
+            //                 centerY: am5.p50,
+            //                 centerX: am5.p50,
+            //                 populateText: true,
+            //             }),
+            //         })
+            //     );
+
+            //     legend.data.push(series);
+            // };
+
+            // Create series
+            // createSeries("Europe", "europe");
+            // createSeries("North America", "namerica");
+            // createSeries("Asia", "asia");
+            // createSeries("Latin America", "lamerica");
+            // createSeries("Middle East", "meast");
+            // createSeries("Africa", "africa");
+
+            const series = chart.series.push(
+                am5xy.ColumnSeries.new(root, {
+                    name: "progressRate",
+                    xAxis: xAxis,
+                    yAxis: yAxis,
+                    baseAxis: yAxis,
+                    valueXField: "progressRate",
+                    categoryYField: "bookNm",
+                    // tooltipText: "{categoryY}: {valueX}",
+                })
+            );
+            series.columns.template.setAll({
+                tooltipY: am5.percent(90),
+            });
+
+            series.data.setAll(this.chartData);
+
+            series.bullets.push(() =>
+                am5.Bullet.new(root, {
+                    sprite: am5.Label.new(root, {
+                        text: "{valueX}",
+                        fill: root.interfaceColors.get("alternativeText"),
+                        centerY: am5.p50,
+                        centerX: am5.p50,
+                        populateText: true,
+                    }),
+                })
+            );
+            // Chart animation
+            chart.appear(1000, 100);
+        },
     },
-  };
-  </script>
-  
-  <style scoped>
-  /* Add necessary styles here */
-  </style>
-  
(No newline at end of file)
+};
+</script>
+
+<style scoped>
+/* Add necessary styles here */
+</style>
Add a comment
List