Skip to content

Commit 28b3e1b

Browse files
committed
fix: using .xx-xx underlined naming conventions when used by WebComponent is reactive #5687
1 parent 1070f12 commit 28b3e1b

File tree

2 files changed

+44
-9
lines changed

2 files changed

+44
-9
lines changed

packages/runtime-dom/__tests__/customElement.spec.ts

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -210,6 +210,27 @@ describe('defineCustomElement', () => {
210210
customElements.define('my-el-upgrade', E)
211211
expect(el.shadowRoot.innerHTML).toBe(`foo: hello`)
212212
})
213+
214+
// #5687
215+
test('using .xx-xx underlined naming conventions when used by WebComponent is reactive', () => {
216+
const E = defineCustomElement({
217+
props: {
218+
maxAge: Number
219+
},
220+
render() {
221+
return `max age: ${this.maxAge}`
222+
}
223+
})
224+
customElements.define('my-element-hyphenate', E)
225+
const el = document.createElement('my-element-hyphenate') as any
226+
el.setAttribute('max-age', 0)
227+
container.appendChild(el)
228+
expect(el.maxAge).toBe(0)
229+
el.maxAge = 50
230+
expect(el.maxAge).toBe(50)
231+
el['max-age'] = 100
232+
expect(el.maxAge).toBe(100)
233+
})
213234
})
214235

215236
describe('emits', () => {

packages/runtime-dom/src/apiCustomElement.ts

Lines changed: 23 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -241,14 +241,10 @@ export class VueElement extends BaseClass {
241241

242242
// defining getter/setters on prototype
243243
for (const key of rawKeys.map(camelize)) {
244-
Object.defineProperty(this, key, {
245-
get() {
246-
return this._getProp(key)
247-
},
248-
set(val) {
249-
this._setProp(key, val)
250-
}
251-
})
244+
this._defineElementProperty(key)
245+
if (hyphenate(key) !== key) {
246+
this._defineElementProperty(hyphenate(key), key, false)
247+
}
252248
}
253249

254250
// apply CSS
@@ -266,9 +262,27 @@ export class VueElement extends BaseClass {
266262
}
267263
}
268264

265+
private _defineElementProperty(
266+
key: string,
267+
originalKey = key,
268+
shouldReflect = true
269+
) {
270+
Object.defineProperty(this, key, {
271+
get() {
272+
return this._getProp(originalKey)
273+
},
274+
set(val) {
275+
this._setProp(originalKey, val, shouldReflect)
276+
}
277+
})
278+
}
279+
269280
protected _setAttr(key: string) {
270281
let value = this.getAttribute(key)
271-
if (this._numberProps && this._numberProps[key]) {
282+
if (
283+
this._numberProps &&
284+
(this._numberProps[key] || this._numberProps[camelize(key)])
285+
) {
272286
value = toNumber(value)
273287
}
274288
this._setProp(camelize(key), value, false)

0 commit comments

Comments
 (0)