Skip to content

Commit b3350c3

Browse files
authored
Merge pull request #199 from code-hike/multiline-mark-annotation
Multiline mark annotation
2 parents 6389d8e + 9e0db7c commit b3350c3

File tree

8 files changed

+138
-70
lines changed

8 files changed

+138
-70
lines changed

packages/mdx/dev/content/comment-annotations.mdx

+7-7
Original file line numberDiff line numberDiff line change
@@ -20,22 +20,22 @@ function adipiscing(...elit) {
2020
console.log("hey")
2121
```
2222

23-
Same with other annotations like `bg` and `box`.
23+
Same with other annotations like `mark` and `box`.
2424

2525
```js
26-
// bg(1:2)
26+
// mark(1:2)
2727
function foo() {
28-
// box[6:9]
28+
// mark[6:9] mark-box
2929
console.log("hover me")
3030
return 8
3131
}
3232
```
3333

34-
You can pass a string parameter to comment annotations. For `bg` and `box`, it will be used as a color.
34+
You can pass a string parameter to comment annotations. For `mark` and `box`, it will be used as a color.
3535

3636
```js index.js
3737
function lorem(ipsum, dolor = 1) {
38-
// bg(1:3) linear-gradient(90deg, #020024 0%, #090979 35%, #00d4ff 100%)
38+
// mark(1:3) mark-red-background
3939
const sit = ipsum == null && 0
4040
dolor = sit - amet(dolor)
4141
return sit ? consectetur(ipsum) : []
@@ -47,7 +47,7 @@ function lorem(ipsum, dolor = 1) {
4747
// å
4848
function adipiscing(...elit) {
4949
console.log(elit)
50-
// box[19:36] aqua
50+
// mark[19:36]
5151
return elit.map(ipsum => ipsum.sit)
5252
}
5353
```
@@ -85,7 +85,7 @@ def lorem(ipsum, dolor = 1):
8585
```bash
8686
function lorem(ipsum, dolor = 1) {
8787
# focus(1:3)
88-
# box[3:7]
88+
# mark[3:7]
8989
local sit=0
9090
# label something something
9191
dolor=$((sit - amet(dolor)))

packages/mdx/pages/styles.css

+16
Original file line numberDiff line numberDiff line change
@@ -36,3 +36,19 @@ div#__next > div {
3636
.annotation-class span {
3737
text-decoration: line-through;
3838
}
39+
40+
.mark-red-background {
41+
background: #550000 !important;
42+
}
43+
44+
.mark-red-background .ch-code-multiline-mark-border {
45+
background: #bb0000 !important;
46+
}
47+
48+
.mark-box {
49+
background: #000 !important;
50+
}
51+
52+
.mark-box * {
53+
color: #0f0 !important;
54+
}

packages/mdx/pages/themes.tsx

+2-1
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ const mdx = `
99
1010
<CH.Code>
1111
12-
~~~json package.json
12+
~~~json package.json mark=2[12:23]
1313
{
1414
"name": "package.json"
1515
}
@@ -31,6 +31,7 @@ function PostPage() {
3131
3232
~~~js pages/alpha.ts
3333
function AlphaPage() {
34+
// mark
3435
return 1
3536
}
3637
~~~

packages/mdx/src/index.scss

+13
Original file line numberDiff line numberDiff line change
@@ -53,3 +53,16 @@
5353
.ch-section-link[data-active="true"] * {
5454
text-decoration-thickness: 1.5px;
5555
}
56+
57+
.ch-code-inline-mark {
58+
border-radius: 0.25rem;
59+
padding: 0.2rem 0.15rem 0.1rem;
60+
margin: 0 -0.15rem;
61+
}
62+
63+
.ch-code-multiline-mark-border {
64+
width: 3px;
65+
height: 100%;
66+
position: absolute;
67+
left: 0;
68+
}

packages/mdx/src/mdx-client/annotations.tsx

+52-62
Original file line numberDiff line numberDiff line change
@@ -11,14 +11,56 @@ export const annotationsMap: Record<
1111
CodeAnnotation["Component"]
1212
> = {
1313
box: Box,
14-
bg: Background,
14+
bg: MultilineMark,
1515
label: Label,
1616
link: CodeLink,
1717
mark: Mark,
1818
withClass: WithClass,
1919
}
2020

21-
function Mark({
21+
function Mark(props: any) {
22+
if (props.isInline) {
23+
return <InlineMark {...props} />
24+
} else {
25+
return <MultilineMark {...props} />
26+
}
27+
}
28+
function MultilineMark({
29+
children,
30+
data,
31+
style,
32+
theme,
33+
}: {
34+
data: string
35+
children: React.ReactNode
36+
style?: React.CSSProperties
37+
theme?: any
38+
}) {
39+
const className = `ch-code-multiline-mark ` + (data ?? "")
40+
const bg = getColor(
41+
theme,
42+
ColorName.RangeHighlightBackground
43+
)
44+
const border = getColor(
45+
theme,
46+
ColorName.EditorInfoForeground
47+
)
48+
49+
return (
50+
<div
51+
style={{ ...style, background: bg }}
52+
className={className}
53+
>
54+
<span
55+
className="ch-code-multiline-mark-border"
56+
style={{ background: border }}
57+
/>
58+
{children}
59+
</div>
60+
)
61+
}
62+
63+
function InlineMark({
2264
children,
2365
data,
2466
theme,
@@ -28,24 +70,15 @@ function Mark({
2870
theme: any
2971
}) {
3072
const bg =
31-
data && typeof data === "string"
32-
? data
33-
: tryGuessColor(children) ||
34-
transparent(
35-
getColor(theme, ColorName.CodeForeground),
36-
0.2
37-
)
73+
tryGuessColor(children) ||
74+
transparent(
75+
getColor(theme, ColorName.CodeForeground),
76+
0.2
77+
)
3878

79+
const className = "ch-code-inline-mark " + (data ?? "")
3980
return (
40-
<span
41-
className="ch-code-mark-annotation"
42-
style={{
43-
background: bg,
44-
borderRadius: "0.25rem",
45-
padding: "0.2rem 0.15rem 0.1rem",
46-
margin: "0 -0.15rem",
47-
}}
48-
>
81+
<span className={className} style={{ background: bg }}>
4982
{children}
5083
</span>
5184
)
@@ -64,7 +97,7 @@ function tryGuessColor(
6497
grandChild?.props?.children || []
6598
)[0] as any
6699

67-
const { color } = grandGrandChild?.props?.style
100+
const { color } = grandGrandChild?.props?.style || {}
68101

69102
if (color) {
70103
return transparent(color as string, 0.2)
@@ -117,49 +150,6 @@ function WithClass({
117150
)
118151
}
119152

120-
function Background({
121-
children,
122-
data,
123-
style,
124-
theme,
125-
}: {
126-
data: string
127-
children: React.ReactNode
128-
style?: React.CSSProperties
129-
theme?: any
130-
}) {
131-
const bg =
132-
data ||
133-
(((theme as any).colors[
134-
"editor.lineHighlightBackground"
135-
] ||
136-
(theme as any).colors[
137-
"editor.selectionHighlightBackground"
138-
]) as string)
139-
return (
140-
<div
141-
style={{
142-
...style,
143-
background: bg,
144-
// cursor: "pointer",
145-
}}
146-
className="ch-code-bg-annotation"
147-
>
148-
<span
149-
className="ch-code-bg-annotation-border"
150-
style={{
151-
background: "#00a2d3",
152-
width: "3px",
153-
height: "100%",
154-
position: "absolute",
155-
left: 0,
156-
}}
157-
/>
158-
{children}
159-
</div>
160-
)
161-
}
162-
163153
function Label({
164154
children,
165155
data,

packages/mdx/src/smooth-code/partial-step-parser.ts

+2
Original file line numberDiff line numberDiff line change
@@ -142,6 +142,7 @@ export type MultiLineAnnotation = {
142142
children: React.ReactNode
143143
data: any
144144
theme: EditorTheme
145+
isInline: boolean
145146
}) => React.ReactElement
146147
}
147148

@@ -155,6 +156,7 @@ export type InlineAnnotation = {
155156
children: React.ReactNode
156157
data: any
157158
theme: EditorTheme
159+
isInline: boolean
158160
}) => React.ReactElement
159161
}
160162

packages/mdx/src/smooth-code/smooth-lines.tsx

+2
Original file line numberDiff line numberDiff line change
@@ -108,6 +108,7 @@ function Lines({
108108
key={i}
109109
data={group.annotation.data}
110110
theme={group.annotation.theme}
111+
isInline={false}
111112
>
112113
<LineGroup
113114
lines={group.lines}
@@ -258,6 +259,7 @@ function AnnotatedTokens({
258259
children={children}
259260
data={annotated?.annotation?.data}
260261
theme={annotated?.annotation?.theme!}
262+
isInline={true}
261263
/>
262264
) : (
263265
<>{children}</>

packages/mdx/src/utils/theme.ts

+44
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@ export enum ColorName {
3232
CodeBackground,
3333
EditorForeground,
3434
EditorBackground,
35+
FocusBorder,
3536
ActiveTabBackground,
3637
ActiveTabForeground,
3738
InactiveTabBackground,
@@ -53,6 +54,12 @@ export enum ColorName {
5354
SideBarBackground,
5455
SideBarForeground,
5556
SideBarBorder,
57+
// Background color for the highlight of line at the cursor position
58+
LineHighlightBackground,
59+
// Background color of highlighted ranges, like by quick open and find features
60+
RangeHighlightBackground,
61+
// Foreground color of info squigglies in the editor
62+
EditorInfoForeground,
5663
}
5764

5865
type Color = string | undefined
@@ -97,6 +104,15 @@ export function getColor(
97104
hc: "#fffffe",
98105
})
99106
)
107+
case ColorName.FocusBorder:
108+
return (
109+
colors["focusBorder"] ||
110+
getDefault(theme, {
111+
light: "#0090F1",
112+
dark: "#007FD4",
113+
hc: contrastBorder,
114+
})
115+
)
100116
case ColorName.ActiveTabBackground:
101117
return (
102118
colors["tab.activeBackground"] ||
@@ -267,6 +283,34 @@ export function getColor(
267283
)
268284
case ColorName.ListHoverForeground:
269285
return colors["list.hoverForeground"] || undefined
286+
case ColorName.LineHighlightBackground:
287+
return (
288+
colors["editor.lineHighlightBackground"] ||
289+
getDefault(theme, {
290+
dark: undefined,
291+
light: undefined,
292+
hc: undefined,
293+
})
294+
)
295+
case ColorName.RangeHighlightBackground:
296+
return (
297+
colors["editor.rangeHighlightBackground"] ||
298+
getDefault(theme, {
299+
dark: "#ffffff0b",
300+
light: "#fdff0033",
301+
hc: undefined,
302+
})
303+
)
304+
305+
case ColorName.EditorInfoForeground:
306+
return (
307+
colors["editor.infoForeground"] ||
308+
getDefault(theme, {
309+
dark: "#3794FF",
310+
light: "#1a85ff",
311+
hc: "#3794FF",
312+
})
313+
)
270314

271315
default:
272316
return "#f00"

0 commit comments

Comments
 (0)