UI - Add UiNumericInput component

This commit is contained in:
Kacper Donat 2020-03-18 16:33:06 +01:00
parent ea283a86e7
commit 87e4121444
8 changed files with 102 additions and 20 deletions

View File

@ -0,0 +1,11 @@
<div class="input-group input-group-sm">
<input type="text" class="form-control form-control-sm" :id="id" inputmode="numeric" v-bind="$attrs" :value="value" @blur="update"/>
<div class="input-group-append">
<button class="btn btn-addon" type="button" @click="increment" :disabled="!canIncrement">
<ui-icon icon="increment"/>
</button>
<button class="btn btn-addon" type="button" @click="decrement" :disabled="!canDecrement">
<ui-icon icon="decrement"/>
</button>
</div>
</div>

View File

@ -3,17 +3,18 @@ label {
margin-bottom: 0;
margin-top: -0.2rem;
display: block;
font-size: .8rem;
}
.label-sm {
font-size: .8rem;
font-size: .6rem;
}
.form-group:last-child {
margin-bottom: 0;
}
.form-control, .input-group-text {
.form-control, .input-group-text, .btn-addon {
background: rgba($dark, .06);
border: none;
border-bottom: 2px solid $dark;
@ -32,7 +33,8 @@ label {
}
}
.input-group-append {
.input-group-append,
.input-group-append .btn + .btn {
margin-left: 0;
}

View File

@ -2,9 +2,11 @@ $border-radius: 0;
$border-radius-lg: $border-radius;
$border-radius-sm: $border-radius;
@import "~bootstrap/scss/functions";
@import "~bootstrap/scss/variables";
$form-group-margin-bottom: $form-group-margin-bottom / 2;
$primary: #005ea8;
$custom-control-indicator-checked-bg: $dark;

View File

@ -30,6 +30,8 @@ export class Application extends Vue {
}
};
private count = 8;
private intervals = { messages: null, departures: null };
get messages() {

View File

@ -23,7 +23,7 @@ import {
faTimes,
faTrashAlt
} from "@fortawesome/pro-light-svg-icons";
import { faClock as faClockBold, faCodeCommit, faSpinnerThird } from "@fortawesome/pro-regular-svg-icons";
import { faClock as faClockBold, faCodeCommit, faMinus, faPlus, faSpinnerThird } from "@fortawesome/pro-regular-svg-icons";
import { faExclamationTriangle as faSolidExclamationTriangle, faWalking } from "@fortawesome/pro-solid-svg-icons";
import { fac } from "../../icons";
import { FontAwesomeIcon, FontAwesomeLayers, FontAwesomeLayersText } from "@fortawesome/vue-fontawesome";
@ -81,6 +81,8 @@ const definitions: Dictionary<Icon> = {
'map': simple(faMapMarkerAlt),
'stop': simple(faSign),
'spinner': simple(faSpinnerThird, { spin: true }),
'increment': simple(faPlus, { "fixed-width": true }),
'decrement': simple(faMinus, { "fixed-width": true }),
'departure-warning': stack([
{icon: faClockBold},
{icon: faSolidExclamationTriangle, transform: "shrink-5 down-4 right-6"}

View File

@ -1,2 +1,3 @@
export * from './switch';
export * from './icon';
export * from './numeric-input'

View File

@ -0,0 +1,53 @@
import Vue from 'vue'
import { Component, Prop } from 'vue-property-decorator'
import * as uuid from "uuid";
@Component({
template: require('../../../components/ui/numeric.html'),
inheritAttrs: false
})
export class UiNumericInput extends Vue {
@Prop({
type: String,
default: () => `uuid-${uuid.v4()}`
})
id: string;
@Prop(Number)
value: number;
@Prop({ type: Number, default: 1 })
step: number;
@Prop({ type: Number, default: -Infinity })
min: number;
@Prop({ type: Number, default: Infinity })
max: number;
update(ev) {
this.$emit('input', this.clamp(Number.parseInt(ev.target.value)));
}
increment() {
this.$emit('input', this.clamp(this.value + this.step));
}
decrement() {
this.$emit('input', this.clamp(this.value - this.step));
}
clamp(value: number) {
return Math.max(Math.min(value, this.max), this.min);
}
get canIncrement(): boolean {
return this.max - this.value > Number.EPSILON * 2;
}
get canDecrement(): boolean {
return this.value - this.min > Number.EPSILON * 2;
}
}
Vue.component('UiNumericInput', UiNumericInput);

View File

@ -73,25 +73,34 @@
</button>
<portal to="popups">
<popper reference="settings-departures" v-if="visibility.departures" arrow placement="left-start" @leave="visibility.departures = false">
<h3 class="popper__heading flex">
<label class="text" for="departures-auto-refresh">
<ui-icon icon="refresh" fixed-width></ui-icon>
autoodświeżanie
</label>
<ui-switch id="departures-auto-refresh" v-model="autorefresh.departures.active" class="flex-space-left"></ui-switch>
</h3>
<div class="flex" v-if="autorefresh.departures.active">
<label for="departures-auto-refresh-interval" class="text">
<span class="sr-only">częstotliwość odświeżania</span>
co
</label>
<div class="input-group input-group-sm">
<input type="text" class="form-control form-control-sm form-control-simple" id="departures-auto-refresh-interval" v-model="autorefresh.departures.interval"/>
<div class="input-group-append">
<span class="input-group-text" aria-label="sekund">s</span>
<div class="form-group">
<h3 class="popper__heading flex">
<label class="text" for="departures-auto-refresh-interval">
<ui-icon icon="refresh" fixed-width></ui-icon>
autoodświeżanie
</label>
<ui-switch id="departures-auto-refresh" v-model="autorefresh.departures.active" class="flex-space-left"></ui-switch>
</h3>
<div class="flex " v-if="autorefresh.departures.active">
<label for="departures-auto-refresh-interval" class="text">
<span class="sr-only">częstotliwość odświeżania</span>
co
</label>
<div class="input-group input-group-sm">
<input type="text" class="form-control form-control-sm form-control-simple" id="departures-auto-refresh-interval" v-model="autorefresh.departures.interval"/>
<div class="input-group-append">
<span class="input-group-text" aria-label="sekund">s</span>
</div>
</div>
</div>
</div>
<div class="form-group">
<label class="text" for="departures-count">
<ui-icon icon="line-bus" fixed-width></ui-icon>
Liczba wpisów
</label>
<ui-numeric-input id="departures-count" v-model="count" :min="1" :max="16"></ui-numeric-input>
</div>
</popper>
</portal>
</header>