Reputation: 95
I'm going through Egghead's React tutorial and in one of the lessons I found the following class declaration:
class StopWatch extends React.Component {
state = {lapse: 0, running: false}
render() {
const {lapse, running} = this.state
const buttonStyles = {
border: '1px solid #ccc',
background: '#fff',
fontSize: '2em',
padding: 15,
margin: 5,
width: 200
}
return (
<div style={{textAlign: 'center'}}>
<label style={{fontSize: '5em', display: 'block'}}>
{lapse}ms
</label>
<button style={buttonStyles}>{running ? 'Stop' : 'Start'}</button>
<button style={buttonStyles}>Clear</button>
</div>
)
}
}
So looking at the code, I was just curious about that assignment on the top. I looked at the class and extends documentations on MDN and it doesn't say anything about allowing an assignment inside a class declaration.
Furthermore, I tried it on a sample code and it's throwing an error:
class Square {
constructor(prop1, prop2) {
this.prop1 = prop1
this.prop2 = prop2
}
}
class Polygon extends Square {
constructor(prop1, prop2, prop3) {
super(prop1, prop2)
}
prop2 = prop3
render() {
console.log(prop2)
}
}
So... why does it work?
Upvotes: 1
Views: 158
Reputation: 222979
The subclass uses class fields which are stage 3 proposal and aren't a part of existing standard. They provide syntactic sugar for constructor body. As explained in this question, there's a specific order in which class field assignments are performed.
The subclass is identical to this ES6 class (check also Babel output to get some ideas what's going on):
class Polygon extends Square {
constructor(prop1, prop2, prop3_that_doesnt_collide) {
super(prop1, prop2);
this.prop2 = prop3;
}
render() {
console.log(prop2)
}
}
console.log(prop2)
refers to non-existing prop2
variable and not prop2
property.
Notice that because prop3
was located outside constructor method, it doesn't refer to prop3
constructor parameter but to some non-existing prop3
variable, so prop3_that_doesnt_collide
parameter and prop3
don't collide.
Since prop2
assignment relies on constructor parameter, it should be placed inside constructor method:
class Polygon extends Square {
constructor(prop1, prop2, prop3) {
super(prop1, prop2);
this.prop2 = prop3;
}
render() {
console.log(this.prop2)
}
}
Since it just immediately replaces prop2
value with prop3
, it can be:
constructor(prop1, prop2, prop3) {
super(prop1, prop3);
}
Upvotes: 1
Reputation: 1279
The syntax you're trying to use is not standardized and you'll need Babel to transpile your code. Alternatively you can use static members in classes -
let Foo = class {
static get staticData() {
return 'Static Data';
}
}
console.log(Foo.staticData);
Upvotes: 0