├── jest.config.js ├── media └── preview.gif ├── public ├── favicon.ico └── index.html ├── babel.config.js ├── src ├── assets │ └── vue-logo.png ├── lib.js ├── main.js ├── components │ ├── VueInputCalculator.vue │ └── CalculatorInterface.vue └── App.vue ├── lib ├── demo.html └── vue-input-calculator.umd.min.js ├── vue.config.js ├── .gitignore ├── tests └── unit │ ├── expGenerator.js │ └── calc.spec.js ├── LICENSE ├── package.json └── README.md /jest.config.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | preset: '@vue/cli-plugin-unit-jest' 3 | } 4 | -------------------------------------------------------------------------------- /media/preview.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/lih1989/vue-input-calculator/HEAD/media/preview.gif -------------------------------------------------------------------------------- /public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/lih1989/vue-input-calculator/HEAD/public/favicon.ico -------------------------------------------------------------------------------- /babel.config.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | presets: [ 3 | '@vue/cli-plugin-babel/preset' 4 | ] 5 | } 6 | -------------------------------------------------------------------------------- /src/assets/vue-logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/lih1989/vue-input-calculator/HEAD/src/assets/vue-logo.png -------------------------------------------------------------------------------- /src/lib.js: -------------------------------------------------------------------------------- 1 | import VueInputCalculator from './components/VueInputCalculator' 2 | export default VueInputCalculator 3 | -------------------------------------------------------------------------------- /src/main.js: -------------------------------------------------------------------------------- 1 | import { createApp } from 'vue' 2 | import App from './App.vue' 3 | 4 | const app = createApp(App); 5 | app.mount('#app'); 6 | -------------------------------------------------------------------------------- /lib/demo.html: -------------------------------------------------------------------------------- 1 | vue-input-calculator demo -------------------------------------------------------------------------------- /vue.config.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | publicPath: process.env.NODE_ENV === 'production' 3 | ? '/' 4 | : '/vue-input-calculator/', 5 | outputDir: process.env.NODE_ENV === 'production' 6 | ? __dirname+'/lib' 7 | : __dirname+'/demo', 8 | css: { 9 | extract: false 10 | } 11 | }; 12 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | .DS_Store 2 | node_modules 3 | /dist 4 | 5 | 6 | # local env files 7 | .env.local 8 | .env.*.local 9 | 10 | # Log files 11 | npm-debug.log* 12 | yarn-debug.log* 13 | yarn-error.log* 14 | pnpm-debug.log* 15 | 16 | # Editor directories and files 17 | .idea 18 | .vscode 19 | *.suo 20 | *.ntvs* 21 | *.njsproj 22 | *.sln 23 | *.sw? 24 | /demo/ 25 | -------------------------------------------------------------------------------- /public/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | <%= htmlWebpackPlugin.options.title %> 9 | 10 | 11 | 14 |
15 | 16 | 17 | 18 | -------------------------------------------------------------------------------- /tests/unit/expGenerator.js: -------------------------------------------------------------------------------- 1 | const signs = ['/','*','-','+']; 2 | 3 | function randomFloatRange(min, max) { 4 | return parseFloat((Math.random() * (max - min) + min).toFixed(5)); 5 | } 6 | function randomBoolean() { 7 | return Math.random() < 0.5; 8 | } 9 | 10 | function buildMathExp(numCount) { 11 | if (numCount === 1) 12 | return randomFloatRange(0, 10); 13 | 14 | let numLeft = Math.floor(numCount / 2); 15 | let leftSubTree = buildMathExp(numLeft); 16 | let numRight = Math.ceil(numCount / 2); 17 | let rightSubTree = buildMathExp(numRight); 18 | 19 | let m = Math.floor(randomFloatRange(0, signs.length)); 20 | let str = signs[m]; 21 | return (randomBoolean ? '0':'') + leftSubTree + ' ' + str + ' ' + (randomBoolean ? '':'0') + rightSubTree; 22 | } 23 | 24 | export { 25 | buildMathExp 26 | } 27 | -------------------------------------------------------------------------------- /tests/unit/calc.spec.js: -------------------------------------------------------------------------------- 1 | import { shallowMount } from '@vue/test-utils' 2 | import CalculatorInterface from '@/components/CalculatorInterface' 3 | import { buildMathExp } from "./expGenerator"; 4 | 5 | describe('CalculatorInterface.vue', () => { 6 | it('При расчётах не возникают ошибки и всегла возвращается число!', () => { 7 | const wrapper = shallowMount(CalculatorInterface, { 8 | propsData: { 9 | show: true, 10 | floatResultFixedCount:3 11 | } 12 | }); 13 | 14 | let ch = 0; 15 | while (ch < 20000){ 16 | let exp = buildMathExp(3); 17 | let expArray = exp.split(' '); 18 | for (let value of expArray){ 19 | wrapper.vm.prepareInput(value); 20 | } 21 | wrapper.vm.prepareInput('='); 22 | expect(wrapper.vm.error).toBe(false); 23 | expect(Number.isNaN(Number.parseFloat(wrapper.vm.expresion))).toBe(false); 24 | wrapper.vm.clear(); 25 | ch++; 26 | } 27 | }) 28 | }); 29 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2020 lih1989 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. -------------------------------------------------------------------------------- /src/components/VueInputCalculator.vue: -------------------------------------------------------------------------------- 1 | 9 | 10 | 85 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "vue-input-calculator", 3 | "version": "1.0.1", 4 | "description": "Calculator input component. Mobile friendly.", 5 | "author": "Ivan Lihomanov ", 6 | "scripts": { 7 | "serve": "vue-cli-service serve --port 3000", 8 | "build": "vue-cli-service build --target lib --name vue-input-calculator src/lib.js", 9 | "test:unit": "vue-cli-service test:unit", 10 | "lint": "vue-cli-service lint", 11 | "deploy": "gh-pages -d demo", 12 | "predeploy": "vue-cli-service build --mode demo" 13 | }, 14 | "main": "./lib/vue-input-calculator.common.js", 15 | "files": [ 16 | "lib", 17 | "src" 18 | ], 19 | "devDependencies": { 20 | "@babel/eslint-parser": "^7", 21 | "@babel/eslint-plugin": "^7", 22 | "@vue/cli-plugin-babel": "~5.0", 23 | "@vue/cli-plugin-eslint": "~5.0", 24 | "@vue/cli-plugin-unit-jest": "^5", 25 | "@vue/cli-service": "~5.0", 26 | "@vue/test-utils": "^2.0.0-rc.17", 27 | "@vue/vue3-jest": "^27.0.0-alpha.4", 28 | "core-js": "^3.6.5", 29 | "eslint": "^8", 30 | "eslint-plugin-vue": "^8", 31 | "gh-pages": "^3.1.0", 32 | "sass": "^1.26.10", 33 | "sass-loader": "^9.0.3", 34 | "vue": "^3.2" 35 | }, 36 | "eslintConfig": { 37 | "root": true, 38 | "env": { 39 | "node": true 40 | }, 41 | "extends": [ 42 | "plugin:vue/essential", 43 | "eslint:recommended" 44 | ], 45 | "parserOptions": { 46 | "parser": "@babel/eslint-parser" 47 | }, 48 | "rules": {}, 49 | "overrides": [ 50 | { 51 | "files": [ 52 | "**/__tests__/*.{j,t}s?(x)", 53 | "**/tests/unit/**/*.spec.{j,t}s?(x)" 54 | ], 55 | "env": { 56 | "jest": true 57 | } 58 | } 59 | ] 60 | }, 61 | "browserslist": [ 62 | "> 1%", 63 | "last 2 versions", 64 | "not dead" 65 | ], 66 | "homepage": "https://lih1989.github.io/vue-input-calculator/", 67 | "keywords": [ 68 | "vue", 69 | "input calculator", 70 | "javascript", 71 | "vuejs", 72 | "vue.js", 73 | "input", 74 | "calculator", 75 | "vue component" 76 | ], 77 | "license": "MIT", 78 | "repository": { 79 | "type": "git", 80 | "url": "git+https://github.com/lih1989/vue-input-calculator.git" 81 | } 82 | } 83 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # vue-input-calculator 2 | 3 | [![Software License](https://img.shields.io/badge/license-MIT-brightgreen.svg?style=flat-square)](LICENSE) 4 | [![Latest Version on NPM](https://img.shields.io/npm/v/vue-input-calculator.svg?style=flat-square)](https://www.npmjs.com/package/vue-input-calculator) 5 | [![npm](https://img.shields.io/npm/dt/vue-input-calculator.svg?style=flat-square)](https://www.npmjs.com/package/vue-input-calculator) 6 | [![Vue 3.x](https://img.shields.io/badge/vue-2.x-brightgreen.svg?style=flat-square)](https://vuejs.org) 7 | 8 | > Calculator interface for input field. Touch & Keyboard input. Vue.js component. 9 | > 10 | > Vue 2 < ver. 1.0.0 11 | > 12 | > Vue 3 > ver. 1.0.0 13 | ## Demo 14 | [View demo](https://lih1989.github.io/vue-input-calculator/) 15 | 16 | [![demo](https://raw.githubusercontent.com/lih1989/vue-input-calculator/master/media/preview.gif)](https://lih1989.github.io/vue-input-calculator/) 17 | ## Install 18 | 19 | ```bash 20 | yarn add vue-input-calculator 21 | ``` 22 | 23 | Or 24 | 25 | ```bash 26 | npm install --save vue-input-calculator 27 | ``` 28 | 29 | ## Add to project 30 | 31 | #### Global 32 | ```js 33 | // main.js 34 | import VueInputCalculator from "vue-input-calculator"; 35 | Vue.component('vue-input-calculator', VueInputCalculator); 36 | ``` 37 | 38 | #### Local Usage 39 | 40 | ```html 41 | 49 | 59 | ``` 60 | 61 | ## Setup 62 | ### Parameters 63 | 64 | Props(Parameter) | Type | Default | Description 65 | --------- | ---- | ------- | ----------- 66 | v-model (*required*) | `String, Number` | - | target input value 67 | auto-apply | `Boolean` | `false` | auto continue/close on calc result 68 | enable-keyboard | `Boolean` | `false` | enable keyboard input 69 | persistent | `Boolean` | `false` | disable backdrop click to cancel (outside click) 70 | readonly-input | `Boolean` | `true` | calculator input read only 71 | is-history-logs | `Boolean` | `true` | show math operations log 72 | z-index | `String, Number` | 9999 | layer calculator z-index position 73 | place | `in-place\|modal` | `modal` | `in-place` puts interface in its DOM position, `modal` or other displays on click input. 74 | trigger-wrapper-class | `String` | - | trigger for open calculator class styles 75 | text-color | `String` | `#ffffff` | calculator text color 76 | bg-color | `String` | `#2f2f31` | calculator background color 77 | event-buttons-bg-color | `String` | `#424345` | calculator buttons color(c, ›) 78 | number-buttons-bg-color | `String` | `#616163` | calculator buttons color(0-9.) 79 | action-buttons-bg-color | `String` | `#f49e3f` | calculator buttons color(+-\*=) 80 | action-success-button-bg-color | `String` | `#3ff451` | calculator OK button color 81 | 82 | ## License 83 | [The MIT License](http://opensource.org/licenses/MIT) 84 | 85 | ### Vue CLI configuration 86 | See [Configuration Reference](https://cli.vuejs.org/config/). 87 | -------------------------------------------------------------------------------- /src/App.vue: -------------------------------------------------------------------------------- 1 | 82 | 83 | 98 | 175 | -------------------------------------------------------------------------------- /src/components/CalculatorInterface.vue: -------------------------------------------------------------------------------- 1 | 93 | 94 | 326 | 327 | 509 | -------------------------------------------------------------------------------- /lib/vue-input-calculator.umd.min.js: -------------------------------------------------------------------------------- 1 | (function(t,e){"object"===typeof exports&&"object"===typeof module?module.exports=e(require("vue")):"function"===typeof define&&define.amd?define([],e):"object"===typeof exports?exports["vue-input-calculator"]=e(require("vue")):t["vue-input-calculator"]=e(t["Vue"])})("undefined"!==typeof self?self:this,(function(__WEBPACK_EXTERNAL_MODULE__7203__){return function(){var __webpack_modules__={7679:function(t,e){var r,n,o;(function(c,i){n=[],r=i,o="function"===typeof r?r.apply(e,n):r,void 0===o||(t.exports=o)})("undefined"!==typeof self&&self,(function(){function t(){var e=Object.getOwnPropertyDescriptor(document,"currentScript");if(!e&&"currentScript"in document&&document.currentScript)return document.currentScript;if(e&&e.get!==t&&document.currentScript)return document.currentScript;try{throw new Error}catch(p){var r,n,o,c=/.*at [^(]*\((.*):(.+):(.+)\)$/gi,i=/@([^@]*):(\d+):(\d+)\s*$/gi,a=c.exec(p.stack)||i.exec(p.stack),u=a&&a[1]||!1,s=a&&a[2]||!1,l=document.location.href.replace(document.location.hash,""),f=document.getElementsByTagName("script");u===l&&(r=document.documentElement.outerHTML,n=new RegExp("(?:[^\\n]+?\\n){0,"+(s-2)+"}[^<]*