fumadocs-core 12.0.6 → 12.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -15,6 +15,9 @@ interface IconOptions {
15
15
  shortcuts?: Record<string, string>;
16
16
  extend?: Record<string, CodeBlockIcon>;
17
17
  }
18
+ /**
19
+ * Inject icons to `icon` property (as HTML)
20
+ */
18
21
  declare function transformerIcon(options?: IconOptions): ShikiTransformer;
19
22
 
20
23
  declare const rehypeCodeDefaultOptions: RehypeCodeOptions;
@@ -34,6 +37,12 @@ type RehypeCodeOptions = RehypeShikiOptions & {
34
37
  * Add icon to code blocks
35
38
  */
36
39
  icon?: IconOptions | false;
40
+ /**
41
+ * Wrap code blocks in `<Tab>` component when "tab" meta string presents
42
+ *
43
+ * @defaultValue true
44
+ */
45
+ tab?: false;
37
46
  };
38
47
  /**
39
48
  * Handle codeblocks
@@ -22,7 +22,6 @@ import {
22
22
  } from "@shikijs/transformers";
23
23
 
24
24
  // src/mdx-plugins/transformer-icon.ts
25
- import { toEstree } from "hast-util-to-estree";
26
25
  var defaultShortcuts = {
27
26
  js: "javascript",
28
27
  jsx: "react",
@@ -143,118 +142,21 @@ var defaultIcons = {
143
142
  function transformerIcon(options = {}) {
144
143
  const shortcuts = __spreadValues(__spreadValues({}, defaultShortcuts), options.shortcuts);
145
144
  const icons = __spreadValues(__spreadValues({}, defaultIcons), options.extend);
145
+ const defaultIcon = "default" in icons ? icons.default : void 0;
146
146
  return {
147
147
  name: "rehype-code:icon",
148
- root(root) {
148
+ pre(pre) {
149
149
  const lang = this.options.lang;
150
150
  if (!lang) return;
151
- const pre = root.children[0];
152
- if (pre.type !== "element" || pre.tagName !== "pre") return;
153
151
  const iconName = lang in shortcuts ? shortcuts[lang] : lang;
154
- const icon = iconName in icons ? icons[iconName] : icons.default;
155
- const tree = toEstree(pre, {
156
- elementAttributeNameCase: "react"
157
- });
158
- if (tree.body[0].type === "ExpressionStatement") {
159
- const expression = tree.body[0].expression;
160
- if (expression.type === "JSXElement") {
161
- expression.openingElement.attributes.push({
162
- type: "JSXAttribute",
163
- name: {
164
- type: "JSXIdentifier",
165
- name: "icon"
166
- },
167
- value: createSVGElement(icon)
168
- });
169
- }
152
+ const icon = iconName in icons ? icons[iconName] : defaultIcon;
153
+ if (icon) {
154
+ pre.properties.icon = `<svg viewBox="${icon.viewBox}"><path d="${icon.d}" fill="${icon.fill}" /></svg>`;
170
155
  }
171
- return {
172
- type: "root",
173
- children: [
174
- {
175
- type: "mdxFlowExpression",
176
- value: "",
177
- data: {
178
- estree: tree
179
- }
180
- }
181
- ]
182
- };
156
+ return pre;
183
157
  }
184
158
  };
185
159
  }
186
- function createSVGElement(icon) {
187
- return {
188
- type: "JSXElement",
189
- openingElement: {
190
- type: "JSXOpeningElement",
191
- attributes: [
192
- {
193
- type: "JSXAttribute",
194
- name: {
195
- type: "JSXIdentifier",
196
- name: "viewBox"
197
- },
198
- value: {
199
- type: "Literal",
200
- value: icon.viewBox
201
- }
202
- }
203
- ],
204
- name: {
205
- type: "JSXIdentifier",
206
- name: "svg"
207
- },
208
- selfClosing: false
209
- },
210
- closingElement: {
211
- type: "JSXClosingElement",
212
- name: {
213
- type: "JSXIdentifier",
214
- name: "svg"
215
- }
216
- },
217
- children: [
218
- {
219
- type: "JSXElement",
220
- openingElement: {
221
- type: "JSXOpeningElement",
222
- attributes: [
223
- {
224
- type: "JSXAttribute",
225
- name: {
226
- type: "JSXIdentifier",
227
- name: "fill"
228
- },
229
- value: {
230
- type: "Literal",
231
- value: icon.fill
232
- }
233
- },
234
- {
235
- type: "JSXAttribute",
236
- name: {
237
- type: "JSXIdentifier",
238
- name: "d"
239
- },
240
- value: {
241
- type: "Literal",
242
- value: icon.d
243
- }
244
- }
245
- ],
246
- name: {
247
- type: "JSXIdentifier",
248
- name: "path"
249
- },
250
- selfClosing: true
251
- },
252
- closingElement: null,
253
- children: []
254
- }
255
- ]
256
- };
257
- }
258
160
 
259
161
  // src/mdx-plugins/rehype-code.ts
260
162
  var metaValues = [
@@ -265,6 +167,10 @@ var metaValues = [
265
167
  {
266
168
  name: "custom",
267
169
  regex: new RegExp('custom="(?<value>[^"]+)"')
170
+ },
171
+ {
172
+ name: "tab",
173
+ regex: new RegExp('tab="(?<value>[^"]+)"')
268
174
  }
269
175
  ];
270
176
  var rehypeCodeDefaultOptions = {
@@ -282,8 +188,8 @@ var rehypeCodeDefaultOptions = {
282
188
  const map = {};
283
189
  for (const value of metaValues) {
284
190
  const result = value.regex.exec(meta);
285
- if (result == null ? void 0 : result.groups) {
286
- map[value.name] = result.groups.value;
191
+ if (result) {
192
+ map[value.name] = result[1];
287
193
  }
288
194
  }
289
195
  return map;
@@ -326,11 +232,39 @@ function rehypeCode(options = {}) {
326
232
  transformerIcon(codeOptions.icon)
327
233
  ];
328
234
  }
235
+ if (codeOptions.tab !== false) {
236
+ codeOptions.transformers = [...codeOptions.transformers, transformerTab()];
237
+ }
329
238
  if (codeOptions.defaultLang) {
330
239
  codeOptions.defaultLanguage = codeOptions.defaultLang;
331
240
  }
332
241
  return rehypeShiki.call(this, codeOptions);
333
242
  }
243
+ function transformerTab() {
244
+ return {
245
+ name: "rehype-code:tab",
246
+ root(root) {
247
+ const meta = this.options.meta;
248
+ if (typeof (meta == null ? void 0 : meta.tab) !== "string") return root;
249
+ return {
250
+ type: "root",
251
+ children: [
252
+ {
253
+ type: "mdxJsxFlowElement",
254
+ name: "Tab",
255
+ data: {
256
+ _codeblock: true
257
+ },
258
+ attributes: [
259
+ { type: "mdxJsxAttribute", name: "value", value: meta.tab }
260
+ ],
261
+ children: root.children
262
+ }
263
+ ]
264
+ };
265
+ }
266
+ };
267
+ }
334
268
 
335
269
  // src/mdx-plugins/remark-image.ts
336
270
  import { existsSync } from "fs";
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "fumadocs-core",
3
- "version": "12.0.6",
3
+ "version": "12.1.0",
4
4
  "description": "The library for building a documentation website in Next.js",
5
5
  "keywords": [
6
6
  "NextJs",
@@ -120,11 +120,10 @@
120
120
  ],
121
121
  "dependencies": {
122
122
  "@formatjs/intl-localematcher": "^0.5.4",
123
- "@shikijs/rehype": "^1.6.4",
124
- "@shikijs/transformers": "^1.6.4",
123
+ "@shikijs/rehype": "^1.6.5",
124
+ "@shikijs/transformers": "^1.6.5",
125
125
  "flexsearch": "0.7.21",
126
126
  "github-slugger": "^2.0.0",
127
- "hast-util-to-estree": "^3.1.0",
128
127
  "negotiator": "^0.6.3",
129
128
  "npm-to-yarn": "^2.2.1",
130
129
  "react-remove-scroll": "^2.5.10",
@@ -132,7 +131,7 @@
132
131
  "remark-gfm": "^4.0.0",
133
132
  "remark-mdx": "^3.0.1",
134
133
  "scroll-into-view-if-needed": "^3.1.0",
135
- "shiki": "^1.6.4",
134
+ "shiki": "^1.6.5",
136
135
  "swr": "^2.2.5",
137
136
  "unist-util-visit": "^5.0.0"
138
137
  },