ivue 1.0.2 → 1.0.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.idea/codeStyles/Project.xml +65 -0
- package/.idea/codeStyles/codeStyleConfig.xml +5 -0
- package/.idea/inspectionProfiles/Project_Default.xml +6 -0
- package/.idea/ivue.iml +8 -0
- package/.idea/modules.xml +8 -0
- package/.idea/php.xml +19 -0
- package/.idea/vcs.xml +6 -0
- package/README.md +23 -7
- package/coverage/clover.xml +159 -159
- package/coverage/coverage-final.json +1 -1
- package/coverage/index.html +17 -17
- package/coverage/index.ts.html +86 -107
- package/dist/index.es.js +74 -90
- package/dist/index.umd.js +1 -1
- package/dist/src/index.d.ts +1 -196
- package/dist/src/ivue.d.ts +218 -0
- package/docs/docs/.vitepress/config.ts +110 -22
- package/docs/docs/.vitepress/dist/404.html +4 -4
- package/docs/docs/.vitepress/dist/api/ivue.html +8 -8
- package/docs/docs/.vitepress/dist/api/propsWithDefaults.html +8 -8
- package/docs/docs/.vitepress/dist/assets/{api_ivue.md.BCZ4q_0D.js → api_ivue.md.MRwb9Lcb.js} +1 -1
- package/docs/docs/.vitepress/dist/assets/{api_ivue.md.BCZ4q_0D.lean.js → api_ivue.md.MRwb9Lcb.lean.js} +1 -1
- package/docs/docs/.vitepress/dist/assets/{api_propsWithDefaults.md.Cr5FwI9o.lean.js → api_propsWithDefaults.md.CeE4IC-K.js} +1 -1
- package/docs/docs/.vitepress/dist/assets/{api_propsWithDefaults.md.Cr5FwI9o.js → api_propsWithDefaults.md.CeE4IC-K.lean.js} +1 -1
- package/docs/docs/.vitepress/dist/assets/{app.DRiljpSE.js → app.ConZRsN0.js} +1 -1
- package/docs/docs/.vitepress/dist/assets/chunks/@localSearchIndexroot.CGLWArGd.js +1 -0
- package/docs/docs/.vitepress/dist/assets/chunks/Button.vue_vue_type_script_setup_true_lang.P7niV-n8.js +1 -0
- package/docs/docs/.vitepress/dist/assets/chunks/VPLocalSearchBox.C7VDyivS.js +7 -0
- package/docs/docs/.vitepress/dist/assets/chunks/framework.CNtPHGsN.js +1 -0
- package/docs/docs/.vitepress/dist/assets/chunks/index.es.DnWLDAUc.js +1 -0
- package/docs/docs/.vitepress/dist/assets/chunks/theme.B7n-r1TY.js +2 -0
- package/docs/docs/.vitepress/dist/assets/index.md.wPLoTLBY.js +1 -0
- package/docs/docs/.vitepress/dist/assets/index.md.wPLoTLBY.lean.js +1 -0
- package/docs/docs/.vitepress/dist/assets/pages_advanced-usage.md.BZgX-VP7.js +1 -0
- package/docs/docs/.vitepress/dist/assets/pages_advanced-usage.md.BZgX-VP7.lean.js +1 -0
- package/docs/docs/.vitepress/dist/assets/pages_api.md.C_PvCZns.js +7 -0
- package/docs/docs/.vitepress/dist/assets/pages_api.md.C_PvCZns.lean.js +7 -0
- package/docs/docs/.vitepress/dist/assets/pages_browse-code.md.CPluoaap.js +1 -0
- package/docs/docs/.vitepress/dist/assets/pages_browse-code.md.CPluoaap.lean.js +1 -0
- package/docs/docs/.vitepress/dist/assets/pages_getting-started.md.knQcOZyP.js +8 -0
- package/docs/docs/.vitepress/dist/assets/pages_getting-started.md.knQcOZyP.lean.js +1 -0
- package/docs/docs/.vitepress/dist/assets/pages_guidelines.md.DddPdPom.js +101 -0
- package/docs/docs/.vitepress/dist/assets/pages_guidelines.md.DddPdPom.lean.js +101 -0
- package/docs/docs/.vitepress/dist/assets/pages_how-it-works.md.OJGcGEXF.js +4 -0
- package/docs/docs/.vitepress/dist/assets/pages_how-it-works.md.OJGcGEXF.lean.js +4 -0
- package/docs/docs/.vitepress/dist/assets/pages_how-its-made.md.Vv9Z9TEi.js +1 -0
- package/docs/docs/.vitepress/dist/assets/pages_how-its-made.md.Vv9Z9TEi.lean.js +1 -0
- package/docs/docs/.vitepress/dist/assets/pages_introduction.md.DrDm-R8F.js +1 -0
- package/docs/docs/.vitepress/dist/assets/pages_introduction.md.DrDm-R8F.lean.js +1 -0
- package/docs/docs/.vitepress/dist/assets/pages_usage.md.zSOVjtFF.js +430 -0
- package/docs/docs/.vitepress/dist/assets/pages_usage.md.zSOVjtFF.lean.js +430 -0
- package/docs/docs/.vitepress/dist/assets/style.Fgx7OB_D.css +1 -0
- package/docs/docs/.vitepress/dist/hashmap.json +1 -1
- package/docs/docs/.vitepress/dist/index.html +9 -8
- package/docs/docs/.vitepress/dist/pages/advanced-usage.html +24 -0
- package/docs/docs/.vitepress/dist/pages/api.html +30 -0
- package/docs/docs/.vitepress/dist/pages/browse-code.html +24 -0
- package/docs/docs/.vitepress/dist/pages/getting-started.html +11 -11
- package/docs/docs/.vitepress/dist/pages/guidelines.html +125 -0
- package/docs/docs/.vitepress/dist/pages/how-it-works.html +11 -8
- package/docs/docs/.vitepress/dist/pages/how-its-made.html +24 -0
- package/docs/docs/.vitepress/dist/pages/introduction.html +9 -8
- package/docs/docs/.vitepress/dist/pages/usage.html +428 -14
- package/docs/docs/.vitepress/theme/index.js +5 -0
- package/docs/docs/.vitepress/theme/main.css +29 -0
- package/docs/docs/components/Button.vue +1 -1
- package/docs/docs/components/guidelines/CounterExternalRefsDetailed.vue +41 -0
- package/docs/docs/components/usage/CounterBasic.vue +17 -0
- package/docs/docs/components/usage/CounterComposables.vue +19 -0
- package/docs/docs/components/usage/CounterComposablesDestructuring.vue +46 -0
- package/docs/docs/components/usage/CounterComputeds.vue +25 -0
- package/docs/docs/components/usage/CounterComputedsDisabled.vue +32 -0
- package/docs/docs/components/usage/CounterDefineExpose.vue +12 -0
- package/docs/docs/components/usage/CounterDefineExposeAdvanced.vue +25 -0
- package/docs/docs/components/usage/CounterDefineExposeClass.ts +11 -0
- package/docs/docs/components/usage/CounterExternalRefs.vue +25 -0
- package/docs/docs/components/usage/CounterInsideComposables.vue +27 -0
- package/docs/docs/components/usage/CounterInternalRefs.vue +26 -0
- package/docs/docs/components/usage/CounterLifecycleHooks.vue +22 -0
- package/docs/docs/components/usage/CounterWatch.vue +25 -0
- package/docs/docs/components/usage/CounterWithProps.vue +29 -0
- package/docs/docs/components/usage/CounterWithPropsAndEmits.vue +36 -0
- package/docs/docs/components/usage/functions/useMouse.ts +22 -0
- package/docs/docs/index.md +10 -9
- package/docs/docs/pages/advanced-usage.md +11 -0
- package/docs/docs/pages/api.md +106 -0
- package/docs/docs/pages/browse-code.md +18 -0
- package/docs/docs/pages/getting-started.md +23 -5
- package/docs/docs/pages/guidelines.md +128 -0
- package/docs/docs/pages/how-it-works.md +71 -0
- package/docs/docs/pages/how-its-made.md +32 -0
- package/docs/docs/pages/introduction.md +37 -20
- package/docs/docs/pages/usage.md +347 -10
- package/docs/package.json +4 -3
- package/package.json +4 -2
- package/src/__tests__/ivue.vitest.spec.ts +228 -132
- package/src/index.ts +1 -463
- package/src/ivue.ts +495 -0
- package/vite.config.ts +4 -0
- package/docs/.env +0 -1
- package/docs/docs/.vitepress/dist/assets/chunks/framework.CEhE-9HF.js +0 -1
- package/docs/docs/.vitepress/dist/assets/chunks/theme.CldUEgAJ.js +0 -1
- package/docs/docs/.vitepress/dist/assets/index.md.B1vDz5mb.js +0 -1
- package/docs/docs/.vitepress/dist/assets/index.md.B1vDz5mb.lean.js +0 -1
- package/docs/docs/.vitepress/dist/assets/pages_getting-started.md.C7qtPEWU.js +0 -8
- package/docs/docs/.vitepress/dist/assets/pages_getting-started.md.C7qtPEWU.lean.js +0 -1
- package/docs/docs/.vitepress/dist/assets/pages_how-it-works.md.DKizt6Ny.js +0 -1
- package/docs/docs/.vitepress/dist/assets/pages_how-it-works.md.DKizt6Ny.lean.js +0 -1
- package/docs/docs/.vitepress/dist/assets/pages_introduction.md.Dkqu-XCz.js +0 -1
- package/docs/docs/.vitepress/dist/assets/pages_introduction.md.Dkqu-XCz.lean.js +0 -1
- package/docs/docs/.vitepress/dist/assets/pages_usage.md.qo7ICfLC.js +0 -17
- package/docs/docs/.vitepress/dist/assets/pages_usage.md.qo7ICfLC.lean.js +0 -17
- package/docs/docs/.vitepress/dist/assets/style.BSZVsGuP.css +0 -1
- package/docs/docs/components/examples/Counter.vue +0 -17
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
@import url('https://fonts.googleapis.com/css2?family=Public+Sans:ital,wght@0,100..900;1,100..900&display=swap');
|
|
2
|
+
|
|
3
|
+
.VPNavBarTitle {
|
|
4
|
+
font-family: 'Public Sans';
|
|
5
|
+
}
|
|
6
|
+
|
|
7
|
+
.VPNavBarTitle a span {
|
|
8
|
+
font-size: 22px !important;
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
body {
|
|
12
|
+
font-family: 'Public Sans';
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
.button {
|
|
16
|
+
padding: 5px 10px;
|
|
17
|
+
border-color: var(--vp-custom-block-details-border);
|
|
18
|
+
color: var(--vp-custom-block-details-text);
|
|
19
|
+
background-color: var(--vp-custom-block-details-bg);
|
|
20
|
+
border-radius: 5px;
|
|
21
|
+
margin-bottom: 2px;
|
|
22
|
+
transition: 0.5s;
|
|
23
|
+
}
|
|
24
|
+
.button:hover {
|
|
25
|
+
opacity: 0.8;
|
|
26
|
+
}
|
|
27
|
+
.button:active {
|
|
28
|
+
opacity:0.9;
|
|
29
|
+
}
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import { onMounted, ref } from 'vue';
|
|
3
|
+
import { ivue } from 'ivue';
|
|
4
|
+
|
|
5
|
+
type SpanRef = HTMLElement | null;
|
|
6
|
+
|
|
7
|
+
class Counter {
|
|
8
|
+
constructor(public span: SpanRef) {
|
|
9
|
+
// Do not do this in the constructor() because this.span
|
|
10
|
+
// still refers to this.span.value here:
|
|
11
|
+
// onMounted(() => {
|
|
12
|
+
// (this.span as HTMLElement /*❌*/).innerHTML = 'Initial span text!';
|
|
13
|
+
// });
|
|
14
|
+
}
|
|
15
|
+
init() {
|
|
16
|
+
// Do this inside init() because this.span (.value) is now
|
|
17
|
+
// flattened & (this) is now reactive():
|
|
18
|
+
onMounted(() => {
|
|
19
|
+
(this.span as HTMLElement/*✅*/).innerHTML = 'Initial span text!';
|
|
20
|
+
});
|
|
21
|
+
}
|
|
22
|
+
count = ref(0) as unknown as number;
|
|
23
|
+
increment() {
|
|
24
|
+
this.count++;
|
|
25
|
+
(this.span as HTMLElement).innerHTML = String(this.count + 1);
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
const span = ref<SpanRef>();
|
|
30
|
+
const counter = ivue(
|
|
31
|
+
Counter,
|
|
32
|
+
span as unknown as SpanRef /** Unwrap Ref Manually */
|
|
33
|
+
);
|
|
34
|
+
|
|
35
|
+
defineExpose<Counter>(counter);
|
|
36
|
+
</script>
|
|
37
|
+
<template>
|
|
38
|
+
<a href="javascript:void(0)" @click="() => counter.increment()">Increment</a>
|
|
39
|
+
Count: {{ counter.count }} <br />
|
|
40
|
+
<span ref="span"></span>
|
|
41
|
+
</template>
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import { ref } from 'vue';
|
|
3
|
+
import { ivue } from 'ivue';
|
|
4
|
+
|
|
5
|
+
class Counter {
|
|
6
|
+
count = ref(0) as unknown as number;
|
|
7
|
+
increment() {
|
|
8
|
+
this.count++;
|
|
9
|
+
}
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
const counter = ivue(Counter);
|
|
13
|
+
</script>
|
|
14
|
+
<template>
|
|
15
|
+
<a href="javascript:void(0)" @click="() => counter.increment()">Increment</a>
|
|
16
|
+
Count: {{ counter.count }}
|
|
17
|
+
</template>
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import { useMouse } from '@vueuse/core';
|
|
3
|
+
import { ivue, iref, iuse } from '../../../../src/index';
|
|
4
|
+
|
|
5
|
+
class Counter {
|
|
6
|
+
count = iref(0);
|
|
7
|
+
increment() {
|
|
8
|
+
this.count++;
|
|
9
|
+
}
|
|
10
|
+
mouse = iuse(useMouse());
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
const counter = ivue(Counter);
|
|
14
|
+
</script>
|
|
15
|
+
<template>
|
|
16
|
+
<a href="javascript:void(0)" @click="() => counter.increment()">Increment</a>
|
|
17
|
+
Count: {{ counter.count }} <br />
|
|
18
|
+
Mouse: X: {{ counter.mouse.x }}, Y: {{ counter.mouse.y }}
|
|
19
|
+
</template>
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import { ref } from 'vue';
|
|
3
|
+
import { useMouse } from './functions/useMouse';
|
|
4
|
+
import { ivue, type UseComposable } from '@/ivue';
|
|
5
|
+
|
|
6
|
+
/**
|
|
7
|
+
* Use the ivue Utility Type: UseComposable<typeof YourComposableFunctionName>
|
|
8
|
+
* to get he resulting unwrapped composable properties and functions.
|
|
9
|
+
*/
|
|
10
|
+
type UseMouse = UseComposable<typeof useMouse>;
|
|
11
|
+
|
|
12
|
+
class Counter {
|
|
13
|
+
count = ref(0) as unknown as number;
|
|
14
|
+
|
|
15
|
+
increment() {
|
|
16
|
+
this.count++;
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
// x, y are Refs that will be unwrapped and destructured into this class
|
|
20
|
+
x: UseMouse['x']; // Unwrapped Ref<number> becomes -> number
|
|
21
|
+
y: UseMouse['y']; // Unwrapped Ref<number> becomes -> number
|
|
22
|
+
|
|
23
|
+
sum: UseMouse['sum']; // 'sum' method that will be destructured into this class on construct()
|
|
24
|
+
total: UseMouse['total']; // 'total' computed Ref that will also be destructured into this class on construct()
|
|
25
|
+
|
|
26
|
+
constructor() {
|
|
27
|
+
({
|
|
28
|
+
x: this.x,
|
|
29
|
+
y: this.y,
|
|
30
|
+
sum: this.sum,
|
|
31
|
+
total: this.total
|
|
32
|
+
} = useMouse() as unknown as UseMouse);
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
const counter = ivue(Counter);
|
|
37
|
+
</script>
|
|
38
|
+
<template>
|
|
39
|
+
<a href="javascript:void(0)" @click="() => counter.increment()">Increment</a>
|
|
40
|
+
Count: {{ counter.count }} <br />
|
|
41
|
+
Mouse: X: {{ counter.x }}, Y: {{ counter.y }}
|
|
42
|
+
<br />
|
|
43
|
+
Total (computed): {{ counter.total }}
|
|
44
|
+
<br />
|
|
45
|
+
<button class="button" @click="() => counter.sum()">Click This Big Sum Button To Total X + Y</button>
|
|
46
|
+
</template>
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import { ref } from 'vue';
|
|
3
|
+
import { ivue } from 'ivue';
|
|
4
|
+
|
|
5
|
+
class Counter {
|
|
6
|
+
count = ref(0) as unknown as number;
|
|
7
|
+
increment() {
|
|
8
|
+
this.count++;
|
|
9
|
+
}
|
|
10
|
+
get doubleCount() {
|
|
11
|
+
return this.count * 2;
|
|
12
|
+
}
|
|
13
|
+
get quadCount() {
|
|
14
|
+
return this.doubleCount * 2;
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
const counter = ivue(Counter);
|
|
19
|
+
</script>
|
|
20
|
+
<template>
|
|
21
|
+
<a href="javascript:void(0)" @click="() => counter.increment()">Increment</a>
|
|
22
|
+
Count: {{ counter.count }} <br />
|
|
23
|
+
Double Count: {{ counter.doubleCount }} <br />
|
|
24
|
+
Quad Count: {{ counter.quadCount }} <br />
|
|
25
|
+
</template>
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import { ref } from 'vue';
|
|
3
|
+
import { ivue } from 'ivue';
|
|
4
|
+
|
|
5
|
+
class Counter {
|
|
6
|
+
/**
|
|
7
|
+
* Use static ivue property to disable computed
|
|
8
|
+
* behavior for certain getters.
|
|
9
|
+
*/
|
|
10
|
+
static ivue = {
|
|
11
|
+
doubleCount: false // doubleCount is a regular getter now
|
|
12
|
+
}
|
|
13
|
+
count = ref(0) as unknown as number;
|
|
14
|
+
increment() {
|
|
15
|
+
this.count++;
|
|
16
|
+
}
|
|
17
|
+
get doubleCount() {
|
|
18
|
+
return this.count * 2;
|
|
19
|
+
}
|
|
20
|
+
get quadCount() {
|
|
21
|
+
return this.doubleCount * 2;
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
const counter = ivue(Counter);
|
|
26
|
+
</script>
|
|
27
|
+
<template>
|
|
28
|
+
<a href="javascript:void(0)" @click="() => counter.increment()">Increment</a>
|
|
29
|
+
Count: {{ counter.count }} <br />
|
|
30
|
+
Double Count: {{ counter.doubleCount }} <br />
|
|
31
|
+
Quad Count: {{ counter.quadCount }} <br />
|
|
32
|
+
</template>
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import { ivue } from 'ivue';
|
|
3
|
+
import { ref } from 'vue';
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* See that only 'count', 'increment' properties are picked
|
|
7
|
+
* for the define expose interface.
|
|
8
|
+
*/
|
|
9
|
+
export type CounterExposed = Pick<Counter, 'count' | 'increment'>;
|
|
10
|
+
|
|
11
|
+
class Counter {
|
|
12
|
+
count = ref(0) as unknown as number;
|
|
13
|
+
increment() {
|
|
14
|
+
this.count++;
|
|
15
|
+
}
|
|
16
|
+
decrement() {
|
|
17
|
+
this.count--;
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
const counter = ivue(Counter);
|
|
22
|
+
|
|
23
|
+
defineExpose<CounterExposed>(counter);
|
|
24
|
+
</script>
|
|
25
|
+
<template>Count: {{ counter.count }}</template>
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import { ref } from 'vue';
|
|
3
|
+
import { ivue } from 'ivue';
|
|
4
|
+
|
|
5
|
+
type SpanRef = HTMLElement | null;
|
|
6
|
+
|
|
7
|
+
class Counter {
|
|
8
|
+
constructor(public span: SpanRef) {}
|
|
9
|
+
count = ref(0) as unknown as number;
|
|
10
|
+
increment() {
|
|
11
|
+
this.count++;
|
|
12
|
+
(this.span as HTMLElement).innerHTML = String(this.count + 1);
|
|
13
|
+
}
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
const span = ref<SpanRef>();
|
|
17
|
+
const counter = ivue(Counter, span as unknown as SpanRef /** Unwrap Ref Manually */);
|
|
18
|
+
|
|
19
|
+
defineExpose<Counter>(counter);
|
|
20
|
+
</script>
|
|
21
|
+
<template>
|
|
22
|
+
<a href="javascript:void(0)" @click="() => counter.increment()">Increment</a>
|
|
23
|
+
Count: {{ counter.count }}
|
|
24
|
+
<span ref="span"></span>
|
|
25
|
+
</template>
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import { ref } from 'vue';
|
|
3
|
+
import { ivue } from 'ivue';
|
|
4
|
+
|
|
5
|
+
class Counter {
|
|
6
|
+
count = ref(0) as unknown as number;
|
|
7
|
+
increment() {
|
|
8
|
+
this.count++;
|
|
9
|
+
}
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
function useCounter() {
|
|
13
|
+
/** Convert ivue Counter to a composable with .toRefs() */
|
|
14
|
+
const { count, increment } = ivue(Counter).toRefs();
|
|
15
|
+
|
|
16
|
+
return {
|
|
17
|
+
count,
|
|
18
|
+
increment,
|
|
19
|
+
};
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
const { count, increment } = useCounter();
|
|
23
|
+
</script>
|
|
24
|
+
<template>
|
|
25
|
+
<a href="javascript:void(0)" @click="increment">Increment</a>
|
|
26
|
+
Count: {{ count }} <br />
|
|
27
|
+
</template>
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import { ref } from 'vue';
|
|
3
|
+
import { ivue } from 'ivue';
|
|
4
|
+
|
|
5
|
+
class Counter {
|
|
6
|
+
count = ref(0) as unknown as number;
|
|
7
|
+
span = ref(null) as unknown as HTMLElement | null;
|
|
8
|
+
increment() {
|
|
9
|
+
this.count++;
|
|
10
|
+
(this.span as HTMLElement).innerHTML = String(this.count + 1);
|
|
11
|
+
}
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
const counter = ivue(Counter);
|
|
15
|
+
const { span } = counter.toRefs(['span']);
|
|
16
|
+
/**
|
|
17
|
+
* Or you can use `const { span } = counter.toRefs();`
|
|
18
|
+
* but `const { span } = counter.toRefs(['span']);` is more performant
|
|
19
|
+
* because we are only looping through 1 property instead of all of them.
|
|
20
|
+
*/
|
|
21
|
+
</script>
|
|
22
|
+
<template>
|
|
23
|
+
<a href="javascript:void(0)" @click="() => counter.increment()">Increment</a>
|
|
24
|
+
Count: {{ counter.count }}
|
|
25
|
+
<span ref="span"></span>
|
|
26
|
+
</template>
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import { onMounted, ref } from 'vue';
|
|
3
|
+
import { ivue } from 'ivue';
|
|
4
|
+
|
|
5
|
+
class Counter {
|
|
6
|
+
init() {
|
|
7
|
+
onMounted(() => {
|
|
8
|
+
this.count = 100;
|
|
9
|
+
});
|
|
10
|
+
}
|
|
11
|
+
count = ref(0) as unknown as number;
|
|
12
|
+
increment() {
|
|
13
|
+
this.count++;
|
|
14
|
+
}
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
const counter = ivue(Counter);
|
|
18
|
+
</script>
|
|
19
|
+
<template>
|
|
20
|
+
<a href="javascript:void(0)" @click="() => counter.increment()">Increment</a>
|
|
21
|
+
Count: {{ counter.count }} (onMounted we set it to 100)
|
|
22
|
+
</template>
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import { ref, watch } from 'vue';
|
|
3
|
+
import { ivue } from 'ivue';
|
|
4
|
+
|
|
5
|
+
class Counter {
|
|
6
|
+
init() {
|
|
7
|
+
/** Note that we use this.count as a reactive prop in the watch() function */
|
|
8
|
+
watch(() => this.count, (newCount) => {
|
|
9
|
+
if (newCount === 5) {
|
|
10
|
+
alert('You already clicked 5 times!');
|
|
11
|
+
}
|
|
12
|
+
});
|
|
13
|
+
}
|
|
14
|
+
count = ref(0) as unknown as number;
|
|
15
|
+
increment() {
|
|
16
|
+
this.count++;
|
|
17
|
+
}
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
const counter = ivue(Counter);
|
|
21
|
+
</script>
|
|
22
|
+
<template>
|
|
23
|
+
<a href="javascript:void(0)" @click="() => counter.increment()">Increment</a>
|
|
24
|
+
Count: {{ counter.count }} (Click 5 times to get an alert)
|
|
25
|
+
</template>
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import { ref } from 'vue';
|
|
3
|
+
import { ivue } from 'ivue';
|
|
4
|
+
|
|
5
|
+
interface CounterProps {
|
|
6
|
+
initialCount: number;
|
|
7
|
+
}
|
|
8
|
+
const props = defineProps<CounterProps>();
|
|
9
|
+
|
|
10
|
+
class Counter {
|
|
11
|
+
constructor(public props: CounterProps) {
|
|
12
|
+
this.count = this.props.initialCount;
|
|
13
|
+
}
|
|
14
|
+
count = ref(0) as unknown as number;
|
|
15
|
+
increment() {
|
|
16
|
+
this.count++;
|
|
17
|
+
}
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
/**
|
|
21
|
+
* NOTICE that: ivue(ClassName, ...args) uses TypeScript to infer
|
|
22
|
+
* the correct argument types that you need to pass to the constructor.
|
|
23
|
+
*/
|
|
24
|
+
const counter = ivue(Counter, props);
|
|
25
|
+
</script>
|
|
26
|
+
<template>
|
|
27
|
+
<a href="javascript:void(0)" @click="() => counter.increment()">Increment</a>
|
|
28
|
+
Count: {{ counter.count }}
|
|
29
|
+
</template>
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
import { ref } from 'vue';
|
|
3
|
+
import { ivue } from 'ivue';
|
|
4
|
+
|
|
5
|
+
interface CounterProps {
|
|
6
|
+
initialCount: number;
|
|
7
|
+
}
|
|
8
|
+
|
|
9
|
+
interface CounterEmits {
|
|
10
|
+
(e: 'increment', count: number): void;
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
const props = defineProps<CounterProps>();
|
|
14
|
+
const emit = defineEmits<CounterEmits>();
|
|
15
|
+
|
|
16
|
+
class Counter {
|
|
17
|
+
constructor(public props: CounterProps, public emit: CounterEmits) {
|
|
18
|
+
this.count = this.props.initialCount;
|
|
19
|
+
}
|
|
20
|
+
count = ref(0) as unknown as number;
|
|
21
|
+
increment() {
|
|
22
|
+
this.count++;
|
|
23
|
+
this.emit('increment', this.count);
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
/**
|
|
28
|
+
* NOTICE that: ivue(ClassName, ...args) uses TypeScript to infer
|
|
29
|
+
* the correct argument types that you need to pass to the constructor.
|
|
30
|
+
*/
|
|
31
|
+
const counter = ivue(Counter, props, emit);
|
|
32
|
+
</script>
|
|
33
|
+
<template>
|
|
34
|
+
<a href="javascript:void(0)" @click="() => counter.increment()">Increment</a>
|
|
35
|
+
Count: {{ counter.count }}
|
|
36
|
+
</template>
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import { computed, ref } from 'vue';
|
|
2
|
+
import { useMouse as _useMouse } from '@vueuse/core';
|
|
3
|
+
|
|
4
|
+
export function useMouse() {
|
|
5
|
+
const { x, y } = _useMouse();
|
|
6
|
+
const _sum = ref(0);
|
|
7
|
+
|
|
8
|
+
function sum() {
|
|
9
|
+
_sum.value = x.value + y.value;
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
const total = computed(() => {
|
|
13
|
+
return _sum;
|
|
14
|
+
});
|
|
15
|
+
|
|
16
|
+
return {
|
|
17
|
+
x,
|
|
18
|
+
y,
|
|
19
|
+
sum,
|
|
20
|
+
total,
|
|
21
|
+
};
|
|
22
|
+
}
|
package/docs/docs/index.md
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
<script lang="ts"
|
|
1
|
+
<script setup lang="ts">
|
|
2
2
|
import Button from './components/Button.vue'
|
|
3
3
|
|
|
4
4
|
</script>
|
|
5
|
-
# Documentation
|
|
5
|
+
# Infinite Vue Documentation
|
|
6
6
|
|
|
7
7
|
|
|
8
8
|
## About
|
|
@@ -12,14 +12,15 @@ import Button from './components/Button.vue'
|
|
|
12
12
|
## Features
|
|
13
13
|
<div style="padding-left:20px;">
|
|
14
14
|
– Simple & Elegant Architecture<br />
|
|
15
|
-
–
|
|
16
|
-
–
|
|
17
|
-
–
|
|
18
|
-
–
|
|
19
|
-
–
|
|
20
|
-
– Improves DX by elegantly dealing with
|
|
21
|
-
– Can be used both as a Store and a
|
|
15
|
+
– Extensible Classes using JavaScript / TypeScript native Class API<br />
|
|
16
|
+
– Extensible Props And Props Defaults<br />
|
|
17
|
+
– Extensible Emits<br />
|
|
18
|
+
– Extensible Slots<br />
|
|
19
|
+
– Extensible Components<br />
|
|
20
|
+
– Improves DX by elegantly dealing with `.value` in the background<br />
|
|
21
|
+
– Can be used both as a Store and a ViewModel for Components<br />
|
|
22
22
|
– Provides Full TypeScript Support<br />
|
|
23
|
+
– Extends Vue 3 TypeScript Capability<br />
|
|
23
24
|
– 100% Tested<br />
|
|
24
25
|
– Zero dependencies except Vue 3<br />
|
|
25
26
|
– Only 1kb(gzipped) in size!<br />
|
|
@@ -0,0 +1,106 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
</script>
|
|
3
|
+
|
|
4
|
+
# API
|
|
5
|
+
|
|
6
|
+
## Core Functions
|
|
7
|
+
|
|
8
|
+
### ivue()
|
|
9
|
+
|
|
10
|
+
---
|
|
11
|
+
|
|
12
|
+
```ts
|
|
13
|
+
export function ivue<T extends AnyClass>(
|
|
14
|
+
className: T,
|
|
15
|
+
...args: InferredArgs<T>
|
|
16
|
+
): IVue<T>;
|
|
17
|
+
```
|
|
18
|
+
|
|
19
|
+
Core `ivue(className, ...args)` initializer is able to infer and validate the constrcutor argument types of AnyClass and passes those arguments to the constructor of `AnyClass` internally.
|
|
20
|
+
|
|
21
|
+
`ivue(className, arg1, arg2, arg3...)` allows you to pass any number of arguments into the class `constructor(arg1, arg2, arg3...)`
|
|
22
|
+
|
|
23
|
+
`ivue()` initializer function returns an extended Vue 3 `reactive()` object in which getters and setters are internally converted to computeds and adds `.toRefs()` method to the created object. Computeds auto-unwrap themselves when they are accessed as a reactive object property, so the `.value` properties and computeds get flattened in the resulting object and do not require `.value` to be accessed.
|
|
24
|
+
|
|
25
|
+
`ivue()` replicates native JavaScript / TypeScript class implementation by extending descriptors (getters and setters) up the whole prototype chain thus supporting classical inheritance.
|
|
26
|
+
|
|
27
|
+
**Returns:** `<IVue<T>>` or `ivue` `reactive()` object of an `AnyClass` class with flattened (de-Refed) `Refs` and `ComputedRefs` as properties.
|
|
28
|
+
|
|
29
|
+
### .init()
|
|
30
|
+
|
|
31
|
+
---
|
|
32
|
+
|
|
33
|
+
`.init()` method is auto-run on `ivue()` initialization after `constructor()` is run.
|
|
34
|
+
`init()` has access to the reactive state of the object via `this`.
|
|
35
|
+
|
|
36
|
+
:::warning NOTICE
|
|
37
|
+
`.init()` method shoud not have any parameters. You should never need to run this method manually.
|
|
38
|
+
:::
|
|
39
|
+
|
|
40
|
+
:::tip NEED ASYNC/AWAIT?
|
|
41
|
+
You can make `init()` method `async` if you need `await` functionality.
|
|
42
|
+
:::
|
|
43
|
+
|
|
44
|
+
**Returns:** `void | Promise<void>`
|
|
45
|
+
|
|
46
|
+
### .toRefs()
|
|
47
|
+
|
|
48
|
+
---
|
|
49
|
+
|
|
50
|
+
```ts
|
|
51
|
+
function toRefs(props?: (keyof InstanceType<T>)[]): IVueRefs<InstanceType<T>>;
|
|
52
|
+
```
|
|
53
|
+
|
|
54
|
+
Converts an `ivue` object to a Vue 3 Composable with nested refs.
|
|
55
|
+
|
|
56
|
+
:::tip You can pass the name of the properties to `toRefs(properties)`
|
|
57
|
+
```ts
|
|
58
|
+
const { width, height } = ivue(Box).toRefs(['width', 'height']);
|
|
59
|
+
```
|
|
60
|
+
This improves performance if `box` has many other properties that we do not need.
|
|
61
|
+
:::
|
|
62
|
+
|
|
63
|
+
**Returns:** `IVueRefs<InstanceType<T>>`
|
|
64
|
+
|
|
65
|
+
## Utility Functions
|
|
66
|
+
|
|
67
|
+
### propsWithDefaults()
|
|
68
|
+
|
|
69
|
+
---
|
|
70
|
+
|
|
71
|
+
```ts
|
|
72
|
+
export function propsWithDefaults<T extends VuePropsObject>(
|
|
73
|
+
defaults: Record<string, any>,
|
|
74
|
+
typedProps: T
|
|
75
|
+
): VuePropsWithDefaults<T>;
|
|
76
|
+
```
|
|
77
|
+
|
|
78
|
+
Combines statically written defaults object with the runtime type definition of Vue 3 props.
|
|
79
|
+
|
|
80
|
+
**Returns:** `VuePropsWithDefaults<T>`
|
|
81
|
+
|
|
82
|
+
## Utility Types
|
|
83
|
+
|
|
84
|
+
### ExtractPropDefaultTypes
|
|
85
|
+
|
|
86
|
+
Extracts types of the default types definition. This type can be used to validate against the actual defaults definition to make sure both definitions are in sync.
|
|
87
|
+
|
|
88
|
+
---
|
|
89
|
+
|
|
90
|
+
### ExtractEmitTypes
|
|
91
|
+
|
|
92
|
+
---
|
|
93
|
+
|
|
94
|
+
Extracts types of a runtime emits declaration.
|
|
95
|
+
|
|
96
|
+
### ExtendSlots
|
|
97
|
+
|
|
98
|
+
---
|
|
99
|
+
|
|
100
|
+
Allows you to extend slots of a given slot interface.
|
|
101
|
+
|
|
102
|
+
### UseComposable
|
|
103
|
+
|
|
104
|
+
---
|
|
105
|
+
|
|
106
|
+
Extracts and unwraps (de-Refs) the real types of Vue 3 composable definition to make it compatible with `ivue`.
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
---
|
|
2
|
+
aside: false
|
|
3
|
+
---
|
|
4
|
+
# Source code
|
|
5
|
+
Or [Browse the source code on GitHub](https://github.com/infinite-system/ivue/blob/main/src/index.ts)
|
|
6
|
+
|
|
7
|
+
## Install by Copying
|
|
8
|
+
|
|
9
|
+
`ivue` is designed to be easily shareable and installable so if you are running TypeScript, you can just copy the
|
|
10
|
+
`ivue.ts` into your repo and you are done:
|
|
11
|
+
|
|
12
|
+
::: tip NOTE
|
|
13
|
+
This installation path is recommended only if you quickly want to tinker with the internals of ivue, as you won't be getting the latest updates. Also note that this code comes from github `main` branch latest which might also be in beta and not fully published to `npm`.
|
|
14
|
+
:::
|
|
15
|
+
|
|
16
|
+
:::code-group
|
|
17
|
+
<<< ../../../src/index.ts{ts:line-numbers} [ivue.ts]
|
|
18
|
+
:::
|