From 1c273aa831e7412b868b73fafae2615f57371ea4 Mon Sep 17 00:00:00 2001 From: Wesley Ford Date: Fri, 22 Sep 2023 16:17:45 -0500 Subject: [PATCH] v0.9.24 (#3878) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * Added mobileModal to Clockpicker Component (#3840) * Added mobileModal to Clockpicker Component * Added mobileModal to Timepicker Component * Input-id prop checkbox * feat: 🎸 Adding a new prop to set the id for inner input Adding a new prop to set the id for inner input for checkbox component * docs: ✏️ Adding helping data on checkbox api file * refactor: πŸ’‘ Changing prop name * Fix: Logo not displaying in the Sidebar documentation (#3838) (#3839) * Fix: Disabled radio button has cursor 'pointer' (#3826) * Fix: Sidebar image not displaying in the documentation (#3838) * Fix: Expired and broken websites in expo page (#3780) (#3845) * Number input null issue fix - #3698 (#3847) * number input value fix - #3698 * checks fix --------- Co-authored-by: Amal Mathew <122610766+amal-qb@users.noreply.github.com> * Numberinput: fix long-press breaking when disabled (#3860) * Numberinput: fix long-press breaking when disabled * Numberinput: fix long-press unit test * Update notification.js (#3867) Updated documentation for attribute `auto-close` from #3855 * Fix: Full width sidebar doesn't have a close button (#3802) (#3856) * Fix: Expired and broken websites in expo page (#3780) * Fix: Full width sidebar doesn't have a close button (#3802) * Fix: Full width sidebar doesn't have a close button (#3802) - format code * Fix: Full width sidebar doesn't have a close button (#3802) - Add documentation * fix: infinite loop on Datepicker (#3877) - Fixes the bug that `Datepicker` ended up with an infinite loop when a user tried to move focus onto an unselectable cell. * Bump Version From v0.9.23 to v0.9.24 * Fix: Validation error on Input not reset by programmatically correcting the value (#3884) (#3886) * fix(lib): Input not validate on value prop change - Fixes the bug that `Input` did not validate an updated value if `value` prop was updated from outside; i.e., without user interaction. Runs validation whenever `value` is changed from outside. It determines the update is from outside if `computedValue` and the new value are different. Intentionally uses `!=` instead of `!==`, because `computedValue` and `value` may be either string or number. * test(lib): test validation on Input - Introduces new test cases for `Input` that test validation runs on relevant events: - "input" event - "change" event - `value` prop is programmatically changed Also tests cases where the `Input` value has v-model binding. These tests make sure that the chain of events won't run validation twice on the same value. * Fix: Validation error on Field with multiple child components (addons) persists after value is corrected (#3883) (#3885) * fix(lib): validation error on addons persisted - Fixes the bug that a validation error on a `Field` that wraps multile child components (has addons) persisted. `Field` wraps its slot in another `Field` (wrapper) if the slot is consisting of multiple components. It used to propagate `newType` to the wrapper, but this prevented the type of the wrapper updated once `newType` was set due to the line: https://github.com/buefy/buefy/blob/6f41e91bd24dfef8f680f27313e07b488ddcfc1d/src/utils/FormElementMixin.js#L137 Propagates `type` instead of `newType` to the wrapper. * test(lib): add test for Field's type - Adds a new test case for `Field` that tests if `Field` containing multiple components (addons) reflects the validation status of a wrapped input. This verifies the fix of the bug that `Field` with addons did not update its validation status (`newType`) once it was set. * Add nearbyMonthDays prop support to Datetimepicker (#3881) * Add nearbyMonthDays prop support to Datetimepicker Add Datepicker component prop `nearby-month-days` to Datetimepicker component * FIX lint Datetimepicker.vue * Use Datepicker default behavior for nearbyMonthDays prop * Update datetimepicker api doc with nearbyMonthDays prop * Update Twitter and Sponsor Links (#3888) * Updated The Documentation's Twitter Link * Updated Sponsor Links * Update FUNDING.yml * Update Package Json * Add Workflow to Publish Buefy on PR to Master --------- Co-authored-by: julzELO <73643910+julzELO@users.noreply.github.com> Co-authored-by: AarΓ³n J. Montes <32050436+ajomuch92@users.noreply.github.com> Co-authored-by: Amal Mathew <122610766+amal-qb@users.noreply.github.com> Co-authored-by: navedqb <109583873+navedqb@users.noreply.github.com> Co-authored-by: Sylvain Marty <10723351+SylvainMarty@users.noreply.github.com> Co-authored-by: Kikuo Emoto Co-authored-by: Guillaume Mercey --- .github/FUNDING.yml | 4 +- .github/workflows/npm_deploy.yml | 23 +++ docs/components/TheNavbar.vue | 2 +- docs/data/expo.json | 33 +--- .../pages/components/checkbox/api/checkbox.js | 7 + .../components/clockpicker/api/clockpicker.js | 7 + .../components/datepicker/api/datepicker.js | 7 + .../datetimepicker/api/datetimepicker.js | 7 + .../notification/api/notification.js | 2 +- docs/pages/components/sidebar/api/sidebar.js | 2 +- .../components/sidebar/examples/ExSimple.vue | 2 +- .../components/sidebar/examples/ExStatic.vue | 2 +- .../components/timepicker/api/timepicker.js | 7 + package-lock.json | 159 ++++++++++++++---- package.json | 4 +- src/components/checkbox/Checkbox.vue | 5 + src/components/clockpicker/Clockpicker.vue | 1 + .../datepicker/DatepickerTableRow.vue | 2 +- .../datetimepicker/Datetimepicker.vue | 5 + src/components/field/Field.spec.js | 23 +++ src/components/field/Field.vue | 2 +- src/components/input/Input.spec.js | 84 +++++++++ src/components/input/Input.vue | 9 + .../numberinput/Numberinput.spec.js | 4 +- src/components/numberinput/Numberinput.vue | 10 +- src/components/sidebar/Sidebar.vue | 16 ++ src/components/timepicker/Timepicker.vue | 1 + src/scss/components/_sidebar.scss | 9 + src/utils/TimepickerMixin.js | 4 + src/utils/config.js | 1 + 30 files changed, 358 insertions(+), 86 deletions(-) create mode 100644 .github/workflows/npm_deploy.yml diff --git a/.github/FUNDING.yml b/.github/FUNDING.yml index 5927c571c..9b1124d46 100644 --- a/.github/FUNDING.yml +++ b/.github/FUNDING.yml @@ -1,3 +1,5 @@ # These are supported funding model platforms -custom: https://www.paypal.me/wtommasi +custom: + - https://ko-fi.com/kemoto + - https://ko-fi.com/wesdevpro \ No newline at end of file diff --git a/.github/workflows/npm_deploy.yml b/.github/workflows/npm_deploy.yml new file mode 100644 index 000000000..23e550acd --- /dev/null +++ b/.github/workflows/npm_deploy.yml @@ -0,0 +1,23 @@ +name: Publish buefy to NPM +on: + push: + branches: + - master +jobs: + build: + runs-on: ubuntu-latest + permissions: + contents: read + packages: write + steps: + - uses: actions/checkout@v3 + # Setup .npmrc file to publish to GitHub Packages + - uses: actions/setup-node@v3 + with: + node-version: '16.x' + registry-url: 'https://registry.npmjs.org/' + scope: 'buefy' + - run: npm ci + - run: npm publish --access public + env: + NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }} \ No newline at end of file diff --git a/docs/components/TheNavbar.vue b/docs/components/TheNavbar.vue index d27f652ed..c7d245cba 100644 --- a/docs/components/TheNavbar.vue +++ b/docs/components/TheNavbar.vue @@ -40,7 +40,7 @@ diff --git a/docs/data/expo.json b/docs/data/expo.json index b0d64e948..0e8e475c0 100644 --- a/docs/data/expo.json +++ b/docs/data/expo.json @@ -11,18 +11,6 @@ "img": "discordtemplates.png", "url": "https://discordtemplates.com/" }, - { - "title": "Crawly", - "date": "2020-08-04", - "img": "crawly.png", - "url": "https://crawly.app/" - }, - { - "title": "Yakety", - "date": "2020-08-04", - "img": "yakety.png", - "url": "https://yakety.co.uk/" - }, { "title": "KodaDot", "date": "2020-08-04", @@ -78,12 +66,6 @@ "img": "edutechno.png", "url": "https://portail.edutechno.ca/" }, - { - "title": "Wotel", - "date": "2020-02-06", - "img": "wotel.png", - "url": "https://wotel.dev/" - }, { "title": "Swap", "date": "2020-01-29", @@ -96,12 +78,6 @@ "img": "sponsus.png", "url": "https://sponsus.org/" }, - { - "title": "Dogs Welcome", - "date": "2019-11-05", - "img": "dogswelcome.png", - "url": "https://dogswelcome.in/" - }, { "title": "Rate My Meeting", "date": "2019-11-05", @@ -187,13 +163,6 @@ "img": "nestandcut.png", "url": "https://nestandcut.com" }, - { - "title": "Okuna", - "date": "2019-04-24", - "img": "openbook.png", - "url": "https://www.okuna.io", - "featured": true - }, { "title": "Switchblade", "date": "2019-04-24", @@ -235,7 +204,7 @@ "title": "Salamander Garten", "date": "2019-04-24", "img": "salamander-garten.png", - "url": "https://voranalyse.salamander-garten.ch" + "url": "https://www.salamander-garten.ch" }, { "title": "Pumpipumpe Map", diff --git a/docs/pages/components/checkbox/api/checkbox.js b/docs/pages/components/checkbox/api/checkbox.js index cd3bf98c3..9a0df4448 100644 --- a/docs/pages/components/checkbox/api/checkbox.js +++ b/docs/pages/components/checkbox/api/checkbox.js @@ -81,6 +81,13 @@ export default [ type: 'String', values: 'β€”', default: 'β€”' + }, + { + name: 'input-id', + description: 'String to set the inner input id', + type: 'String', + values: 'β€”', + default: 'β€”' } ], events: [ diff --git a/docs/pages/components/clockpicker/api/clockpicker.js b/docs/pages/components/clockpicker/api/clockpicker.js index 9acf50101..936aba998 100644 --- a/docs/pages/components/clockpicker/api/clockpicker.js +++ b/docs/pages/components/clockpicker/api/clockpicker.js @@ -123,6 +123,13 @@ export default [ values: 'true, false', default: 'true' }, + { + name: 'mobile-modal', + description: 'Clockpicker is shown into a modal on mobile', + type: 'Boolean', + values: 'true, false', + default: 'true' + }, { name: 'position', description: 'Optional, position of the timepicker relative to the input', diff --git a/docs/pages/components/datepicker/api/datepicker.js b/docs/pages/components/datepicker/api/datepicker.js index 1c7f2aea5..4032fe722 100644 --- a/docs/pages/components/datepicker/api/datepicker.js +++ b/docs/pages/components/datepicker/api/datepicker.js @@ -191,6 +191,13 @@ export default [ values: 'true, false', default: 'true' }, + { + name: 'mobile-modal', + description: 'Datepicker is shown into a modal on mobile', + type: 'Boolean', + values: 'true, false', + default: 'true' + }, { name: 'position', description: 'Optional, position of the datepicker relative to the input', diff --git a/docs/pages/components/datetimepicker/api/datetimepicker.js b/docs/pages/components/datetimepicker/api/datetimepicker.js index 086d0c7d1..e08e890cb 100644 --- a/docs/pages/components/datetimepicker/api/datetimepicker.js +++ b/docs/pages/components/datetimepicker/api/datetimepicker.js @@ -43,6 +43,13 @@ export default [ values: '0 - 6 (Sunday is 0, Monday is 1, and so on)', default: '0' }, + { + name: 'nearby-month-days', + description: 'Show/Hide nearby month days (prev and next month)', + type: 'Boolean', + values: '-', + default: 'true' + }, { name: 'size', description: 'Vertical size of input and picker, optional', diff --git a/docs/pages/components/notification/api/notification.js b/docs/pages/components/notification/api/notification.js index 807a20bc8..cea6f2fc9 100644 --- a/docs/pages/components/notification/api/notification.js +++ b/docs/pages/components/notification/api/notification.js @@ -34,7 +34,7 @@ export default [ }, { name: 'auto-close', - description: `Hide notification after duration only not programmatic`, + description: `Hide notification after duration`, type: 'Boolean', values: 'β€”', default: 'false' diff --git a/docs/pages/components/sidebar/api/sidebar.js b/docs/pages/components/sidebar/api/sidebar.js index 8606e6a1a..ae8bf1edc 100644 --- a/docs/pages/components/sidebar/api/sidebar.js +++ b/docs/pages/components/sidebar/api/sidebar.js @@ -42,7 +42,7 @@ export default [ }, { name: 'fullwidth', - description: 'Show sidebar in fullwidth.', + description: 'Show sidebar in fullwidth. A close button will be present for a fullwidth sidebar.', type: 'Boolean', values: '-', default: 'false' diff --git a/docs/pages/components/sidebar/examples/ExSimple.vue b/docs/pages/components/sidebar/examples/ExSimple.vue index e1d022f2a..c35511dfa 100644 --- a/docs/pages/components/sidebar/examples/ExSimple.vue +++ b/docs/pages/components/sidebar/examples/ExSimple.vue @@ -10,7 +10,7 @@ >
Lightweight UI components for Vue.js based on Bulma diff --git a/docs/pages/components/sidebar/examples/ExStatic.vue b/docs/pages/components/sidebar/examples/ExStatic.vue index 9a7acb3fe..41588d486 100644 --- a/docs/pages/components/sidebar/examples/ExStatic.vue +++ b/docs/pages/components/sidebar/examples/ExStatic.vue @@ -13,7 +13,7 @@
Lightweight UI components for Vue.js based on Bulma
diff --git a/docs/pages/components/timepicker/api/timepicker.js b/docs/pages/components/timepicker/api/timepicker.js index c118c1a76..3fadcacc0 100644 --- a/docs/pages/components/timepicker/api/timepicker.js +++ b/docs/pages/components/timepicker/api/timepicker.js @@ -113,6 +113,13 @@ export default [ values: '', default: 'true' }, + { + name: 'mobile-modal', + description: 'Timepicker is shown into a modal on mobile', + type: 'Boolean', + values: 'true, false', + default: 'true' + }, { name: 'position', description: 'Optional, position of the timepicker relative to the input', diff --git a/package-lock.json b/package-lock.json index 93ec82e9b..63b0b2e9e 100644 --- a/package-lock.json +++ b/package-lock.json @@ -6,7 +6,7 @@ "packages": { "": { "name": "buefy", - "version": "0.9.22", + "version": "0.9.23", "license": "MIT", "dependencies": { "bulma": "0.9.4" @@ -30,7 +30,7 @@ "babel-preset-env": "1.3.2", "babel-preset-stage-2": "6.22.0", "babel-register": "6.22.0", - "bulma-css-vars": "0.4.3", + "bulma-css-vars": "^0.8.0", "chalk": "4.1.0", "clean-css-cli": "4.3.0", "cleave.js": "1.0.1", @@ -5490,15 +5490,14 @@ "integrity": "sha512-86FlT5+1GrsgKbPLRRY7cGDg8fsJiP/jzTqXXVqiUZZ2aZT8uemEOHlU1CDU+TxklPEZ11HZNNWclRBBecP4CQ==" }, "node_modules/bulma-css-vars": { - "version": "0.4.3", - "resolved": "https://registry.npmjs.org/bulma-css-vars/-/bulma-css-vars-0.4.3.tgz", - "integrity": "sha512-ABmdyUORhXzV5Sglg13M+LpUJ2dOcYSHJEeNc8Rvwys6DyN/c0A+SzcjSx2gpm2QQc2uE80cOQXsDQDQkSOb+g==", + "version": "0.8.0", + "resolved": "https://registry.npmjs.org/bulma-css-vars/-/bulma-css-vars-0.8.0.tgz", + "integrity": "sha512-PhhvuZcSPlnPvgWoo/8y8QAYHCCkW2gjCcVD5P/zIyNrKwzk+I4QdDpexKtzCF7TduNNP5DQGG8InulBe5TGtg==", "dev": true, "dependencies": { - "color": "^3.1.2", - "css": "^2.2.4", - "mkdirp": "^1.0.4", - "sass": "^1.26.5" + "color": "^4.2.1", + "css": "^3.0.0", + "mkdirp": "^1.0.4" }, "bin": { "bulma-css-vars": "bin/bulma-css-vars.js" @@ -5507,29 +5506,67 @@ "node": ">= 10.0.0" }, "peerDependencies": { - "bulma": "^0.8.0" + "bulma": "^0.9.3" } }, "node_modules/bulma-css-vars/node_modules/color": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/color/-/color-3.1.2.tgz", - "integrity": "sha512-vXTJhHebByxZn3lDvDJYw4lR5+uB3vuoHsuYA5AKuxRVn5wzzIfQKGLBmgdVRHKTJYeK5rvJcHnrd0Li49CFpg==", + "version": "4.2.3", + "resolved": "https://registry.npmjs.org/color/-/color-4.2.3.tgz", + "integrity": "sha512-1rXeuUUiGGrykh+CeBdu5Ie7OJwinCgQY0bc7GCRxy5xVHy+moaqkpL/jqQq0MtQOeYcrqEz4abc5f0KtU7W4A==", "dev": true, "dependencies": { - "color-convert": "^1.9.1", - "color-string": "^1.5.2" + "color-convert": "^2.0.1", + "color-string": "^1.9.0" + }, + "engines": { + "node": ">=12.5.0" } }, + "node_modules/bulma-css-vars/node_modules/color-convert": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dev": true, + "dependencies": { + "color-name": "~1.1.4" + }, + "engines": { + "node": ">=7.0.0" + } + }, + "node_modules/bulma-css-vars/node_modules/color-name": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "dev": true + }, "node_modules/bulma-css-vars/node_modules/color-string": { - "version": "1.5.3", - "resolved": "https://registry.npmjs.org/color-string/-/color-string-1.5.3.tgz", - "integrity": "sha512-dC2C5qeWoYkxki5UAXapdjqO672AM4vZuPGRQfO8b5HKuKGBbKWpITyDYN7TOFKvRW7kOgAn3746clDBMDJyQw==", + "version": "1.9.1", + "resolved": "https://registry.npmjs.org/color-string/-/color-string-1.9.1.tgz", + "integrity": "sha512-shrVawQFojnZv6xM40anx4CkoDP+fZsw/ZerEMsW/pyzsRbElpsL/DBVW7q3ExxwusdNXI3lXpuhEZkzs8p5Eg==", "dev": true, "dependencies": { "color-name": "^1.0.0", "simple-swizzle": "^0.2.2" } }, + "node_modules/bulma-css-vars/node_modules/css": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/css/-/css-3.0.0.tgz", + "integrity": "sha512-DG9pFfwOrzc+hawpmqX/dHYHJG+Bsdb0klhyi1sDneOgGOXy9wQIC8hzyVp1e4NRYDBdxcylvywPkkXCHAzTyQ==", + "dev": true, + "dependencies": { + "inherits": "^2.0.4", + "source-map": "^0.6.1", + "source-map-resolve": "^0.6.0" + } + }, + "node_modules/bulma-css-vars/node_modules/inherits": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", + "dev": true + }, "node_modules/bulma-css-vars/node_modules/mkdirp": { "version": "1.0.4", "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-1.0.4.tgz", @@ -5542,6 +5579,17 @@ "node": ">=10" } }, + "node_modules/bulma-css-vars/node_modules/source-map-resolve": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/source-map-resolve/-/source-map-resolve-0.6.0.tgz", + "integrity": "sha512-KXBr9d/fO/bWo97NXsPIAW1bFSBOuCnjbNTBMO7N59hsv5i9yzRDfcYwwt0l04+VqnKC+EwzvJZIP/qkuMgR/w==", + "deprecated": "See https://github.com/lydell/source-map-resolve#deprecated", + "dev": true, + "dependencies": { + "atob": "^2.1.2", + "decode-uri-component": "^0.2.0" + } + }, "node_modules/bytes": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.0.tgz", @@ -20768,7 +20816,7 @@ "node_modules/simple-swizzle": { "version": "0.2.2", "resolved": "https://registry.npmjs.org/simple-swizzle/-/simple-swizzle-0.2.2.tgz", - "integrity": "sha1-pNprY1/8zMoz9w0Xy5JZLeleVXo=", + "integrity": "sha512-JA//kQgZtbuY83m+xT+tXJkmJncGMTFT+C+g2h2R9uxkYIrE2yy9sgmcLhCnw57/WSD+Eh3J97FPEDFnbXnDUg==", "dev": true, "dependencies": { "is-arrayish": "^0.3.1" @@ -30196,42 +30244,83 @@ "integrity": "sha512-86FlT5+1GrsgKbPLRRY7cGDg8fsJiP/jzTqXXVqiUZZ2aZT8uemEOHlU1CDU+TxklPEZ11HZNNWclRBBecP4CQ==" }, "bulma-css-vars": { - "version": "0.4.3", - "resolved": "https://registry.npmjs.org/bulma-css-vars/-/bulma-css-vars-0.4.3.tgz", - "integrity": "sha512-ABmdyUORhXzV5Sglg13M+LpUJ2dOcYSHJEeNc8Rvwys6DyN/c0A+SzcjSx2gpm2QQc2uE80cOQXsDQDQkSOb+g==", + "version": "0.8.0", + "resolved": "https://registry.npmjs.org/bulma-css-vars/-/bulma-css-vars-0.8.0.tgz", + "integrity": "sha512-PhhvuZcSPlnPvgWoo/8y8QAYHCCkW2gjCcVD5P/zIyNrKwzk+I4QdDpexKtzCF7TduNNP5DQGG8InulBe5TGtg==", "dev": true, "requires": { - "color": "^3.1.2", - "css": "^2.2.4", - "mkdirp": "^1.0.4", - "sass": "^1.26.5" + "color": "^4.2.1", + "css": "^3.0.0", + "mkdirp": "^1.0.4" }, "dependencies": { "color": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/color/-/color-3.1.2.tgz", - "integrity": "sha512-vXTJhHebByxZn3lDvDJYw4lR5+uB3vuoHsuYA5AKuxRVn5wzzIfQKGLBmgdVRHKTJYeK5rvJcHnrd0Li49CFpg==", + "version": "4.2.3", + "resolved": "https://registry.npmjs.org/color/-/color-4.2.3.tgz", + "integrity": "sha512-1rXeuUUiGGrykh+CeBdu5Ie7OJwinCgQY0bc7GCRxy5xVHy+moaqkpL/jqQq0MtQOeYcrqEz4abc5f0KtU7W4A==", "dev": true, "requires": { - "color-convert": "^1.9.1", - "color-string": "^1.5.2" + "color-convert": "^2.0.1", + "color-string": "^1.9.0" } }, + "color-convert": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dev": true, + "requires": { + "color-name": "~1.1.4" + } + }, + "color-name": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "dev": true + }, "color-string": { - "version": "1.5.3", - "resolved": "https://registry.npmjs.org/color-string/-/color-string-1.5.3.tgz", - "integrity": "sha512-dC2C5qeWoYkxki5UAXapdjqO672AM4vZuPGRQfO8b5HKuKGBbKWpITyDYN7TOFKvRW7kOgAn3746clDBMDJyQw==", + "version": "1.9.1", + "resolved": "https://registry.npmjs.org/color-string/-/color-string-1.9.1.tgz", + "integrity": "sha512-shrVawQFojnZv6xM40anx4CkoDP+fZsw/ZerEMsW/pyzsRbElpsL/DBVW7q3ExxwusdNXI3lXpuhEZkzs8p5Eg==", "dev": true, "requires": { "color-name": "^1.0.0", "simple-swizzle": "^0.2.2" } }, + "css": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/css/-/css-3.0.0.tgz", + "integrity": "sha512-DG9pFfwOrzc+hawpmqX/dHYHJG+Bsdb0klhyi1sDneOgGOXy9wQIC8hzyVp1e4NRYDBdxcylvywPkkXCHAzTyQ==", + "dev": true, + "requires": { + "inherits": "^2.0.4", + "source-map": "^0.6.1", + "source-map-resolve": "^0.6.0" + } + }, + "inherits": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", + "dev": true + }, "mkdirp": { "version": "1.0.4", "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-1.0.4.tgz", "integrity": "sha512-vVqVZQyf3WLx2Shd0qJ9xuvqgAyKPLAiqITEtqW0oIUjzo3PePDd6fW9iFz30ef7Ysp/oiWqbhszeGWW2T6Gzw==", "dev": true + }, + "source-map-resolve": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/source-map-resolve/-/source-map-resolve-0.6.0.tgz", + "integrity": "sha512-KXBr9d/fO/bWo97NXsPIAW1bFSBOuCnjbNTBMO7N59hsv5i9yzRDfcYwwt0l04+VqnKC+EwzvJZIP/qkuMgR/w==", + "dev": true, + "requires": { + "atob": "^2.1.2", + "decode-uri-component": "^0.2.0" + } } } }, @@ -43046,7 +43135,7 @@ "simple-swizzle": { "version": "0.2.2", "resolved": "https://registry.npmjs.org/simple-swizzle/-/simple-swizzle-0.2.2.tgz", - "integrity": "sha1-pNprY1/8zMoz9w0Xy5JZLeleVXo=", + "integrity": "sha512-JA//kQgZtbuY83m+xT+tXJkmJncGMTFT+C+g2h2R9uxkYIrE2yy9sgmcLhCnw57/WSD+Eh3J97FPEDFnbXnDUg==", "dev": true, "requires": { "is-arrayish": "^0.3.1" diff --git a/package.json b/package.json index 751851f14..6dfe52dfc 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "buefy", - "version": "0.9.23", + "version": "0.9.24", "homepage": "https://buefy.org", "description": "Lightweight UI components for Vue.js based on Bulma", "author": "Rafael Beraldo ", @@ -84,7 +84,7 @@ "babel-preset-env": "1.3.2", "babel-preset-stage-2": "6.22.0", "babel-register": "6.22.0", - "bulma-css-vars": "0.4.3", + "bulma-css-vars": "^0.8.0", "chalk": "4.1.0", "clean-css-cli": "4.3.0", "cleave.js": "1.0.1", diff --git a/src/components/checkbox/Checkbox.vue b/src/components/checkbox/Checkbox.vue index 4e669ef02..9cfd3c873 100644 --- a/src/components/checkbox/Checkbox.vue +++ b/src/components/checkbox/Checkbox.vue @@ -12,6 +12,7 @@ trigger the checkbox change in the b-table --> diff --git a/src/components/datepicker/DatepickerTableRow.vue b/src/components/datepicker/DatepickerTableRow.vue index 16a2d3a20..f40acca83 100644 --- a/src/components/datepicker/DatepickerTableRow.vue +++ b/src/components/datepicker/DatepickerTableRow.vue @@ -369,7 +369,7 @@ export default { (!this.maxDate || nextDay < this.maxDate) && !this.selectableDate(nextDay) ) { - nextDay.setDate(day.getDate() + Math.sign(inc)) + nextDay.setDate(nextDay.getDate() + Math.sign(inc)) } this.setRangeHoverEndDate(nextDay) this.$emit('change-focus', nextDay) diff --git a/src/components/datetimepicker/Datetimepicker.vue b/src/components/datetimepicker/Datetimepicker.vue index 5bae605ea..e0d26d2c8 100644 --- a/src/components/datetimepicker/Datetimepicker.vue +++ b/src/components/datetimepicker/Datetimepicker.vue @@ -18,6 +18,7 @@ :date-parser="defaultDatetimeParser" :min-date="minDate" :max-date="maxDate" + :nearby-month-days="nearbyMonthDays" :icon="icon" :icon-right="iconRight" :icon-right-clickable="iconRightClickable" @@ -145,6 +146,10 @@ export default { }, minDatetime: Date, maxDatetime: Date, + nearbyMonthDays: { + type: Boolean, + default: config.defaultDatepickerNearbyMonthDays + }, datetimeFormatter: { type: Function }, diff --git a/src/components/field/Field.spec.js b/src/components/field/Field.spec.js index 4207c4230..d55d2cd20 100644 --- a/src/components/field/Field.spec.js +++ b/src/components/field/Field.spec.js @@ -180,6 +180,29 @@ describe('BField', () => { }) expect(wrapper.find('.field').find('label').isVisible()).toBe(true) }) + + it('should reflect validation status of wrapped input unless type is specified', async () => { + const wrapper = mount(BField, mountOptions) + const input = wrapper.find(BInput) + + input.vm.setInvalid() + await wrapper.vm.$nextTick() + expect(wrapper.vm.newType).toBe('is-danger') + + input.vm.setValidity(null, null) + await wrapper.vm.$nextTick() + expect(wrapper.vm.newType).toBeFalsy() + + await wrapper.setProps({ type: 'is-warning' }) + + input.vm.setInvalid() + await wrapper.vm.$nextTick() + expect(wrapper.vm.newType).toBe('is-warning') + + input.vm.setValidity(null, null) + await wrapper.vm.$nextTick() + expect(wrapper.vm.newType).toBe('is-warning') + }) }) describe('Passing true for horizontal prop', () => { diff --git a/src/components/field/Field.vue b/src/components/field/Field.vue index 66a08ea6c..a0cd3951d 100644 --- a/src/components/field/Field.vue +++ b/src/components/field/Field.vue @@ -32,7 +32,7 @@
diff --git a/src/components/input/Input.spec.js b/src/components/input/Input.spec.js index 756f72ecc..e8a7d18bf 100644 --- a/src/components/input/Input.spec.js +++ b/src/components/input/Input.spec.js @@ -197,4 +197,88 @@ describe('BInput', () => { done() }) }) + + describe('validation', () => { + let spyOnCheckHtml5Validity + + beforeEach(() => { + spyOnCheckHtml5Validity = jest + .spyOn(BInput.mixins[0].methods, 'checkHtml5Validity') + .mockImplementation(function () { + this.isValid = false + }) + }) + + afterEach(() => { + spyOnCheckHtml5Validity.mockReset() + }) + + it('should validate value when updated by user interaction', async () => { + const wrapper = shallowMount(BInput, { + data: () => ({ isValid: false }) + }) + + // simulates "input" event + wrapper.vm.onInput({ target: { value: 'foo' } }) + await wrapper.vm.$nextTick() + expect(spyOnCheckHtml5Validity).toHaveBeenCalledTimes(1) + + // simulates "change" event + await wrapper.setProps({ lazy: true }) + wrapper.vm.onChange({ target: { value: 'bar' } }) + await wrapper.vm.$nextTick() + expect(spyOnCheckHtml5Validity).toHaveBeenCalledTimes(2) + }) + + it('should validate value when programmatically updated', async () => { + const wrapper = shallowMount(BInput, { + data: () => ({ isValid: false }) + }) + await wrapper.setProps({ value: 'foo' }) + await wrapper.vm.$nextTick() + expect(spyOnCheckHtml5Validity).toHaveBeenCalledTimes(1) + }) + + describe('via v-model', () => { + let root + let wrapper + + beforeEach(async () => { + root = mount({ + template: '', + components: { 'b-input': BInput }, + data: () => ({ + value: '', + lazy: false + }) + }) + wrapper = root.find(BInput) + // triggers validation and invalidates + wrapper.vm.onBlur({}) + await wrapper.vm.$nextTick() + spyOnCheckHtml5Validity.mockClear() + }) + + it('should validate value once when updated by user interaction', async () => { + // simulates "input" event + wrapper.vm.onInput({ target: { value: 'foo' } }) + await wrapper.vm.$nextTick() + expect(root.vm.value).toBe('foo') + expect(spyOnCheckHtml5Validity).toHaveBeenCalledTimes(1) + + // simulates "change" event + await root.setData({ lazy: true }) + wrapper.vm.onChange({ target: { value: 'bar' } }) + await wrapper.vm.$nextTick() + expect(root.vm.value).toBe('bar') + expect(spyOnCheckHtml5Validity).toHaveBeenCalledTimes(2) + }) + + it('should validate value once when programmatically updated', async () => { + await root.setData({ value: 'foo' }) + await wrapper.vm.$nextTick() + expect(spyOnCheckHtml5Validity).toHaveBeenCalledTimes(1) + }) + }) + }) }) diff --git a/src/components/input/Input.vue b/src/components/input/Input.vue index 68996fb18..c8b839303 100644 --- a/src/components/input/Input.vue +++ b/src/components/input/Input.vue @@ -214,9 +214,18 @@ export default { /** * When v-model is changed: * 1. Set internal value. + * 2. Validate it if the value came from outside; + * i.e., not equal to computedValue */ value(value) { + const fromOutside = this.computedValue != value // eslint-disable-line eqeqeq this.newValue = value + if (fromOutside) { + // validation must wait for DOM updated + this.$nextTick(() => { + !this.isValid && this.checkHtml5Validity() + }) + } }, type(type) { this.newType = type diff --git a/src/components/numberinput/Numberinput.spec.js b/src/components/numberinput/Numberinput.spec.js index 855824a81..fd9397c56 100644 --- a/src/components/numberinput/Numberinput.spec.js +++ b/src/components/numberinput/Numberinput.spec.js @@ -108,7 +108,7 @@ describe('BNumberinput', () => { jest.runOnlyPendingTimers() wrapper.find('.control.plus').trigger('mouseup') - expect(wrapper.vm.computedValue).toBe(0) + expect(wrapper.vm.computedValue).toBe(1) // Decrement wrapper.find('.control.minus button').trigger('mousedown') @@ -343,7 +343,7 @@ describe('BNumberinput', () => { const min = 5 wrapper.setProps({ min }) wrapper.vm.computedValue = '' - expect(wrapper.vm.computedValue).toBe(min) + expect(wrapper.vm.computedValue).toBeNull() }) it('increments/decrements on click', async () => { diff --git a/src/components/numberinput/Numberinput.vue b/src/components/numberinput/Numberinput.vue index 4776409d6..c489adff2 100644 --- a/src/components/numberinput/Numberinput.vue +++ b/src/components/numberinput/Numberinput.vue @@ -167,11 +167,7 @@ export default { // Parses the number, so that "0" => 0, and "invalid" => null let newValue = (Number(value) === 0) ? 0 : (Number(value) || null) if (value === '' || value === undefined || value === null) { - if (this.minNumber !== undefined) { - newValue = this.minNumber - } else { - newValue = null - } + newValue = null } this.newValue = newValue if (newValue === null) { @@ -278,7 +274,7 @@ export default { } }, increment() { - if (this.computedValue === null || typeof this.computedValue === 'undefined') { + if (this.computedValue === null || typeof this.computedValue === 'undefined' || this.computedValue < this.minNumber) { if (this.minNumber !== null && typeof this.minNumber !== 'undefined') { this.computedValue = this.minNumber return @@ -300,12 +296,12 @@ export default { if (inc) this.increment() else this.decrement() + if (!this.longPress) return this._$intervalRef = setTimeout(() => { this.longPressTick(inc) }, this.exponential ? (250 / (this.exponential * this.timesPressed++)) : 250) }, onStartLongPress(event, inc) { - if (!this.longPress) return if (event.button !== 0 && event.type !== 'touchstart') return clearTimeout(this._$intervalRef) this.longPressTick(inc) diff --git a/src/components/sidebar/Sidebar.vue b/src/components/sidebar/Sidebar.vue index ca74c89bb..51ff61401 100644 --- a/src/components/sidebar/Sidebar.vue +++ b/src/components/sidebar/Sidebar.vue @@ -15,6 +15,12 @@ :class="rootClasses" @mouseenter="onHover" @mouseleave="onHoverLeave"> +
@@ -243,6 +249,16 @@ export default { this.hasLeaved = true this.timer = null this.isDelayOver = false + }, + /** + * Close sidebar if close button is clicked. + */ + clickedCloseButton() { + if (this.isFixed) { + if (this.isOpen && this.fullwidth) { + this.cancel('outside') + } + } } }, created() { diff --git a/src/components/timepicker/Timepicker.vue b/src/components/timepicker/Timepicker.vue index edf05af8e..46b86f0b8 100644 --- a/src/components/timepicker/Timepicker.vue +++ b/src/components/timepicker/Timepicker.vue @@ -6,6 +6,7 @@ :position="position" :disabled="disabled" :inline="inline" + :mobile-modal="mobileModal" :append-to-body="appendToBody" append-to-body-copy-parent @active-change="onActiveChange"> diff --git a/src/scss/components/_sidebar.scss b/src/scss/components/_sidebar.scss index a72a3ba3f..10d1ce83f 100644 --- a/src/scss/components/_sidebar.scss +++ b/src/scss/components/_sidebar.scss @@ -4,6 +4,8 @@ $sidebar-width: 260px !default; $sidebar-mobile-width: 80px !default; $sidebar-mobile-breakpoint: $tablet !default; $sidebar-colors: $navbar-colors !default; +$sidebar-close-button-background: rgba(10,10,10,.3) !default; +$sidebar-close-button-dark-background: rgba(10,10,10,.86) !default; .b-sidebar { .sidebar-content { @@ -88,6 +90,13 @@ $sidebar-colors: $navbar-colors !default; max-width: 100%; } } + .sidebar-close { + background: $sidebar-close-button-background; + + &:hover { + background: $sidebar-close-button-dark-background; + } + } } .sidebar-background { @include overlay; diff --git a/src/utils/TimepickerMixin.js b/src/utils/TimepickerMixin.js index 930ed4183..21a636f1e 100644 --- a/src/utils/TimepickerMixin.js +++ b/src/utils/TimepickerMixin.js @@ -145,6 +145,10 @@ export default { type: Boolean, default: () => config.defaultTimepickerMobileNative }, + mobileModal: { + type: Boolean, + default: () => config.defaultTimepickerMobileModal + }, timeCreator: { type: Function, default: () => { diff --git a/src/utils/config.js b/src/utils/config.js index e2d541ddd..dd6e411e2 100644 --- a/src/utils/config.js +++ b/src/utils/config.js @@ -32,6 +32,7 @@ let config = { defaultModalScroll: null, defaultDatepickerMobileNative: true, defaultTimepickerMobileNative: true, + defaultTimepickerMobileModal: true, defaultNoticeQueue: true, defaultInputHasCounter: true, defaultTaginputHasCounter: true,