1
-
import { Vue, CreateElement } from "./vue";
1
+
import { Vue, CreateElement, CombinedVueInstance } from "./vue";
2
2
import { VNode, VNodeData, VNodeDirective } from "./vnode";
3
3
4
4
type Constructor = {
5
5
new (...args: any[]): any;
6
6
}
7
7
8
-
export type Component = typeof Vue | ComponentOptions<Vue> | FunctionalComponentOptions;
8
+
// we don't support infer props in async component
9
+
export type Component<Data=DefaultData<Vue>, Methods=DefaultMethods<Vue>, Computed=DefaultComputed, Props=DefaultProps> =
10
+
| typeof Vue
11
+
| FunctionalComponentOptions<Props>
12
+
| ThisTypedComponentOptionsWithArrayProps<Vue, Data, Methods, Computed, keyof Props>
13
+
| ThisTypedComponentOptionsWithRecordProps<Vue, Data, Methods, Computed, Props>;
9
14
10
15
interface EsModuleComponent {
11
16
default: Component
12
17
}
13
18
14
-
export type AsyncComponent = (
15
-
resolve: (component: Component) => void,
19
+
export type AsyncComponent<Data=DefaultData<Vue>, Methods=DefaultMethods<Vue>, Computed=DefaultComputed, Props=DefaultProps> = (
20
+
resolve: (component: Component<Data, Methods, Computed, Props>) => void,
16
21
reject: (reason?: any) => void
17
-
) => Promise<Component | EsModuleComponent> | Component | void;
22
+
) => Promise<Component | EsModuleComponent> | void;
23
+
24
+
/**
25
+
* When the `Computed` type parameter on `ComponentOptions` is inferred,
26
+
* it should have a property with the return type of every get-accessor.
27
+
* Since there isn't a way to query for the return type of a function, we allow TypeScript
28
+
* to infer from the shape of `Accessors<Computed>` and work backwards.
29
+
*/
30
+
export type Accessors<T> = {
31
+
[K in keyof T]: (() => T[K]) | ComputedOptions<T[K]>
32
+
}
18
33
19
-
export interface ComponentOptions<V extends Vue> {
20
-
data?: Object | ((this: V) => Object);
21
-
props?: string[] | { [key: string]: PropOptions | Constructor | Constructor[] };
34
+
/**
35
+
* This type should be used when an array of strings is used for a component's `props` value.
36
+
*/
37
+
export type ThisTypedComponentOptionsWithArrayProps<V extends Vue, Data, Methods, Computed, PropNames extends string> =
38
+
object &
39
+
ComponentOptions<V, Data | ((this: Readonly<Record<PropNames, any>> & V) => Data), Methods, Computed, PropNames[]> &
40
+
ThisType<CombinedVueInstance<V, Data, Methods, Computed, Readonly<Record<PropNames, any>>>>;
41
+
42
+
/**
43
+
* This type should be used when an object mapped to `PropOptions` is used for a component's `props` value.
44
+
*/
45
+
export type ThisTypedComponentOptionsWithRecordProps<V extends Vue, Data, Methods, Computed, Props> =
46
+
object &
47
+
ComponentOptions<V, Data | ((this: Readonly<Props> & V) => Data), Methods, Computed, RecordPropsDefinition<Props>> &
48
+
ThisType<CombinedVueInstance<V, Data, Methods, Computed, Readonly<Props>>>;
49
+
50
+
type DefaultData<V> = object | ((this: V) => object);
51
+
type DefaultProps = Record<string, any>;
52
+
type DefaultMethods<V> = { [key: string]: (this: V, ...args: any[]) => any };
53
+
type DefaultComputed = { [key: string]: any };
54
+
export interface ComponentOptions<
55
+
V extends Vue,
56
+
Data=DefaultData<V>,
57
+
Methods=DefaultMethods<V>,
58
+
Computed=DefaultComputed,
59
+
PropsDef=PropsDefinition<DefaultProps>> {
60
+
data?: Data;
61
+
props?: PropsDef;
22
62
propsData?: Object;
23
-
computed?: { [key: string]: ((this: V) => any) | ComputedOptions<V> };
24
-
methods?: { [key: string]: (this: V, ...args: any[]) => any };
25
-
watch?: { [key: string]: ({ handler: WatchHandler<V, any> } & WatchOptions) | WatchHandler<V, any> | string };
63
+
computed?: Accessors<Computed>;
64
+
methods?: Methods;
65
+
watch?: Record<string, WatchOptionsWithHandler<any> | WatchHandler<any> | string>;
26
66
27
67
el?: Element | String;
28
68
template?: string;
29
-
render?(this: V, createElement: CreateElement): VNode;
69
+
render?(createElement: CreateElement): VNode;
30
70
renderError?: (h: () => VNode, err: Error) => VNode;
31
71
staticRenderFns?: ((createElement: CreateElement) => VNode)[];
32
72
33
73
beforeCreate?(this: V): void;
34
-
created?(this: V): void;
35
-
beforeDestroy?(this: V): void;
36
-
destroyed?(this: V): void;
37
-
beforeMount?(this: V): void;
38
-
mounted?(this: V): void;
39
-
beforeUpdate?(this: V): void;
40
-
updated?(this: V): void;
41
-
activated?(this: V): void;
42
-
deactivated?(this: V): void;
43
-
44
-
directives?: { [key: string]: DirectiveOptions | DirectiveFunction };
45
-
components?: { [key: string]: Component | AsyncComponent };
74
+
created?(): void;
75
+
beforeDestroy?(): void;
76
+
destroyed?(): void;
77
+
beforeMount?(): void;
78
+
mounted?(): void;
79
+
beforeUpdate?(): void;
80
+
updated?(): void;
81
+
activated?(): void;
82
+
deactivated?(): void;
83
+
84
+
directives?: { [key: string]: DirectiveFunction | DirectiveOptions };
85
+
components?: { [key: string]: Component<any, any, any, any> | AsyncComponent<any, any, any, any> };
46
86
transitions?: { [key: string]: Object };
47
87
filters?: { [key: string]: Function };
48
88
@@ -57,49 +97,64 @@ export interface ComponentOptions<V extends Vue> {
57
97
parent?: Vue;
58
98
mixins?: (ComponentOptions<Vue> | typeof Vue)[];
59
99
name?: string;
100
+
// TODO: support properly inferred 'extends'
60
101
extends?: ComponentOptions<Vue> | typeof Vue;
61
102
delimiters?: [string, string];
62
103
comments?: boolean;
63
104
inheritAttrs?: boolean;
64
105
}
65
106
66
-
export interface FunctionalComponentOptions {
107
+
export interface FunctionalComponentOptions<Props = DefaultProps, PropDefs = PropsDefinition<Props>> {
67
108
name?: string;
68
-
props?: string[] | { [key: string]: PropOptions | Constructor | Constructor[] };
109
+
props?: PropDefs;
69
110
inject?: { [key: string]: string | symbol } | string[];
70
111
functional: boolean;
71
-
render(this: never, createElement: CreateElement, context: RenderContext): VNode | void;
112
+
render(this: undefined, createElement: CreateElement, context: RenderContext<Props>): VNode;
72
113
}
73
114
74
-
export interface RenderContext {
75
-
props: any;
115
+
export interface RenderContext<Props=DefaultProps> {
116
+
props: Props;
76
117
children: VNode[];
77
118
slots(): any;
78
119
data: VNodeData;
79
120
parent: Vue;
80
121
injections: any
81
122
}
82
123
83
-
export interface PropOptions {
84
-
type?: Constructor | Constructor[] | null;
124
+
export type Prop<T> = { (): T } | { new (...args: any[]): T & object }
125
+
126
+
export type PropValidator<T> = PropOptions<T> | Prop<T> | Prop<T>[];
127
+
128
+
export interface PropOptions<T=any> {
129
+
type?: Prop<T> | Prop<T>[];
85
130
required?: boolean;
86
-
default?: any;
87
-
validator?(value: any): boolean;
131
+
default?: T | null | undefined | (() => object);
132
+
validator?(value: T): boolean;
88
133
}
89
134
90
-
export interface ComputedOptions<V> {
91
-
get?(this: V): any;
92
-
set?(this: V, value: any): void;
135
+
export type RecordPropsDefinition<T> = {
136
+
[K in keyof T]: PropValidator<T[K]>
137
+
}
138
+
export type ArrayPropsDefinition<T> = (keyof T)[];
139
+
export type PropsDefinition<T> = ArrayPropsDefinition<T> | RecordPropsDefinition<T>;
140
+
141
+
export interface ComputedOptions<T> {
142
+
get?(): T;
143
+
set?(value: T): void;
93
144
cache?: boolean;
94
145
}
95
146
96
-
export type WatchHandler<V, T> = (this: V, val: T, oldVal: T) => void;
147
+
export type WatchHandler<T> = (val: T, oldVal: T) => void;
97
148
98
149
export interface WatchOptions {
99
150
deep?: boolean;
100
151
immediate?: boolean;
101
152
}
102
153
154
+
export interface WatchOptionsWithHandler<T> extends WatchOptions {
155
+
handler: WatchHandler<T>;
156
+
}
157
+
103
158
export type DirectiveFunction = (
104
159
el: HTMLElement,
105
160
binding: VNodeDirective,
RetroSearch is an open source project built by @garambo | Open a GitHub Issue
Search and Browse the WWW like it's 1997 | Search results from DuckDuckGo
HTML:
3.2
| Encoding:
UTF-8
| Version:
0.7.4