I have a vue single file component, which have a custom class instance as property: now i want to bind a event to a method of this class instance but i'm having issues, there is a simplified version of my code files
<template>
<div @click="class_prop.method"></div>
</template>
export default {
data() {
return {
class_prop: new CustomClass(),
};
},
}
class CustomClass {
constructor(){
this.prop = 'default_value';
}
method(){
this.prop = 'new_value';
console.log(this.prop);
}
}
When clicking on the page element i receive this error:
[Vue warn]: Error in v-on handler: "TypeError: Cannot read property 'prop' of null"
But when i try to call the custom class method from the browser console (i'm using Chrome with Vue Devtools extension) i get NO error, it works correctly:
$vm0.class_prop.method()
Since i get two different behaviours of my code i cannot tell if it is my class wrong, the vue single file component, or something else.
Behind the scenes Vue somehow called or applied your method using null. Thus the error you've mentioned:
Error in v-on handler: "TypeError: Cannot read property 'prop' of null"
What can you do to workaround the problem?
You can use a lambda expression, so you can have full control of the object owner of the method, like this:
<div @click="() => class_prop.method()"></div>
You can also use the class instance in a method like this:
export default {
data: () => ({
foo: new CustomClass(),
}),
methods: {
bar() {
this.foo.method();
},
},
}
And then in your template:
<div @click="bar">{{ foo.prop }}</div>
What you see is not Vue's fault, it's just plain JavaScript.
Here is a citation from great JS learning resource
The consequences of unbound
this
If you come from another programming language, then you are probably used to the idea of a "bound this", where methods defined in an object always have
thisreferencing that object. In JavaScriptthisis “free”, its value is evaluated at call-time and does not depend on where the method was declared, but rather on what object is “before the dot”.
Here is very simple example of consequences of above paragraphs (and why your code does not work):
class CustomClass {
constructor() {
this.prop = 'default_value';
}
method() {
this.prop = 'new_value';
console.log(this.prop);
}
}
let instance = new CustomClass()
instance.method() // this works OK
let f = instance.method
f() // this does not! f is "unbound" ....have no "this"
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With