Skip to content

Commit f3da4a4

Browse files
committed
feat: add heading example
1 parent 7e851c8 commit f3da4a4

27 files changed

+6552
-1348
lines changed

.verdaccio/config.yml

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
# path to a directory with all packages
2+
storage: ../tmp/local-registry/storage
3+
4+
# a list of other known repositories we can talk to
5+
uplinks:
6+
npmjs:
7+
url: https://registry.npmjs.org/
8+
maxage: 60m
9+
10+
packages:
11+
'**':
12+
# give all users (including non-authenticated users) full access
13+
# because it is a local registry
14+
access: $all
15+
publish: $all
16+
unpublish: $all
17+
18+
# if package is not available locally, proxy requests to npm registry
19+
proxy: npmjs
20+
21+
# log settings
22+
logs:
23+
type: stdout
24+
format: pretty
25+
level: warn
26+
27+
publish:
28+
allow_offline: true # set offline to true to allow publish offline

docs/src/app/app.routes.ts

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ import { AlertBlockPage } from '../pages/examples/custom/alert-block/alert-block
1111
import { ApiContentBlockPage } from '../pages/examples/custom/api-content-block/api-content-block.page';
1212
import { MentionsMenuPage } from '../pages/examples/custom/mentions-menu/mentions-menu.page';
1313
import { ExamplesPage } from '../pages/examples/examples.page';
14+
import { HeadingBlockPage } from '../pages/examples/extensions/heading/heading-block.page';
1415
import { ConvertToHtmlPage } from '../pages/examples/interoperability/convert-to-html/convert-to-html.page';
1516
import { AddingSideMenuDragHandleItemsPage } from '../pages/examples/ui-components/adding-side-menu-drag-handle-items/adding-side-menu-drag-handle-items.page';
1617
import { FormattingSideMenuButtonsPage } from '../pages/examples/ui-components/formatting-side-menu-buttons/formatting-side-menu-buttons.page';
@@ -57,6 +58,10 @@ export const appRoutes: Route[] = [
5758
path: 'custom/mentions-menu',
5859
component: MentionsMenuPage,
5960
},
61+
{
62+
path: 'extensions/heading-block',
63+
component: HeadingBlockPage,
64+
},
6065
{
6166
path: 'interoperability/convert-to-html',
6267
component: ConvertToHtmlPage,

docs/src/pages/examples/examples.page.ts

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -104,6 +104,15 @@ import { HlmButtonDirective } from '@dytab/block-note-angular';
104104
routerLink="custom/api-content-block"
105105
>Api Content Block</a
106106
>
107+
Extensions
108+
<a
109+
hlmBtn
110+
variant="ghost"
111+
class="justify-start"
112+
routerLinkActive="active-link"
113+
routerLink="extensions/heading-block"
114+
>Heading Block</a
115+
>
107116
<a
108117
hlmBtn
109118
variant="ghost"
Lines changed: 131 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,131 @@
1+
import { CommonModule } from '@angular/common';
2+
import { Component } from '@angular/core';
3+
import {
4+
BlockNoteSchema,
5+
defaultBlockSpecs,
6+
defaultInlineContentSpecs,
7+
defaultStyleSpecs,
8+
PartialBlock,
9+
} from '@blocknote/core';
10+
import {
11+
BlockNoteEditorOptionsType,
12+
BnaEditorComponent,
13+
HlmButtonDirective,
14+
} from '@dytab/block-note-angular';
15+
import { Heading } from '@dytab/block-note-extensions';
16+
17+
const schema = BlockNoteSchema.create({
18+
blockSpecs: {
19+
...defaultBlockSpecs,
20+
heading: Heading,
21+
},
22+
inlineContentSpecs: { ...defaultInlineContentSpecs },
23+
styleSpecs: { ...defaultStyleSpecs },
24+
});
25+
@Component({
26+
selector: 'bna-heading-block-example',
27+
standalone: true,
28+
imports: [CommonModule, BnaEditorComponent, HlmButtonDirective],
29+
template: `<bna-editor
30+
[initialContent]="initialContent"
31+
[options]="options"
32+
/>`,
33+
})
34+
export class HeadingBlockExample {
35+
initialContent: PartialBlock<typeof schema.blockSchema>[] = [
36+
{ type: 'heading', props: { level: 1 }, content: 'Level 1' },
37+
{ type: 'heading', props: { level: 2 }, content: 'Level 2' },
38+
{ type: 'heading', props: { level: 3 }, content: 'Level 3' },
39+
{ type: 'heading', props: { level: 4 }, content: 'Level 4' },
40+
{ type: 'heading', props: { level: 5 }, content: 'Level 5' },
41+
{ type: 'heading', props: { level: 6 }, content: 'Level 6' },
42+
];
43+
options: BlockNoteEditorOptionsType<
44+
typeof schema.blockSchema,
45+
typeof schema.inlineContentSchema,
46+
typeof schema.styleSchema
47+
> = {
48+
schema,
49+
};
50+
}
51+
52+
export const alertBlockExampleCode = `import { CommonModule } from '@angular/common';
53+
import { Component } from '@angular/core';
54+
import {
55+
BlockNoteEditor,
56+
BlockNoteSchema,
57+
defaultBlockSpecs,
58+
defaultInlineContentSpecs,
59+
defaultStyleSpecs,
60+
insertOrUpdateBlock,
61+
PartialBlock,
62+
} from '@blocknote/core';
63+
import {
64+
BlockNoteEditorOptionsType,
65+
BnaEditorComponent,
66+
} from '@dytab/block-note-angular';
67+
import { HlmButtonDirective } from '@dytab/block-note-angular';
68+
import { alertBlock } from './alert-block';
69+
70+
const schema = BlockNoteSchema.create({
71+
blockSpecs: {
72+
...defaultBlockSpecs,
73+
alert: alertBlock,
74+
},
75+
inlineContentSpecs: { ...defaultInlineContentSpecs },
76+
styleSpecs: { ...defaultStyleSpecs },
77+
});
78+
@Component({
79+
selector: 'bna-alert-block-example',
80+
standalone: true,
81+
imports: [CommonModule, BnaEditorComponent, HlmButtonDirective],
82+
template: \`<bna-editor
83+
[initialContent]="initialContent"
84+
[options]="options"
85+
/>\`,
86+
})
87+
export class AlertBlockExample {
88+
initialContent: PartialBlock<typeof schema.blockSchema>[] = [
89+
{
90+
type: 'alert',
91+
props: {
92+
type: 'warning',
93+
},
94+
},
95+
];
96+
options: BlockNoteEditorOptionsType<
97+
typeof schema.blockSchema,
98+
typeof schema.inlineContentSchema,
99+
typeof schema.styleSchema
100+
> = {
101+
schema,
102+
inputSlashMenuItems: [
103+
(
104+
editor: BlockNoteEditor<
105+
typeof schema.blockSchema,
106+
typeof schema.inlineContentSchema,
107+
typeof schema.styleSchema
108+
>
109+
) => ({
110+
title: 'Alert',
111+
onItemClick: () => {
112+
insertOrUpdateBlock(editor, {
113+
type: 'alert' as never,
114+
});
115+
},
116+
badge: 'BAFD',
117+
subtext: 'SUBTEXT',
118+
aliases: [
119+
'alert',
120+
'notification',
121+
'emphasize',
122+
'warning',
123+
'error',
124+
'info',
125+
'success',
126+
],
127+
group: 'Other',
128+
}),
129+
],
130+
};
131+
}`;
Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
import { CommonModule } from '@angular/common';
2+
import { Component } from '@angular/core';
3+
import {
4+
BnaEditorComponent,
5+
HlmButtonDirective,
6+
hlmP,
7+
HlmTabsComponent,
8+
} from '@dytab/block-note-angular';
9+
import { CodeComponent } from '../../../../shared/code/code.component';
10+
import { DemoBoxComponent } from '../../../../shared/layout/demo-box.component';
11+
import { TabsComponent } from '../../../../shared/layout/example-tabs.component';
12+
import { SectionIntroComponent } from '../../../../shared/layout/section-intro.component';
13+
import {
14+
alertBlockExampleCode,
15+
HeadingBlockExample,
16+
} from './heading-block.example';
17+
18+
@Component({
19+
standalone: true,
20+
imports: [
21+
CommonModule,
22+
BnaEditorComponent,
23+
HlmButtonDirective,
24+
SectionIntroComponent,
25+
CodeComponent,
26+
DemoBoxComponent,
27+
HlmTabsComponent,
28+
TabsComponent,
29+
HeadingBlockExample,
30+
],
31+
template: `<bna-section-intro name="Heading Block">
32+
<p class="${hlmP} mb-8">
33+
In this example, we use our custom heading so that we can use 6 level
34+
headings instead of the default 3.
35+
</p>
36+
<p>
37+
<strong>Try it out</strong>: Press the "/" key to open the Slash Menu
38+
and insert the new heading levels!
39+
</p>
40+
</bna-section-intro>
41+
<hlm-tabs tab="preview">
42+
<bna-example-tabs firstTab="Preview" secondTab="Code">
43+
<bna-demo-box firstTab>
44+
<bna-heading-block-example />
45+
</bna-demo-box>
46+
<bna-code [code]="exampleCode" secondTab />
47+
</bna-example-tabs>
48+
</hlm-tabs>`,
49+
})
50+
export class HeadingBlockPage {
51+
exampleCode = alertBlockExampleCode;
52+
}

docs/src/pages/tiptap.d.ts

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
import {
2+
BlockSchema,
3+
InlineContentSchema,
4+
PartialBlock,
5+
StyleSchema,
6+
} from '@blocknote/core';
7+
8+
//TODO: check if tooling is the problem, that this is needed
9+
declare module '@tiptap/core' {
10+
interface Commands<ReturnType> {
11+
block: {
12+
BNCreateBlock: (pos: number) => ReturnType;
13+
BNDeleteBlock: (posInBlock: number) => ReturnType;
14+
BNMergeBlocks: (posBetweenBlocks: number) => ReturnType;
15+
BNSplitBlock: (
16+
posInBlock: number,
17+
keepType?: boolean,
18+
keepProps?: boolean
19+
) => ReturnType;
20+
BNUpdateBlock: <
21+
BSchema extends BlockSchema,
22+
I extends InlineContentSchema,
23+
S extends StyleSchema
24+
>(
25+
posInBlock: number,
26+
block: PartialBlock<BSchema, I, S>
27+
) => ReturnType;
28+
BNCreateOrUpdateBlock: <
29+
BSchema extends BlockSchema,
30+
I extends InlineContentSchema,
31+
S extends StyleSchema
32+
>(
33+
posInBlock: number,
34+
block: PartialBlock<BSchema, I, S>
35+
) => ReturnType;
36+
};
37+
}
38+
}
Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
{
2+
"extends": ["../../.eslintrc.base.json"],
3+
"ignorePatterns": ["!**/*"],
4+
"overrides": [
5+
{
6+
"files": ["*.ts", "*.tsx", "*.js", "*.jsx"],
7+
"rules": {}
8+
},
9+
{
10+
"files": ["*.ts", "*.tsx"],
11+
"rules": {}
12+
},
13+
{
14+
"files": ["*.js", "*.jsx"],
15+
"rules": {}
16+
},
17+
{
18+
"files": ["*.json"],
19+
"parser": "jsonc-eslint-parser",
20+
"rules": {
21+
"@nx/dependency-checks": [
22+
"error",
23+
{
24+
"ignoredFiles": ["{projectRoot}/vite.config.{js,ts,mjs,mts}"]
25+
}
26+
]
27+
}
28+
}
29+
]
30+
}

libs/block-note-extensions/README.md

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
# block-note-extensions
2+
3+
This library was generated with [Nx](https://nx.dev).
4+
5+
## Building
6+
7+
Run `nx build block-note-extensions` to build the library.
8+
9+
## Running unit tests
10+
11+
Run `nx test block-note-extensions` to execute the unit tests via [Vitest](https://vitest.dev/).
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
{
2+
"name": "@dytab/block-note-extensions",
3+
"version": "0.0.1",
4+
"dependencies": {},
5+
"main": "./index.js",
6+
"module": "./index.mjs",
7+
"typings": "./index.d.ts"
8+
}
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
{
2+
"name": "block-note-extensions",
3+
"$schema": "../../node_modules/nx/schemas/project-schema.json",
4+
"sourceRoot": "libs/block-note-extensions/src",
5+
"projectType": "library",
6+
"release": {
7+
"version": {
8+
"generatorOptions": {
9+
"packageRoot": "dist/{projectRoot}",
10+
"currentVersionResolver": "git-tag"
11+
}
12+
}
13+
},
14+
"tags": [],
15+
"targets": {
16+
"build": {
17+
"executor": "@nx/vite:build",
18+
"outputs": ["{options.outputPath}"],
19+
"options": {
20+
"outputPath": "dist/libs/block-note-extensions",
21+
"main": "libs/block-note-extensions/src/index.ts",
22+
"tsConfig": "libs/block-note-extensions/tsconfig.lib.json",
23+
"assets": ["libs/block-note-extensions/*.md"]
24+
}
25+
},
26+
"nx-release-publish": {
27+
"options": {
28+
"packageRoot": "dist/{projectRoot}"
29+
}
30+
}
31+
}
32+
}
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
export * from './lib/heading/heading.block';

0 commit comments

Comments
 (0)