Nory31 downloadsConvert Bilibili video URLs in Canvas to embedded player URLs (player.bilibili.com), auto-fit node size to 16:9 and set the real video title as node label.
English | 中文
Drop a Bilibili link onto an Obsidian Canvas and it becomes a real video player node — sized 16:9 and labelled with the actual video title — instead of a cramped 400×400 frame captioned "External Player - 哔哩哔哩弹幕网嵌入式播放器".
Obsidian's Canvas treats every URL as a generic web page. For a Bilibili video that means:
| Default behaviour | With this plugin | |
|---|---|---|
| URL loaded | bilibili.com/video/BV… (the full site) |
player.bilibili.com/player.html?bvid=BV… (embed player) |
| Node size | 400 × 400 | 16:9, at least 480 px wide |
| Node label | "External Player - 哔哩哔哩弹幕网嵌入式播放器" | the real video title |
| Label visibility | hover only | always visible |
Conversion is automatic: paste a link, drag one in from the browser, or use Add web page. The URL and size are rewritten before the node is created, so the original page never loads first.
Two commands are also available (Command palette → search for B站嵌入):
| Command | What it does |
|---|---|
B站嵌入: 整理当前 Canvas(换链接 + 取标题,不改尺寸) |
Converts URLs and refreshes titles on the active canvas without touching sizes — safe on a canvas you have hand-arranged |
B站嵌入: 整理当前 Canvas(换链接 + 取标题 + 强制 16:9) |
Same, plus forces every Bilibili node to 16:9 |
Command names are currently in Chinese.
Two Obsidian internals make this less trivial than it looks, and both are handled:
CanvasNode.moveAndResize does not fill in omitted arguments. Calling it with only { width, height } writes NaN into x/y, which poisons the canvas' rbush spatial index — afterwards nodes stop rendering and can no longer be dragged. This plugin always supplies all four values, or uses resize() (which fills them in internally).updateNodeLabel, triggered by setFrameUrl() and by the webview's page-title-updated event. The embed player reports its own title, which would overwrite the real one. Rather than racing that event, the plugin intercepts the label on its way out and substitutes the cached title.The label interception is installed as soon as a canvas is opened, not only when a node is created — otherwise reopening an existing canvas would get every title clobbered.
The plugin talks to Bilibili, because there is no other way to obtain a video title:
| Destination | Why | When |
|---|---|---|
api.bilibili.com/x/web-interface/view |
read the title for a given bvid |
once per video, then cached |
player.bilibili.com |
the embedded player shown in the node — an ordinary iframe your browser loads directly; the plugin does not proxy it | while the node is on screen |
Fetched titles are stored in the plugin's own data.json under .obsidian/plugins/bili-embed/. Nothing apart from the bvid being looked up is sent anywhere. No analytics, no other requests.
If the API rate-limits you, or a video is region/copyright restricted, no title is cached — the node label falls back to the URL, which is Obsidian's own default for link nodes.
canvas.createLinkNode, and the link node's setUrl / updateNodeLabel). A future Obsidian release could change them. The plugin fails safe: if a patch cannot be applied, links are simply left untouched.bilibili.com/video/BV…, m.bilibili.com/…, and already-converted player.bilibili.com links. Part information (?p=2) is preserved.Until the plugin is listed in the community directory, install manually:
main.js and manifest.json from the latest release<your vault>/.obsidian/plugins/bili-embed/Or install via BRAT using this repository's URL.
No build step — main.js is the source. Edit it, then reload the plugin.
MIT — see LICENSE.