vue3-core/packages/runtime-dom/src/modules/attrs.ts

80 lines
1.8 KiB
TypeScript
Raw Normal View History

import { isSpecialBooleanAttr } from '@vue/shared'
export const xlinkNS = 'http://www.w3.org/1999/xlink'
2020-01-29 07:48:27 +08:00
export function patchAttr(
el: Element,
key: string,
value: any,
isSVG: boolean
) {
if (isSVG && key.startsWith('xlink:')) {
if (value == null) {
el.removeAttributeNS(xlinkNS, key.slice(6, key.length))
} else {
el.setAttributeNS(xlinkNS, key, value)
}
2018-09-19 23:35:38 +08:00
} else {
2021-04-08 05:36:56 +08:00
if (__COMPAT__ && compatCoerceAttr(el, key, value)) {
return
}
// note we are only checking boolean attributes that don't have a
2020-05-01 21:42:58 +08:00
// corresponding dom prop of the same name here.
const isBoolean = isSpecialBooleanAttr(key)
if (value == null || (isBoolean && value === false)) {
el.removeAttribute(key)
} else {
el.setAttribute(key, isBoolean ? '' : value)
}
2018-09-19 23:35:38 +08:00
}
}
2021-04-08 05:36:56 +08:00
// 2.x compat
import { makeMap, NOOP } from '@vue/shared'
import { compatUtils, DeprecationTypes } from '@vue/runtime-core'
const isEnumeratedAttr = __COMPAT__
? /*#__PURE__*/ makeMap('contenteditable,draggable,spellcheck')
: NOOP
export function compatCoerceAttr(
el: Element,
key: string,
value: unknown
): boolean {
if (isEnumeratedAttr(key)) {
const v2CocercedValue =
value === null
? 'false'
: typeof value !== 'boolean' && value !== undefined
? 'true'
: null
if (
v2CocercedValue &&
compatUtils.softAssertCompatEnabled(
DeprecationTypes.ATTR_ENUMERATED_COERSION,
2021-04-10 11:21:13 +08:00
null,
2021-04-08 05:36:56 +08:00
key,
value,
v2CocercedValue
)
) {
el.setAttribute(key, v2CocercedValue)
return true
}
} else if (
value === false &&
!isSpecialBooleanAttr(key) &&
2021-04-10 11:21:13 +08:00
compatUtils.softAssertCompatEnabled(
DeprecationTypes.ATTR_FALSE_VALUE,
null,
key
)
2021-04-08 05:36:56 +08:00
) {
el.removeAttribute(key)
return true
}
return false
}