Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
xxadev
vscode
提交
f31b3de9
V
vscode
项目概览
xxadev
/
vscode
与 Fork 源项目一致
从无法访问的项目Fork
通知
2
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
V
vscode
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
提交
Issue看板
体验新版 GitCode,发现更多精彩内容 >>
提交
f31b3de9
编写于
1月 30, 2020
作者:
M
Martin Aeschlimann
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
improve inspect token hover
上级
8345780f
变更
2
隐藏空白更改
内联
并排
Showing
2 changed file
with
124 addition
and
105 deletion
+124
-105
src/vs/workbench/contrib/codeEditor/browser/inspectEditorTokens/inspectEditorTokens.css
...ditor/browser/inspectEditorTokens/inspectEditorTokens.css
+11
-0
src/vs/workbench/contrib/codeEditor/browser/inspectEditorTokens/inspectEditorTokens.ts
...Editor/browser/inspectEditorTokens/inspectEditorTokens.ts
+113
-105
未找到文件。
src/vs/workbench/contrib/codeEditor/browser/inspectEditorTokens/inspectEditorTokens.css
浏览文件 @
f31b3de9
...
...
@@ -33,6 +33,17 @@
font-family
:
var
(
--monaco-monospace-font
);
text-align
:
right
;
}
.tiw-metadata-key
{
vertical-align
:
top
;
}
.tiw-metadata-semantic
{
font-style
:
italic
;
}
.tiw-metadata-scopes
{
line-height
:
normal
;
}
.tiw-theme-selector
{
font-family
:
var
(
--monaco-monospace-font
);
...
...
src/vs/workbench/contrib/codeEditor/browser/inspectEditorTokens/inspectEditorTokens.ts
浏览文件 @
f31b3de9
...
...
@@ -17,7 +17,7 @@ import { Position } from 'vs/editor/common/core/position';
import
{
Range
}
from
'
vs/editor/common/core/range
'
;
import
{
IEditorContribution
}
from
'
vs/editor/common/editorCommon
'
;
import
{
ITextModel
}
from
'
vs/editor/common/model
'
;
import
{
FontStyle
,
LanguageIdentifier
,
StandardTokenType
,
TokenMetadata
,
DocumentSemanticTokensProviderRegistry
,
SemanticTokensLegend
,
SemanticTokens
,
LanguageId
}
from
'
vs/editor/common/modes
'
;
import
{
FontStyle
,
LanguageIdentifier
,
StandardTokenType
,
TokenMetadata
,
DocumentSemanticTokensProviderRegistry
,
SemanticTokensLegend
,
SemanticTokens
,
LanguageId
,
ColorId
}
from
'
vs/editor/common/modes
'
;
import
{
IModeService
}
from
'
vs/editor/common/services/modeService
'
;
import
{
INotificationService
}
from
'
vs/platform/notification/common/notification
'
;
import
{
editorHoverBackground
,
editorHoverBorder
}
from
'
vs/platform/theme/common/colorRegistry
'
;
...
...
@@ -27,7 +27,7 @@ import { ITextMateService, IGrammar, IToken, StackElement } from 'vs/workbench/s
import
{
IWorkbenchThemeService
}
from
'
vs/workbench/services/themes/common/workbenchThemeService
'
;
import
{
CancellationTokenSource
}
from
'
vs/base/common/cancellation
'
;
import
{
ColorThemeData
,
TokenStyleDefinitions
,
TokenStyleDefinition
}
from
'
vs/workbench/services/themes/common/colorThemeData
'
;
import
{
TokenStylingRule
}
from
'
vs/platform/theme/common/tokenClassificationRegistry
'
;
import
{
TokenStylingRule
,
TokenStyleData
}
from
'
vs/platform/theme/common/tokenClassificationRegistry
'
;
import
{
IConfigurationService
}
from
'
vs/platform/configuration/common/configuration
'
;
import
type
{
IEditorSemanticHighlightingOptions
}
from
'
vs/editor/common/config/editorOptions
'
;
...
...
@@ -128,14 +128,16 @@ interface ISemanticTokenInfo {
type
:
string
;
modifiers
:
string
[];
range
:
Range
;
metadata
:
IDecodedMetadata
,
metadata
?
:
IDecodedMetadata
,
definitions
:
TokenStyleDefinitions
}
interface
IDecodedMetadata
{
languageIdentifier
:
LanguageIdentifier
;
tokenType
:
StandardTokenType
;
fontStyle
:
string
;
bold
?:
boolean
;
italic
?:
boolean
;
underline
?:
boolean
;
foreground
?:
string
;
background
?:
string
;
}
...
...
@@ -262,97 +264,137 @@ class InspectEditorTokensWidget extends Disposable implements IContentWidget {
private
_compute
(
grammar
:
IGrammar
|
null
,
semanticTokens
:
SemanticTokensResult
|
null
,
position
:
Position
):
string
{
const
textMateTokenInfo
=
grammar
&&
this
.
_getTokensAtPosition
(
grammar
,
position
);
const
semanticTokenInfo
=
semanticTokens
&&
this
.
_getSemanticTokenAtPosition
(
semanticTokens
,
position
);
if
(
!
textMateTokenInfo
&&
!
semanticTokenInfo
)
{
return
'
No grammar or semantic tokens available.
'
;
}
let
tokenText
;
let
tmMetadata
=
textMateTokenInfo
?.
metadata
;
let
semMetadata
=
semanticTokenInfo
?.
metadata
;
let
metadata
:
IDecodedMetadata
|
undefined
;
let
tmFallback
:
IDecodedMetadata
|
undefined
;
const
semTokenText
=
semanticTokenInfo
&&
renderTokenText
(
this
.
_model
.
getValueInRange
(
semanticTokenInfo
.
range
))
;
const
tmTokenText
=
textMateTokenInfo
&&
renderTokenText
(
this
.
_model
.
getLineContent
(
position
.
lineNumber
).
substring
(
textMateTokenInfo
.
token
.
startIndex
,
textMateTokenInfo
.
token
.
endIndex
))
;
if
(
semanticTokenInfo
)
{
tokenText
=
this
.
_model
.
getValueInRange
(
semanticTokenInfo
.
range
);
metadata
=
semanticTokenInfo
.
metadata
;
if
(
textMateTokenInfo
)
{
tmFallback
=
textMateTokenInfo
.
metadata
;
}
}
else
if
(
textMateTokenInfo
)
{
let
tokenStartIndex
=
textMateTokenInfo
.
token
.
startIndex
;
let
tokenEndIndex
=
textMateTokenInfo
.
token
.
endIndex
;
tokenText
=
this
.
_model
.
getLineContent
(
position
.
lineNumber
).
substring
(
tokenStartIndex
,
tokenEndIndex
);
metadata
=
textMateTokenInfo
.
metadata
;
}
else
{
return
'
No grammar or semantic tokens available.
'
;
}
const
tokenText
=
semTokenText
||
tmTokenText
||
''
;
let
result
=
''
;
result
+=
`<h2 class="tiw-token">
${
renderTokenText
(
tokenText
)
}
<span class="tiw-token-length">(
${
tokenText
.
length
}
${
tokenText
.
length
===
1
?
'
char
'
:
'
chars
'
}
)</span></h2>`
;
result
+=
`<h2 class="tiw-token">
${
tokenText
}
<span class="tiw-token-length">(
${
tokenText
.
length
}
${
tokenText
.
length
===
1
?
'
char
'
:
'
chars
'
}
)</span></h2>`
;
result
+=
`<hr class="tiw-metadata-separator" style="clear:both"/>`
;
result
+=
`<table class="tiw-metadata-table"><tbody>`
;
result
+=
`<tr><td class="tiw-metadata-key">language</td><td class="tiw-metadata-value">
${
escape
(
textMateTokenInfo
?.
metadata
.
languageIdentifier
.
language
||
''
)}
</td></tr>`
;
result
+=
`<tr><td class="tiw-metadata-key">standard token type</td><td class="tiw-metadata-value">
${
this
.
_tokenTypeToString
(
textMateTokenInfo
?.
metadata
.
tokenType
||
StandardTokenType
.
Other
)}
</td></tr>`
;
result
+=
`<tr><td class="tiw-metadata-key">language</td><td class="tiw-metadata-value">
${
escape
(
tmMetadata
?.
languageIdentifier
.
language
||
''
)}
</td></tr>`
;
result
+=
`<tr><td class="tiw-metadata-key">standard token type</td><td class="tiw-metadata-value">
${
this
.
_tokenTypeToString
(
tmMetadata
?.
tokenType
||
StandardTokenType
.
Other
)}
</td></tr>`
;
result
+=
`</tbody></table>`
;
result
+=
`<hr class="tiw-metadata-separator"/>`
;
result
+=
`<table class="tiw-metadata-table"><tbody>`
;
result
+=
this
.
_formatMetadata
(
metadata
,
tmFallback
);
result
+=
this
.
_formatMetadata
(
semMetadata
,
tmMetadata
);
result
+=
`</tbody></table>`
;
if
(
semanticTokenInfo
)
{
result
+=
`<hr class="tiw-metadata-separator"/>`
;
result
+=
`<table class="tiw-metadata-table"><tbody>`
;
result
+=
`<tr><td class="tiw-metadata-key">semantic token type</td><td class="tiw-metadata-value">
${
semanticTokenInfo
.
type
}
</td></tr>`
;
const
modifiers
=
semanticTokenInfo
.
modifiers
.
join
(
'
'
)
||
'
-
'
;
result
+=
`<tr><td class="tiw-metadata-key">semantic token modifiers</td><td class="tiw-metadata-value">
${
modifiers
}
</td></tr>`
;
if
(
semanticTokenInfo
.
modifiers
.
length
)
{
result
+=
`<tr><td class="tiw-metadata-key">modifiers</td><td class="tiw-metadata-value">
${
semanticTokenInfo
.
modifiers
.
join
(
'
'
)}
</td></tr>`
;
}
if
(
semanticTokenInfo
.
metadata
)
{
const
properties
:
(
keyof
TokenStyleData
)[]
=
[
'
foreground
'
,
'
bold
'
,
'
italic
'
,
'
underline
'
];
const
propertiesByDefValue
:
{
[
rule
:
string
]:
string
[]
}
=
{};
const
allDefValues
=
[];
// remember the order
// first collect to detect when the same rule is used fro multiple properties
for
(
let
property
of
properties
)
{
if
(
semanticTokenInfo
.
metadata
[
property
])
{
const
definition
=
semanticTokenInfo
.
definitions
[
property
];
const
defValue
=
this
.
_renderTokenStyleDefinition
(
definition
,
property
);
let
properties
=
propertiesByDefValue
[
defValue
];
if
(
!
properties
)
{
propertiesByDefValue
[
defValue
]
=
properties
=
[];
allDefValues
.
push
(
defValue
);
}
properties
.
push
(
property
);
}
}
for
(
let
defValue
of
allDefValues
)
{
result
+=
`<tr><td class="tiw-metadata-key">
${
propertiesByDefValue
[
defValue
].
join
(
'
,
'
)}
</td><td class="tiw-metadata-value">
${
defValue
}
</td></tr>`
;
}
}
result
+=
`</tbody></table>`
;
result
+=
`<div>
${
this
.
_renderTokenStyleDefinition
(
semanticTokenInfo
.
definitions
.
foreground
)}
</div>`
;
}
if
(
textMateTokenInfo
)
{
let
theme
=
this
.
_themeService
.
getColorTheme
();
result
+=
`<hr class="tiw-metadata-separator"/>`
;
if
(
!
semanticTokenInfo
)
{
let
matchingRule
=
findMatchingThemeRule
(
theme
,
textMateTokenInfo
.
token
.
scopes
,
false
);
if
(
matchingRule
)
{
result
+=
`<code class="tiw-theme-selector">
${
matchingRule
.
rawSelector
}
\n
${
JSON
.
stringify
(
matchingRule
.
settings
,
null
,
'
\t
'
)}
</code>`
;
}
else
{
result
+=
`<span class="tiw-theme-selector">No theme selector.</span>`
;
result
+=
`<table class="tiw-metadata-table"><tbody>`
;
if
(
tmTokenText
&&
tmTokenText
!==
tokenText
)
{
result
+=
`<tr><td class="tiw-metadata-key">textmate token</td><td class="tiw-metadata-value">
${
tmTokenText
}
(
${
tmTokenText
.
length
}
)</td></tr>`
;
}
let
scopes
=
''
;
for
(
let
i
=
textMateTokenInfo
.
token
.
scopes
.
length
-
1
;
i
>=
0
;
i
--
)
{
scopes
+=
escape
(
textMateTokenInfo
.
token
.
scopes
[
i
]);
if
(
i
>
0
)
{
scopes
+=
'
<br>
'
;
}
}
result
+=
`<tr><td class="tiw-metadata-key">textmate scopes</td><td class="tiw-metadata-value tiw-metadata-scopes">
${
scopes
}
</td></tr>`
;
result
+=
`<ul>`
;
for
(
let
i
=
textMateTokenInfo
.
token
.
scopes
.
length
-
1
;
i
>=
0
;
i
--
)
{
result
+=
`<li>
${
escape
(
textMateTokenInfo
.
token
.
scopes
[
i
])}
</li>`
;
let
matchingRule
=
findMatchingThemeRule
(
theme
,
textMateTokenInfo
.
token
.
scopes
,
false
);
const
semForeground
=
semanticTokenInfo
?.
metadata
?.
foreground
;
if
(
matchingRule
)
{
let
defValue
=
`<code class="tiw-theme-selector">
${
matchingRule
.
rawSelector
}
\n
${
JSON
.
stringify
(
matchingRule
.
settings
,
null
,
'
\t
'
)}
</code>`
;
if
(
semForeground
!==
textMateTokenInfo
.
metadata
.
foreground
)
{
if
(
semForeground
)
{
defValue
=
`<s>
${
defValue
}
</s>`
;
}
result
+=
`<tr><td class="tiw-metadata-key">foreground</td><td class="tiw-metadata-value">
${
defValue
}
</td></tr>`
;
}
}
else
if
(
!
semForeground
)
{
result
+=
`<tr><td class="tiw-metadata-key">foreground</td><td class="tiw-metadata-value">No theme selector</td></tr>`
;
}
result
+=
`</
ul
>`
;
result
+=
`</
tbody></table
>`
;
}
return
result
;
}
private
_formatMetadata
(
metadata
?:
IDecodedMetadata
,
fallback
?:
IDecodedMetadata
)
{
private
_formatMetadata
(
semantic
?:
IDecodedMetadata
,
tm
?:
IDecodedMetadata
)
{
let
result
=
''
;
function
render
(
label
:
string
,
value
:
string
|
undefined
,
property
:
keyof
IDecodedMetadata
)
{
const
info
=
metadata
?.[
property
]
!==
value
?
` (tm)`
:
''
;
return
`<tr><td class="tiw-metadata-key">
${
label
}
</td><td class="tiw-metadata-value">
${
value
+
info
}
</td></tr>`
;
}
function
render
(
property
:
'
foreground
'
|
'
background
'
)
{
let
value
=
semantic
?.[
property
]
||
tm
?.[
property
];
if
(
value
!==
undefined
)
{
const
semanticStyle
=
semantic
?.[
property
]
?
'
tiw-metadata-semantic
'
:
''
;
result
+=
`<tr><td class="tiw-metadata-key">
${
property
}
</td><td class="tiw-metadata-value
${
semanticStyle
}
">
${
value
}
</td></tr>`
;
const
fontStyle
=
metadata
?.
fontStyle
||
fallback
?.
fontStyle
;
result
+=
render
(
'
font style
'
,
fontStyle
,
'
fontStyle
'
);
const
foreground
=
metadata
?.
foreground
||
fallback
?.
foreground
;
result
+=
render
(
'
foreground
'
,
foreground
,
'
foreground
'
);
const
background
=
metadata
?.
background
||
fallback
?.
background
;
result
+=
render
(
'
background
'
,
background
,
'
background
'
);
}
return
value
;
}
const
foreground
=
render
(
'
foreground
'
);
const
background
=
render
(
'
background
'
);
if
(
foreground
&&
background
)
{
const
backgroundColor
=
Color
.
fromHex
(
background
),
foregroundColor
=
Color
.
fromHex
(
foreground
);
if
(
backgroundColor
.
isOpaque
())
{
result
+=
`<tr><td class="tiw-metadata-key">contrast ratio</td><td class="tiw-metadata-value">
${
backgroundColor
.
getContrastRatio
(
foregroundColor
.
makeOpaque
(
backgroundColor
)).
toFixed
(
2
)}
</td></tr>`
;
}
else
{
result
+=
'
<tr><td class="tiw-metadata-key">Contrast ratio cannot be precise for background colors that use transparency</td><td class="tiw-metadata-value"></td></tr>
'
;
}
}
let
fontStyleLabels
:
string
[]
=
[];
function
addStyle
(
key
:
'
bold
'
|
'
italic
'
|
'
underline
'
)
{
if
(
semantic
&&
semantic
[
key
])
{
fontStyleLabels
.
push
(
`<span class='tiw-metadata-semantic'>
${
key
}
</span>`
);
}
else
if
(
tm
&&
tm
[
key
])
{
fontStyleLabels
.
push
(
key
);
}
}
addStyle
(
'
bold
'
);
addStyle
(
'
italic
'
);
addStyle
(
'
underline
'
);
if
(
fontStyleLabels
.
length
)
{
result
+=
`<tr><td class="tiw-metadata-key">font style</td><td class="tiw-metadata-value">
${
fontStyleLabels
.
join
(
'
'
)}
</td></tr>`
;
}
return
result
;
}
...
...
@@ -366,7 +408,9 @@ class InspectEditorTokensWidget extends Disposable implements IContentWidget {
return
{
languageIdentifier
:
this
.
_modeService
.
getLanguageIdentifier
(
languageId
)
!
,
tokenType
:
tokenType
,
fontStyle
:
this
.
_fontStyleToString
(
fontStyle
),
bold
:
(
fontStyle
&
FontStyle
.
Bold
)
?
true
:
undefined
,
italic
:
(
fontStyle
&
FontStyle
.
Italic
)
?
true
:
undefined
,
underline
:
(
fontStyle
&
FontStyle
.
Underline
)
?
true
:
undefined
,
foreground
:
colorMap
[
foreground
],
background
:
colorMap
[
background
]
};
...
...
@@ -382,23 +426,6 @@ class InspectEditorTokensWidget extends Disposable implements IContentWidget {
return
'
??
'
;
}
private
_fontStyleToString
(
fontStyle
:
FontStyle
):
string
{
let
r
=
''
;
if
(
fontStyle
&
FontStyle
.
Italic
)
{
r
+=
'
italic
'
;
}
if
(
fontStyle
&
FontStyle
.
Bold
)
{
r
+=
'
bold
'
;
}
if
(
fontStyle
&
FontStyle
.
Underline
)
{
r
+=
'
underline
'
;
}
if
(
r
.
length
===
0
)
{
r
=
'
---
'
;
}
return
r
;
}
private
_getTokensAtPosition
(
grammar
:
IGrammar
,
position
:
Position
):
ITextMateTokenInfo
{
const
lineNumber
=
position
.
lineNumber
;
let
stateBeforeLine
=
this
.
_getStateBeforeLine
(
grammar
,
lineNumber
);
...
...
@@ -478,26 +505,18 @@ class InspectEditorTokensWidget extends Disposable implements IContentWidget {
const
theme
=
this
.
_themeService
.
getTheme
()
as
ColorThemeData
;
const
tokenStyle
=
theme
.
getTokenStyleMetadata
(
type
,
modifiers
,
true
,
definitions
);
let
fontStyle
=
FontStyle
.
None
;
let
foreground
:
string
|
undefined
=
undefined
;
let
metadata
:
IDecodedMetadata
|
undefined
=
undefined
;
if
(
tokenStyle
)
{
fontStyle
=
(
(
tokenStyle
.
italic
?
FontStyle
.
Italic
:
0
)
|
(
tokenStyle
.
bold
?
FontStyle
.
Bold
:
0
)
|
(
tokenStyle
.
underline
?
FontStyle
.
Underline
:
0
)
);
if
(
tokenStyle
.
foreground
)
{
foreground
=
colorMap
[
tokenStyle
.
foreground
];
}
metadata
=
{
languageIdentifier
:
this
.
_modeService
.
getLanguageIdentifier
(
LanguageId
.
Null
)
!
,
tokenType
:
StandardTokenType
.
Other
,
bold
:
tokenStyle
?.
bold
,
italic
:
tokenStyle
?.
italic
,
underline
:
tokenStyle
?.
underline
,
foreground
:
colorMap
[
tokenStyle
?.
foreground
||
ColorId
.
None
]
}
;
}
const
metadata
:
IDecodedMetadata
=
{
languageIdentifier
:
this
.
_modeService
.
getLanguageIdentifier
(
LanguageId
.
Null
)
!
,
tokenType
:
StandardTokenType
.
Other
,
fontStyle
:
this
.
_fontStyleToString
(
fontStyle
),
foreground
:
foreground
,
};
return
{
type
,
modifiers
,
range
,
metadata
,
definitions
};
}
lastLine
=
line
;
...
...
@@ -506,7 +525,7 @@ class InspectEditorTokensWidget extends Disposable implements IContentWidget {
return
null
;
}
private
_renderTokenStyleDefinition
(
definition
:
TokenStyleDefinition
|
undefined
):
string
{
private
_renderTokenStyleDefinition
(
definition
:
TokenStyleDefinition
|
undefined
,
property
:
keyof
TokenStyleData
):
string
{
if
(
definition
===
undefined
)
{
return
''
;
}
...
...
@@ -514,30 +533,19 @@ class InspectEditorTokensWidget extends Disposable implements IContentWidget {
const
isTokenStylingRule
=
(
d
:
any
):
d
is
TokenStylingRule
=>
!!
d
.
value
;
if
(
Array
.
isArray
(
definition
))
{
let
result
=
''
;
let
matchingRule
=
undefined
;
result
+=
`<ul>`
;
for
(
const
d
of
definition
)
{
result
+=
`<li>
${
escape
(
d
.
join
(
'
'
))}
</li>`
;
matchingRule
=
findMatchingThemeRule
(
theme
,
d
,
false
);
const
matchingRule
=
findMatchingThemeRule
(
theme
,
d
,
false
);
if
(
matchingRule
)
{
break
;
return
`
${
escape
(
d
.
join
(
'
'
))}
<br><code class="tiw-theme-selector">
${
matchingRule
.
rawSelector
}
\n
${
JSON
.
stringify
(
matchingRule
.
settings
,
null
,
'
\t
'
)}
</code>`
;
}
}
result
+=
`</ul>`
;
if
(
matchingRule
)
{
result
+=
`<code class="tiw-theme-selector">
${
matchingRule
.
rawSelector
}
\n
${
JSON
.
stringify
(
matchingRule
.
settings
,
null
,
'
\t
'
)}
</code>`
;
}
return
result
;
return
''
;
}
else
if
(
isTokenStylingRule
(
definition
))
{
const
scope
=
theme
.
getTokenStylingRuleScope
(
definition
);
if
(
scope
===
'
setting
'
)
{
return
`User settings
:
${
definition
.
selector
}
`
;
return
`User settings
`
;
// todo: print selector and style once selector is a string
}
else
if
(
scope
===
'
theme
'
)
{
return
`Color theme
:
${
definition
.
selector
}
`
;
return
`Color theme
`
;
// todo: print selector and style once selector is a string
}
return
''
;
}
else
if
(
typeof
definition
===
'
string
'
)
{
...
...
@@ -545,11 +553,11 @@ class InspectEditorTokensWidget extends Disposable implements IContentWidget {
const
definitions
:
TokenStyleDefinitions
=
{};
const
m
=
theme
.
getTokenStyleMetadata
(
type
,
modifiers
,
true
,
definitions
);
if
(
m
&&
definitions
.
foreground
)
{
return
this
.
_renderTokenStyleDefinition
(
definitions
.
foreground
);
return
this
.
_renderTokenStyleDefinition
(
definitions
[
property
],
property
);
}
return
''
;
}
else
{
return
`Token style: Foreground:
${
definition
.
foreground
}
, bold:
${
definition
.
bold
}
, italic:
${
definition
.
italic
}
, underline:
${
definition
.
underline
}
,`
;
return
String
(
definition
[
property
])
;
}
}
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录