├── .babelrc ├── .eslintignore ├── .eslintrc.js ├── .gitignore ├── .travis.yml ├── LICENSE ├── README.md ├── package.json ├── publish-demo.js ├── src ├── App.vue ├── DoughnutChart.vue ├── doughnut-chart.js ├── index.ejs └── main.js ├── webpack.config.js ├── webpack.config.prod.js └── yarn.lock /.babelrc: -------------------------------------------------------------------------------- 1 | { 2 | "presets": [ 3 | ["@babel/preset-env", { 4 | "modules": false, 5 | "useBuiltIns": "usage" 6 | }] 7 | ], 8 | "env": { 9 | "test": { 10 | "presets": [ 11 | ["@babel/preset-env", { 12 | "targets": { 13 | "node": "current" 14 | } 15 | }] 16 | ] 17 | } 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /.eslintignore: -------------------------------------------------------------------------------- 1 | build/*.js 2 | config/*.js 3 | dist/*.js 4 | test/*.js 5 | node_modules 6 | *.config* -------------------------------------------------------------------------------- /.eslintrc.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | env: { 3 | browser: true, 4 | commonjs: true, 5 | es6: true, 6 | jest: true 7 | }, 8 | extends: ['eslint:recommended', 'plugin:vue/recommended'], 9 | plugins: ['html'], 10 | parserOptions: { 11 | ecmaVersion: 2018, 12 | sourceType: 'module' 13 | }, 14 | rules: { 15 | indent: ['error', 2], 16 | 'linebreak-style': ['error', 'unix'], 17 | quotes: ['error', 'single'], 18 | semi: ['error', 'never'], 19 | 'no-console': 'off' 20 | } 21 | }; 22 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | npm-debug.log* 5 | yarn-debug.log* 6 | yarn-error.log* 7 | 8 | # Runtime data 9 | pids 10 | *.pid 11 | *.seed 12 | *.pid.lock 13 | 14 | # Directory for instrumented libs generated by jscoverage/JSCover 15 | lib-cov 16 | 17 | # Coverage directory used by tools like istanbul 18 | coverage 19 | 20 | # nyc test coverage 21 | .nyc_output 22 | 23 | # Grunt intermediate storage (http://gruntjs.com/creating-plugins#storing-task-files) 24 | .grunt 25 | 26 | # Bower dependency directory (https://bower.io/) 27 | bower_components 28 | 29 | # node-waf configuration 30 | .lock-wscript 31 | 32 | # Compiled binary addons (https://nodejs.org/api/addons.html) 33 | build/Release 34 | 35 | # Dependency directories 36 | node_modules/ 37 | jspm_packages/ 38 | 39 | # TypeScript v1 declaration files 40 | typings/ 41 | 42 | # Optional npm cache directory 43 | .npm 44 | 45 | # Optional eslint cache 46 | .eslintcache 47 | 48 | # Optional REPL history 49 | .node_repl_history 50 | 51 | # Output of 'npm pack' 52 | *.tgz 53 | 54 | # Yarn Integrity file 55 | .yarn-integrity 56 | 57 | # dotenv environment variables file 58 | .env 59 | 60 | # next.js build output 61 | .next 62 | dist/ 63 | dist-demo/ 64 | -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | language: node_js 2 | node_js: '10.16.3' 3 | branches: 4 | only: 5 | - master 6 | cache: 7 | directories: 8 | - node_modules 9 | script: 10 | - npm run lint 11 | - npm run build 12 | deploy: 13 | provider: pages 14 | skip-cleanup: true 15 | github-token: $GITHUB_TOKEN 16 | keep-history: true 17 | local-dir: dist-demo 18 | verbose: true 19 | on: 20 | branch: master 21 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2018 Irfan Maulana 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # 🍩 Vue Doughnut Chart 2 | 3 | > Doughnut chart component for Vue.js, originally created by Greg Willson in [codepen](https://codepen.io/biomassives/pen/yaZwQw) 4 | 5 | [![version](https://img.shields.io/npm/v/vue-doughnut-chart.svg)](https://www.npmjs.com/package/vue-doughnut-chart) ![minified](https://badgen.net/bundlephobia/minzip/vue-doughnut-chart) [![downloads](https://img.shields.io/npm/dt/vue-doughnut-chart.svg)](https://www.npmjs.com/package/vue-doughnut-chart) [![Travis](https://img.shields.io/travis/mazipan/vue-doughnut-chart.svg)](https://travis-ci.org/mazipan/vue-doughnut-chart) [![Dependabot Status](https://api.dependabot.com/badges/status?host=github&repo=mazipan/vue-doughnut-chart)](https://dependabot.com) 6 | 7 | ## Demo 8 | 9 | [https://mazipan.github.io/vue-doughnut-chart](https://mazipan.github.io/vue-doughnut-chart) 10 | 11 | ## Install 12 | 13 | ```shell 14 | yarn add vue-doughnut-chart 15 | # OR 16 | npm i vue-doughnut-chart 17 | ``` 18 | 19 | ## Use in components 20 | 21 | ```js 22 | import DoughnutChart from 'vue-doughnut-chart' 23 | 24 | export default { 25 | components: { 26 | DoughnutChart 27 | } 28 | } 29 | ``` 30 | 31 | ## Props 32 | 33 | | Props Name | Type | Default Value |Description | 34 | |-----------------------|-----------|---------------|---------------------------------------------| 35 | | `percent` | Number | 0 | | 36 | | `foregroundColor` | String | '#1993ff' | | 37 | | `backgroundColor` | String | '#ecf6ff' | | 38 | | `strokeWidth` | Number | 10 | | 39 | | `radius` | Number | 85 | | 40 | | `width` | Number | 200 | | 41 | | `height` | Number | 200 | | 42 | | `classValue` | String | '' | | 43 | | `visibleValue` | Boolean | false | | 44 | | `valueCountUp` | Boolean | false | | 45 | | `valueCountUpDuration`| Number | 2000 | Number in milliseconds | 46 | | `valueCountUpDelay` | Number | 500 | Percent count-up delay (for changing values)| 47 | | `customPercentSize` | Number | 40 | Percent font size in pixels (max 60) | 48 | | `passTextAsHtml` | Boolean | false | Allows to add simple html into label | 49 | | `customText` | String | '' | Label value | 50 | | `customTextColor` | String | '#1993ff' | Valid HEX color code or CSS color for label | 51 | | `customTextSize` | Number | 15 | Label font size in pixels (max 22) | 52 | 53 | ----- 54 | 55 | Bringing to NPM Registry by Irfan Maulana © 2018 56 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "vue-doughnut-chart", 3 | "description": "Doughnut chart component for Vue.js, originally created by Greg Willson", 4 | "version": "0.3.0", 5 | "license": "MIT", 6 | "author": "Irfan Maulana (https://github.com/mazipan/)", 7 | "homepage": "https://mazipan.github.io/vue-doughnut-chart/", 8 | "main": "./dist/doughnut-chart.js", 9 | "files": [ 10 | "dist/doughnut-chart.js", 11 | "dist/doughnut-chart.js.gz", 12 | "src/doughnut-chart.js", 13 | "src/DoughnutChart.vue" 14 | ], 15 | "keywords": [ 16 | "vue chart", 17 | "vue doughnut chart", 18 | "vue gauge chart" 19 | ], 20 | "repository": { 21 | "type": "git", 22 | "url": "https://github.com/mazipan/vue-doughnut-chart.git" 23 | }, 24 | "bugs": { 25 | "url": "https://github.com/mazipan/vue-doughnut-chart/issues" 26 | }, 27 | "scripts": { 28 | "dev": "cross-env NODE_ENV=development webpack-dev-server --inline --hot --open", 29 | "build:demo": "rm -rf dist-demo && cross-env NODE_ENV=production webpack --progress --config webpack.config.js", 30 | "build:lib": "rm -rf dist && cross-env NODE_ENV=production webpack --progress --config webpack.config.prod.js", 31 | "test": "./node_modules/.bin/jest --coverage", 32 | "dist": "npm run build:lib && npm run build:demo", 33 | "build": "npm run dist", 34 | "lint": "node node_modules/eslint/bin/eslint.js --ext .js,.vue src --fix --no-ignore", 35 | "publish-demo": "node ./publish-demo.js" 36 | }, 37 | "devDependencies": { 38 | "@babel/core": "7.12.3", 39 | "@babel/preset-env": "7.12.1", 40 | "@vue/test-utils": "1.1.1", 41 | "autoprefixer": "10.0.1", 42 | "babel-core": "7.0.0-bridge.0", 43 | "babel-jest": "26.6.1", 44 | "babel-loader": "8.1.0", 45 | "compression-webpack-plugin": "6.0.4", 46 | "copy-webpack-plugin": "6.2.1", 47 | "cross-env": "7.0.2", 48 | "css-loader": "5.0.0", 49 | "eslint": "7.12.1", 50 | "eslint-plugin-html": "6.1.0", 51 | "eslint-plugin-vue": "7.1.0", 52 | "gh-pages": "3.1.0", 53 | "html-webpack-plugin": "4.5.0", 54 | "jest": "26.6.1", 55 | "jest-serializer-vue": "2.0.2", 56 | "node-sass": "4.14.1", 57 | "sass-loader": "10.0.4", 58 | "vue": "2.6.12", 59 | "vue-jest": "3.0.7", 60 | "vue-loader": "15.9.5", 61 | "vue-script2": "2.1.0", 62 | "vue-style-loader": "4.1.2", 63 | "vue-template-compiler": "2.6.12", 64 | "webpack": "5.3.2", 65 | "webpack-cli": "4.1.0", 66 | "webpack-dev-server": "3.11.0", 67 | "webpack-serve": "3.2.0", 68 | "workbox-webpack-plugin": "5.1.4" 69 | }, 70 | "dependencies": {} 71 | } 72 | -------------------------------------------------------------------------------- /publish-demo.js: -------------------------------------------------------------------------------- 1 | const ghpages = require('gh-pages') 2 | const BRANCH = 'gh-pages' 3 | const TODAY = new Date().toLocaleString() 4 | const FOLDER_DIST = 'dist-demo' 5 | 6 | console.log(`start publishing folder ${FOLDER_DIST} to ${BRANCH}`) 7 | 8 | ghpages.publish(FOLDER_DIST, { 9 | branch: BRANCH, 10 | message: `Publishing folder ${FOLDER_DIST} to ${BRANCH} in ${TODAY}` 11 | }, () => { 12 | console.log(`done publishing folder ${FOLDER_DIST} to ${BRANCH}`) 13 | }) -------------------------------------------------------------------------------- /src/App.vue: -------------------------------------------------------------------------------- 1 | 48 | 49 | 65 | 66 | 166 | 167 | -------------------------------------------------------------------------------- /src/DoughnutChart.vue: -------------------------------------------------------------------------------- 1 | 53 | 54 | 256 | 274 | -------------------------------------------------------------------------------- /src/doughnut-chart.js: -------------------------------------------------------------------------------- 1 | import DoughnutChart from './DoughnutChart.vue' 2 | 3 | export default DoughnutChart -------------------------------------------------------------------------------- /src/index.ejs: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | Vue Doughnut Chart | Irfan Maulana 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 86 | 94 | 95 | 96 |
97 |
98 |
99 |

100 | Vue Doughnut Chart 101 |

102 |

103 | Doughnut chart component for Vue.js, originally created by Greg Willson in codepen 104 |

105 |
106 |
107 |
108 | 109 |
110 |
111 |

Welcome to Vue-Doughnut-Chart

112 | 113 |
114 | 115 |
116 |
117 | 118 | 133 | 134 | 135 | 136 | 142 | 145 | 146 | 147 | 148 | 149 | 150 | -------------------------------------------------------------------------------- /src/main.js: -------------------------------------------------------------------------------- 1 | import Vue from 'vue' 2 | import App from './App.vue' 3 | 4 | new Vue({ 5 | el: '#app', 6 | render: h => h(App) 7 | }) -------------------------------------------------------------------------------- /webpack.config.js: -------------------------------------------------------------------------------- 1 | const path = require('path'); 2 | const webpack = require('webpack'); 3 | const HtmlWebpackPlugin = require('html-webpack-plugin') 4 | const { GenerateSW } = require('workbox-webpack-plugin') 5 | const VueLoaderPlugin = require('vue-loader/lib/plugin') 6 | 7 | const NODE_ENV = process.env.NODE_ENV; 8 | 9 | const setPath = function(folderName) { 10 | return path.join(__dirname, folderName); 11 | } 12 | 13 | const buildingForLocal = () => { 14 | return (NODE_ENV === 'development'); 15 | }; 16 | 17 | const setPublicPath = () => { 18 | return buildingForLocal() ? '/' : '/vue-doughnut-chart/'; 19 | }; 20 | 21 | const extractHTML = new HtmlWebpackPlugin({ 22 | title: 'History Search', 23 | filename: 'index.html', 24 | inject: true, 25 | template: setPath('/src/index.ejs'), 26 | minify: { 27 | removeAttributeQuotes: true, 28 | collapseWhitespace: true, 29 | html5: true, 30 | minifyCSS: true, 31 | removeComments: true, 32 | removeEmptyAttributes: true 33 | }, 34 | environment: process.env.NODE_ENV 35 | }); 36 | 37 | 38 | const config = { 39 | entry: { 40 | app: path.join(setPath('src'), 'main.js') 41 | }, 42 | output: { 43 | path: buildingForLocal() ? path.resolve(__dirname) : setPath('dist-demo'), 44 | publicPath: setPublicPath(), 45 | filename: buildingForLocal() ? 'js/[name].js' : 'js/[name].[hash].js' 46 | }, 47 | optimization:{ 48 | runtimeChunk: false, 49 | splitChunks: { 50 | chunks: "all", //Taken from https://gist.github.com/sokra/1522d586b8e5c0f5072d7565c2bee693 51 | } 52 | }, 53 | resolveLoader: { 54 | modules: [ 'node_modules' ], 55 | }, 56 | resolve: { 57 | alias: { 58 | 'vue$': 'vue/dist/vue.esm.js' 59 | }, 60 | extensions: ['*', '.js', '.vue', '.json'] 61 | }, 62 | mode: buildingForLocal() ? 'development' : 'production', 63 | devServer: { 64 | historyApiFallback: true, 65 | noInfo: false 66 | }, 67 | plugins: [ 68 | new VueLoaderPlugin(), 69 | extractHTML, 70 | new webpack.DefinePlugin({ 71 | 'process.env': { 72 | isStaging: (NODE_ENV === 'development' || NODE_ENV === 'staging'), 73 | NODE_ENV: '"'+NODE_ENV+'"' 74 | } 75 | }), 76 | new GenerateSW({ 77 | swDest: 'sw.js' 78 | }) 79 | ], 80 | module: { 81 | rules: [ 82 | { 83 | test: /\.css$/, 84 | use: [ 85 | 'vue-style-loader', 86 | 'css-loader' 87 | ], 88 | }, 89 | { 90 | test: /\.scss$/, 91 | use: [ 92 | 'vue-style-loader', 93 | 'css-loader', 94 | 'sass-loader' 95 | ], 96 | }, 97 | { 98 | test: /\.sass$/, 99 | use: [ 100 | 'vue-style-loader', 101 | 'css-loader', 102 | 'sass-loader?indentedSyntax' 103 | ], 104 | }, 105 | { 106 | test: /\.vue$/, 107 | loader: 'vue-loader', 108 | options: { 109 | loaders: { 110 | js: 'babel-loader', 111 | scss: 'vue-style-loader!css-loader!sass-loader', 112 | sass: 'vue-style-loader!css-loader!sass-loader?indentedSyntax' 113 | } 114 | } 115 | }, 116 | { 117 | test: /\.m?js$/, 118 | exclude: /(node_modules|bower_components)/, 119 | use: { 120 | loader: 'babel-loader', 121 | options: { 122 | presets: ['@babel/preset-env'] 123 | } 124 | } 125 | } 126 | ] 127 | } 128 | }; 129 | module.exports = config; 130 | -------------------------------------------------------------------------------- /webpack.config.prod.js: -------------------------------------------------------------------------------- 1 | const path = require('path'); 2 | const webpack = require('webpack'); 3 | const VueLoaderPlugin = require('vue-loader/lib/plugin'); 4 | const CompressionPlugin = require("compression-webpack-plugin") 5 | 6 | const NODE_ENV = process.env.NODE_ENV; 7 | 8 | const setPath = function(folderName) { 9 | return path.join(__dirname, folderName); 10 | } 11 | 12 | const config = { 13 | entry: { 14 | app: './src/doughnut-chart.js' 15 | }, 16 | output: { 17 | filename: "doughnut-chart.js", 18 | library: 'DoughnutChart', 19 | libraryTarget: 'commonjs2' 20 | }, 21 | resolveLoader: { 22 | modules: [ 23 | setPath('node_modules') 24 | ] 25 | }, 26 | mode: 'production', 27 | plugins: [ 28 | new webpack.DefinePlugin({ 29 | 'process.env': { 30 | isStaging: (NODE_ENV === 'development'), 31 | NODE_ENV: '"'+NODE_ENV+'"' 32 | } 33 | }), 34 | new VueLoaderPlugin(), 35 | new CompressionPlugin({ 36 | algorithm: 'gzip' 37 | }) 38 | ], 39 | module: { 40 | rules: [ 41 | { 42 | test: /\.css$/, 43 | use: [ 44 | 'vue-style-loader', 45 | 'css-loader' 46 | ], 47 | }, 48 | { 49 | test: /\.scss$/, 50 | use: [ 51 | 'vue-style-loader', 52 | 'css-loader', 53 | 'sass-loader' 54 | ], 55 | }, 56 | { 57 | test: /\.sass$/, 58 | use: [ 59 | 'vue-style-loader', 60 | 'css-loader', 61 | 'sass-loader?indentedSyntax' 62 | ], 63 | }, 64 | { 65 | test: /\.vue$/, 66 | loader: 'vue-loader', 67 | options: { 68 | loaders: { 69 | js: 'babel-loader', 70 | scss: 'vue-style-loader!css-loader!sass-loader', 71 | sass: 'vue-style-loader!css-loader!sass-loader?indentedSyntax' 72 | } 73 | } 74 | }, 75 | { 76 | test: /\.m?js$/, 77 | exclude: /(node_modules|bower_components)/, 78 | use: { 79 | loader: 'babel-loader', 80 | options: { 81 | presets: ['@babel/preset-env'] 82 | } 83 | } 84 | } 85 | ] 86 | } 87 | }; 88 | module.exports = config; 89 | --------------------------------------------------------------------------------