Skip to content
This repository was archived by the owner on Aug 2, 2024. It is now read-only.

Commit e9257a9

Browse files
fixes vmodel
1 parent abdd15d commit e9257a9

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

52 files changed

+802
-449
lines changed

package-lock.json

Lines changed: 17 additions & 17 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/api/Decorators.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ import { apiDocsEnabled } from '@/config';
33
import { ComponentDocumentation } from './ComponentDocumentation';
44
import { SlotDocumentation } from './SlotDocumentation';
55
import { EventDocumentation } from './EventDocumentation';
6-
import TsxComponent from '@/vue-tsx';
6+
import { TsxComponent } from '@/vue-tsx';
77
import { ComponentOptions, PropOptions, Constructor } from 'vue/types/options';
88
import { Prop } from 'vue/types/options';
99
import Vue from 'vue';

src/components/Breadcrumb/BreadcrumbItem.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ export class BreadcrumbItem extends Base<Props> {
2525
const title = this.$slots.default;
2626
return (
2727
<li class='fd-breadcrumb__item'>
28-
<a class='fd-breadcrumb__link' href='#' on-click={event => this.onClick(event)}>{title}</a>
28+
<a class='fd-breadcrumb__link' href='#' on-click={this.onClick}>{title}</a>
2929
</li>
3030
);
3131
}

src/components/Calendar/Calendar.tsx

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,9 @@
1-
import { ComponentProps } from '@/vue-tsx';
21
import { CalendarHeader } from './CalendarHeader';
32
import { PresentDateMixin, DisplayedDateMixin, DateSelectionMixin } from './mixins';
43
import { mixins } from 'vue-class-component';
54
import { MonthPicker, YearPicker, DayPicker } from './Pickers';
65
import { Props as DateSelectionProps } from './mixins/DateSelection';
7-
import { Component, Mixins, Prop } from '@/core';
6+
import { ComponentProps, Component, Mixins, Prop } from '@/core';
87
const pickerMapping = { year: 'year', month: 'month' };
98
type PickerType = keyof typeof pickerMapping;
109

src/components/ClickAwayContainer.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import { Watch } from 'vue-property-decorator';
2-
import { VNode } from 'vue';
2+
import { CreateElement, VNode } from 'vue';
33
import { Component, Prop, Base } from '@/core';
44

55
type IgnoredElements = () => Element[];
@@ -34,8 +34,8 @@ export class ClickAwayContainer extends Base<Props> {
3434
@Prop({ type: Function, default: () => () => [] })
3535
public ignoredElements!: IgnoredElements;
3636

37-
public render(createElement): VNode {
38-
return createElement(this.tag, this.$slots.default);
37+
public render(h: CreateElement): VNode {
38+
return h(this.tag, this.$slots.default);
3939
}
4040

4141
public beforeDestroy() {

src/components/Counter.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -34,7 +34,7 @@ export class Counter extends Base<Props> {
3434
private get classes() {
3535
return {
3636
'fd-counter--notification': this.type === 'notification',
37-
}
37+
};
3838
}
3939

4040
public render() {
Lines changed: 157 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,157 @@
1+
import { Base, Model, Component, Event, Prop } from '@/core';
2+
import { UidProps } from '@/mixins';
3+
import { FormItem, FORM_ITEM_KEY, FORM_ITEM_ID_KEY } from './../FormItem';
4+
import { Inject } from 'vue-property-decorator';
5+
import { isInputElement } from './Helper';
6+
7+
const stateMapping = {
8+
valid: 'Valid',
9+
invalid: 'Invalid',
10+
warning: 'Warning',
11+
};
12+
type InputState = keyof (typeof stateMapping);
13+
const InputStates = Object.keys(stateMapping) as InputState[];
14+
15+
type ValueType = string | number | boolean;
16+
const ValueCtors = [String, Number, Boolean];
17+
18+
interface Props extends UidProps {
19+
placeholder?: string;
20+
required?: boolean;
21+
disabled?: boolean;
22+
readonly?: boolean;
23+
value?: ValueType;
24+
falseValue?: ValueType;
25+
trueValue?: ValueType;
26+
compact?: boolean;
27+
state?: InputState | null;
28+
}
29+
30+
@Component('Checkbox')
31+
@Event('change', 'Sent when the checkbox has been checked/unchecked.')
32+
export class Checkbox extends Base<Props> {
33+
@Inject({from: FORM_ITEM_KEY, default: null})
34+
public formItem!: FormItem | null;
35+
36+
@Inject({from: FORM_ITEM_ID_KEY, default: null})
37+
public formItemId!: string | null;
38+
39+
private get uid(): string | null {
40+
return this.formItemId;
41+
}
42+
43+
public mounted() {
44+
const formItem = this.formItem;
45+
if(formItem) {
46+
formItem.setCheck(true);
47+
}
48+
}
49+
50+
@Prop('Payload of the change-event when the user checks the checkbox', {
51+
default: true,
52+
type: ValueCtors,
53+
})
54+
public trueValue!: ValueType;
55+
56+
@Prop('Payload of the change-event when the user unchecks the checkbox', {
57+
default: false,
58+
type: ValueCtors,
59+
})
60+
public falseValue!: ValueType;
61+
62+
@Prop('value used when checked is true', {
63+
default: true,
64+
type: ValueCtors,
65+
})
66+
public value!: ValueType;
67+
68+
@Prop('whether input is compact', { type: Boolean, default: false })
69+
public compact!: boolean;
70+
71+
@Prop('whether the control is disabled', { default: false, type: Boolean })
72+
public disabled!: boolean;
73+
74+
@Prop('whether the control is readonly', { default: false, type: Boolean })
75+
public readonly!: boolean;
76+
77+
@Prop('current state', {
78+
acceptableValues: InputStates,
79+
default: null,
80+
type: String,
81+
validator: InputStates.includes,
82+
})
83+
public state!: InputState | null;
84+
85+
@Prop('whether a value is required (adds a *)', {
86+
default: false,
87+
type: Boolean,
88+
})
89+
public required!: boolean;
90+
91+
@Model('modelValue', {
92+
default: false,
93+
event: 'change',
94+
type: [Array, String, Boolean, Number],
95+
})
96+
public modelValue!: ValueType | ValueType[];
97+
98+
private get shouldBeChecked(): boolean {
99+
const modelValue = this.modelValue;
100+
const value = this.value;
101+
if(value == null) {
102+
throw Error('value cannot be null');
103+
}
104+
if (Array.isArray(modelValue)) {
105+
return modelValue.includes(value);
106+
}
107+
return this.modelValue === this.trueValue;
108+
}
109+
110+
public updateInput(event: Event) {
111+
const { target } = event;
112+
if(target == null) {
113+
return;
114+
}
115+
if(!isInputElement(target)) {
116+
return;
117+
}
118+
const { checked } = target;
119+
const { modelValue, value } = this;
120+
if(value == null) {
121+
throw Error('value cannot be null');
122+
}
123+
if(Array.isArray(modelValue)) {
124+
const set = new Set(modelValue);
125+
checked ? set.add(value) : set.delete(value);
126+
const newValue = Array.from(set);
127+
this.$emit('change', newValue);
128+
} else {
129+
const newValue = checked ? this.trueValue : this.falseValue;
130+
this.$emit('change', newValue);
131+
}
132+
}
133+
134+
public render() {
135+
return (
136+
<input
137+
id={this.uid}
138+
class={this.classes}
139+
checked={this.shouldBeChecked}
140+
value={this.value}
141+
on-change={this.updateInput}
142+
type='checkbox'
143+
staticClass='fd-form__control'
144+
/>
145+
);
146+
}
147+
148+
private get classes() {
149+
return {
150+
'fd-input--compact': this.compact,
151+
'is-warning': this.state === 'warning',
152+
'is-invalid': this.state === 'invalid',
153+
'is-valid': this.state === 'valid',
154+
'is-required': this.required,
155+
};
156+
}
157+
}
Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
export const isElement = (target: EventTarget): target is Element => ('tagName' in target);
2+
export const isInputElement = (target: EventTarget): target is HTMLInputElement => isElement(target) && target.tagName === 'INPUT';
3+
export const isTextAreaElement = (target: EventTarget): target is HTMLInputElement => isElement(target) && target.tagName === 'TEXTAREA';
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
export * from './dom';

0 commit comments

Comments
 (0)