Skip to content

Instantly share code, notes, and snippets.

@Akryum
Last active September 14, 2023 08:59
Show Gist options
  • Star 3 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save Akryum/2670684086c92b846ba3be657243435f to your computer and use it in GitHub Desktop.
Save Akryum/2670684086c92b846ba3be657243435f to your computer and use it in GitHub Desktop.
Eager Vue computed property - use for cheap computed properties that always update but that don't trigger updates when their value doesn't change
export function useEagerComputed() {
const properties = []
function eagerComputed(definitions) {
const computedProps = {}
for (const key in definitions) {
const effect = definitions[key]
properties.push({ key, effect })
computedProps[key] = function () {
return this.$data[key]
}
}
return computedProps
}
const mixin = {
data() {
const data = {}
for (const prop of properties) {
data[prop.key] = undefined
}
return data
},
created() {
for (const prop of properties) {
this.$watch(prop.effect.bind(this), (value) => {
this.$data[prop.key] = value
})
}
}
}
return {
mixin,
eagerComputed
}
}
// Usage in component:
const { mixin, eagerComputed } = useEagerComputed()
export default {
name: 'HelloWorld',
mixins: [mixin],
data() {
return {
loadingId: 0,
id: 0
}
},
methods: {
update() {
this.loadingId = (this.loadingId + 1) % 3
}
},
computed: {
...eagerComputed({
isLoading() {
return this.loadingId === this.id
}
}),
myObj() {
console.log('computation')
return {
isLoading: this.isLoading
}
}
}
}
export function eagerComputedMixin<T = any> (key: string, effect: () => T) {
return {
data () {
return {
[key]: undefined,
}
},
created () {
this.$watch(effect.bind(this), (value) => {
this.$data[key] = value
})
},
}
}
import { watchEffect, readonly } from '@vue/composition-api'
export function eagerComputed<T = any> (effect: () => T) {
const holder = ref<T>()
watchEffect(() => {
holder.value = effect()
})
return readonly(holder)
}
import { watchEffect, readonly } from 'vue'
export function eagerComputed<T = any> (effect: () => T) {
const holder = ref<T>()
watchEffect(() => {
holder.value = effect()
})
return readonly(holder)
}
@Akryum
Copy link
Author

Akryum commented Feb 26, 2021

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment