-
Notifications
You must be signed in to change notification settings - Fork 3.7k
/
Copy pathtransformHidden.ts
106 lines (101 loc) · 2.97 KB
/
transformHidden.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
import {
type Expression,
binaryExpression,
booleanLiteral,
conditionalExpression,
identifier,
isIdentifier,
logicalExpression,
stringLiteral,
unaryExpression,
} from '@babel/types'
import {
type AttributeNode,
type DirectiveNode,
NodeTypes,
createSimpleExpression,
} from '@vue/compiler-core'
import { VIRTUAL_HOST_HIDDEN } from '@dcloudio/uni-shared'
import { createBindDirectiveNode } from '@dcloudio/uni-cli-shared'
import { parseExpr } from '../ast'
import { genBabelExpr } from '../codegen'
import type { TransformContext } from '../transform'
import { rewriteExpression } from './utils'
export function isHiddenBinding({ arg, exp }: DirectiveNode) {
return (
arg && arg.type === NodeTypes.SIMPLE_EXPRESSION && arg.content === 'hidden'
)
}
export function findStaticHiddenIndex(
props: (AttributeNode | DirectiveNode)[]
) {
return props.findIndex((prop) => prop.name === 'hidden')
}
export function findVShowIndex(props: (AttributeNode | DirectiveNode)[]) {
return props.findIndex(
(prop) => prop.name === 'show' && prop.type === NodeTypes.DIRECTIVE
)
}
export function rewriteHidden(
index: number,
hiddenBindingProp: DirectiveNode,
props: (AttributeNode | DirectiveNode)[],
virtualHost: boolean,
context: TransformContext
) {
let bindingProp = hiddenBindingProp
const vShowIndex = findVShowIndex(props)
if (vShowIndex > -1) {
bindingProp = props[vShowIndex] as DirectiveNode
}
let expr = bindingProp.exp ? parseExpr(bindingProp.exp, context) : undefined
let hiddenBindingExpr: Expression
if (virtualHost) {
const staticClassPropIndex = findStaticHiddenIndex(props)
// skyline模式hidden传undefined会导致元素被隐藏
const virtualHostHiddenPolyfill = logicalExpression(
'||',
identifier(VIRTUAL_HOST_HIDDEN),
booleanLiteral(false)
)
if (expr || staticClassPropIndex > -1) {
let res: Expression = booleanLiteral(true)
if (expr) {
// TODO ignore all simple expression
res = isIdentifier(expr)
? expr
: identifier(rewriteExpression(bindingProp.exp!, context).content)
if (vShowIndex > -1) {
props.splice(vShowIndex, 1)
res = unaryExpression('!', res)
}
}
hiddenBindingExpr = conditionalExpression(
binaryExpression(
'!==',
identifier(VIRTUAL_HOST_HIDDEN),
stringLiteral('')
),
virtualHostHiddenPolyfill,
res
)
} else {
hiddenBindingExpr = virtualHostHiddenPolyfill
}
} else {
// ignore rewrite without virtualHost
return
}
hiddenBindingProp.exp = createSimpleExpression(
genBabelExpr(hiddenBindingExpr)
)
}
export function createVirtualHostHidden(
props: (AttributeNode | DirectiveNode)[],
context: TransformContext
) {
const hiddenBindingProp = createBindDirectiveNode('hidden', '')
delete hiddenBindingProp.exp
rewriteHidden(0, hiddenBindingProp, props, true, context)
return hiddenBindingProp
}