Skip to content

Commit

Permalink
feat: add textStyle and highlight marks support
Browse files Browse the repository at this point in the history
Signed-off-by: Edvinas Jurele <[email protected]>
  • Loading branch information
edvinasjurele committed Aug 30, 2023
1 parent a716a99 commit 6b68afa
Show file tree
Hide file tree
Showing 5 changed files with 140 additions and 6 deletions.
4 changes: 2 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -178,8 +178,8 @@ schema={{
subscript: () => ({ ... }),
code: () => ({ ... }),
anchor: ({ attrs }) => ({ ... }),
textStyle: ({ attrs }) => ({ ... }), // NOT SUPPORTED YET!
highlight: ({ attrs }) => ({ ... }), // NOT SUPPORTED YET!
textStyle: ({ attrs }) => ({ ... }),
highlight: ({ attrs }) => ({ ... }),
};
}}
```
Expand Down
32 changes: 32 additions & 0 deletions demo/src/pages/index.astro
Original file line number Diff line number Diff line change
Expand Up @@ -207,6 +207,38 @@ const richTextFromStoryblok: RichTextType = {
},
],
},
{
text: ", ",
type: "text",
},
{
text: "textStyle",
type: "text",
marks: [
{
type: "textStyle",
attrs: {
color: "#ddA03A",
},
},
],
},
{
text: ", ",
type: "text",
},
{
text: "highlight",
type: "text",
marks: [
{
type: "highlight",
attrs: {
color: "#9CFFA4",
},
},
],
},
{
text: ".",
type: "text",
Expand Down
12 changes: 8 additions & 4 deletions lib/src/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -37,9 +37,8 @@ export type Schema = {
subscript?: ResponseSchemaFn;
code?: ResponseSchemaFn;
anchor?: ResponseSchemaAttrsFn;
// TODO: add support. The following are known, though not supported yet
// textStyle?: ResponseSchemaAttrsFn;
// highlight?: ResponseSchemaAttrsFn;
textStyle?: ResponseSchemaAttrsFn;
highlight?: ResponseSchemaAttrsFn;
};
};

Expand Down Expand Up @@ -71,6 +70,12 @@ export type Mark =
class: string;
};
}
| {
type: "textStyle" | "highlight";
attrs: {
color: string;
};
}
| {
type: "link";
attrs: {
Expand Down Expand Up @@ -191,7 +196,6 @@ type RichTextContent =

export type SchemaNode = RichTextContent | Text | ListItem | Image | Emoji;

// TODO: expand with full marks support
export type RichTextType = {
type: "doc";
content: Array<RichTextContent>;
Expand Down
70 changes: 70 additions & 0 deletions lib/src/utils/resolveRichTextToNodes.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -826,6 +826,20 @@ describe("resolveMark", () => {
id,
},
}),
textStyle: ({ attrs: { color } }) => ({
component: "span",
props: {
class: "text-style",
style: { color },
},
}),
highlight: ({ attrs: { color } }) => ({
component: "span",
props: {
class: "highlight",
style: { backgroundColor: color },
},
}),
},
};

Expand Down Expand Up @@ -1087,6 +1101,62 @@ describe("resolveMark", () => {
},
});
});

it("textStyle", () => {
const mark: Mark = {
type: "textStyle",
attrs: {
color: "#9CFFA4",
},
};

// default
expect(resolveMark(content, mark)).toStrictEqual({
component: "span",
content,
props: {
style: { color: "#9CFFA4" },
},
});

// with schema override
expect(resolveMark(content, mark, sharedSchema)).toStrictEqual({
component: "span",
content,
props: {
class: "text-style",
style: { color: "#9CFFA4" },
},
});
});

it("highlight", () => {
const mark: Mark = {
type: "highlight",
attrs: {
color: "#9CFFA4",
},
};

// default
expect(resolveMark(content, mark)).toStrictEqual({
component: "span",
content,
props: {
style: { backgroundColor: "#9CFFA4" },
},
});

// with schema override
expect(resolveMark(content, mark, sharedSchema)).toStrictEqual({
component: "span",
content,
props: {
class: "highlight",
style: { backgroundColor: "#9CFFA4" },
},
});
});
});

describe("resolveRichTextToNodes", () => {
Expand Down
28 changes: 28 additions & 0 deletions lib/src/utils/resolveRichTextToNodes.ts
Original file line number Diff line number Diff line change
Expand Up @@ -129,6 +129,34 @@ export const resolveMark = (
...resolverFn?.({ attrs }),
};
}

if (mark.type === "textStyle") {
const resolverFn = schema?.marks?.[mark.type];
const { attrs } = mark;

return {
component: "span",
content,
props: {
style: { color: attrs.color },
},
...resolverFn?.({ attrs }),
};
}

if (mark.type === "highlight") {
const resolverFn = schema?.marks?.[mark.type];
const { attrs } = mark;

return {
component: "span",
content,
props: {
style: { backgroundColor: attrs.color },
},
...resolverFn?.({ attrs }),
};
}
};

// all available nodes: https://github.com/storyblok/storyblok-js-client/blob/main/src/schema.ts#L21
Expand Down

0 comments on commit 6b68afa

Please sign in to comment.