Skip to content

Add Typst integration (and appease clippy) - #1587

Open
Xyndra wants to merge 23 commits into
flxzt:mainfrom
Xyndra:typst
Open

Add Typst integration (and appease clippy)#1587
Xyndra wants to merge 23 commits into
flxzt:mainfrom
Xyndra:typst

Conversation

@Xyndra

@Xyndra Xyndra commented Nov 14, 2025

Copy link
Copy Markdown

Fixes #644

Current state (as of first commit): button with a menu that has a preview button and renders into a vector
Ideal end state: button with a menu that automatically updates its preview, rendering into an image or vector format that contains its original text for editing, but can also cancel in cases where some resources went missing and can't be recovered

@Xyndra

Xyndra commented Nov 14, 2025

Copy link
Copy Markdown
Author
  • Live preview
  • Higher resolution in the preview
  • Fix monospace
  • Option between image and vector format (considered unimportant/useless for first version)
  • Allow for changing text after inserting (with proper cancel button)
  • Possibly some kind of auto-saving for changes since there are a lot of important changes happening without closing the menu and the menu can simply be closed with escape atm
  • Consider shipping fonts for typst

@Xyndra

Xyndra commented Nov 14, 2025

Copy link
Copy Markdown
Author

how it looks atm:

image

@Xyndra

Xyndra commented Nov 15, 2025

Copy link
Copy Markdown
Author

I would appreciate feedback, especially from @flxzt, both about the looks/idea and the code

@Xyndra

Xyndra commented Nov 15, 2025

Copy link
Copy Markdown
Author

I am unsure whether to increment the save version number, would need some info from the maintainers.
It does not crash in either direction, but accessing it with an older version removes the Typst text metadata.

@Xyndra
Xyndra marked this pull request as ready for review November 16, 2025 11:51
@Xyndra

Xyndra commented Nov 16, 2025

Copy link
Copy Markdown
Author

I think this is enough for a first version. The auto-save and option between pixel and vector are not must-haves, and about incrementing the version number, I would need feedback from maintainers (most of the save format seems to be from @flxzt)

@anesthetice

Copy link
Copy Markdown
Contributor

Not a maintainer, but looks pretty promising! I have a couple of comments / suggestions though (not in order of importance or anything):

(also saw you just commit something as I'm writing this, I hope my comments aren't already out-of-date)

  • Any reason for using version 0.12.0 of typst when 0.14.0 is out?
  • I would move the typst-related code in crates/rnote-engine/src/utils.rs to their own file
  • Is there a way to import typst packages (e.g. CeTZ)?
  • I realize I am way too dependent on code-completion (e.g. from tinymist) to write typst, but somewhat hard to use without to be frank.

As for the UI

satty_2025-11-16_13:15:01

Finally, I'm still not too familiar with GTK and more complicated Rnote internals as a whole, so I can't comment on much more..

@Xyndra

Xyndra commented Nov 16, 2025

Copy link
Copy Markdown
Author

Not a maintainer, but looks pretty promising! I have a couple of comments / suggestions though (not in order of importance or anything):

(also saw you just commit something as I'm writing this, I hope my comments aren't already out-of-date)

* Any reason for using version `0.12.0` of typst when `0.14.0` is out?

* I would move the typst-related code in [crates/rnote-engine/src/utils.rs](https://github.com/flxzt/rnote/pull/1587/files#diff-69e14b6632502e3ecc34bc99cab25aebed4717bb0b288df3f5f8fb96808827a4) to their own file

* Is there a way to import typst packages (e.g. CeTZ)?

* I realize I am way too dependent on code-completion (e.g. from tinymist) to write typst, but somewhat hard to use without to be frank.

As for the UI
satty_2025-11-16_13:15:01

Finally, I'm still not too familiar with GTK and more complicated Rnote internals as a whole, so I can't comment on much more..

Thanks for the feedback, you are right, I did seem to make a few oversights. I will look into all of them, but I can already say that tinymist integration is close to impossible, at least for me. That is something that would require IDE-like infrastructure, which a simple GTK text field most likely does not have.

@anesthetice

Copy link
Copy Markdown
Contributor

There does seem to be a library GtkSourceView for gtk4 that helps with code completion, but still probably a herculean task to set up and integrate with something like tinymist.

@Xyndra

Xyndra commented Nov 16, 2025

Copy link
Copy Markdown
Author

Yeah, that is something that is definitely too much for a first version, maybe at a later point in time. This is also not meant to be a Typst IDE, just a way to write something scientific like with LaTeX.

@Xyndra

Xyndra commented Nov 16, 2025

Copy link
Copy Markdown
Author

Lilaq is now working
image

@Xyndra

Xyndra commented Nov 16, 2025

Copy link
Copy Markdown
Author

I have now fixed all the feedback except for the misalignment of the middle line (which is draggable, and honestly not that bad), and the tinymist stuff since that is way too hard

@Xyndra

Xyndra commented Nov 17, 2025

Copy link
Copy Markdown
Author

@flxzt I fixed all the clippy messages, if that was what is keeping you from merging this. Would be nice if you could merge this, since I have other changes conflicting with this I want to work on

@Xyndra Xyndra changed the title Add Typst integration Add Typst integration (and appease clippy) Nov 17, 2025
@flxzt

flxzt commented Nov 17, 2025

Copy link
Copy Markdown
Owner

Typst support is something that is super exciting, this is quite incredible!

I need to do a proper review on this huge diff. It looks good, but it might take a little while until I am able to do it

Also, remove random vertical seperater from shape page
Vim habits caused me so much pain before this lol Also, I switched the
position of the insert button
@Xyndra

Xyndra commented Nov 18, 2025

Copy link
Copy Markdown
Author

Btw if this ever gets merged, I also have another branch based on this where I also added a marker tool

@Doublonmousse

Copy link
Copy Markdown
Collaborator

One trick that could be used for the IDE part is the use of temporary files.

I've seen it done on some GUI sftp software. Show the folder content, and if you want to edit a text file on remote, you can "open with" your favorite IDE and it just opens the file with the IDE. Internally, it downloads and copy the file to a temp folder, calls the "open with" command on the file (so you can choose any program that opens txt), and more importantly watches the files so that when you save it in the IDE, it syncs the change back to the remote.

Using the same tactic here, we could make it possible to edit each typst element in vscode with all the benefits of the IDE support

@Xyndra

Xyndra commented Nov 20, 2025

Copy link
Copy Markdown
Author

I also noticed I need to set the flag for the flatpak somewhere so that it is allowed to access the internet for typst plugins

@hoellwerth

hoellwerth commented Dec 13, 2025

Copy link
Copy Markdown

Wonderful feature! It also integrates well with whole app.

Is there a possibility of rendering in white font when dark style is active? Maybe also allow exiting the typst editor by pressing 'Esc'

image

Also when double-clicking an existing typst text, which is not tha unintuitive, it opens the windows twice.

@Xyndra

Xyndra commented Dec 13, 2025

Copy link
Copy Markdown
Author

Is there a possibility of a white font when dark style is active?

This is not really something for the wrapper but rather for the file (you can change font color and background color in typst), but in the future, maybe it could put the color from the current tool as text color. I think that is a bit much for a first attempt though, as there are already huge changes.

Maybe also allow exiting the typst editor by pressing 'Esc'

See the conversation above, allowing 'esc' to exit would lead to the entire file being lost, which can be really annoying, especially for people frequently using vim where you esc+:+w+enter to save a file. As mentioned above, maybe this could be solved by implementing an "open in editor", but since this is cross-platform, even supporting embedded, which I can't test, I am not sure if that is a good idea to add.

Also when double-clicking an existing typst text, which is not tha unintuitive, it opens the windows twice.

I noticed that too, however that is a bit hard to fix with the project structure. This happens because renderer and drawing are decoupled and the popup sometimes is not fast enough. For me, this only occurs the first time since once Typst is loaded, it is fast enough to open before I can click again, but that probably depends on system load

@hoellwerth

Copy link
Copy Markdown

Thanks for the really fast reply, Sorry for not entirely reading the conversation, I guess I was just too excited for the change! can't wait to see this in upstream and really looking forward to future features.

@Doublonmousse Doublonmousse left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For other comments on the thread

See the conversation above, allowing 'esc' to exit would lead to the entire file being lost, which can be really annoying, especially for people frequently using vim where you esc+:+w+enter to save a file. As mentioned above, maybe this could be solved by implementing an "open in editor", but since this is cross-platform, even supporting embedded, which I can't test, I am not sure if that is a good idea to add.

I'm not getting this (is it because you call update on the VectorImage on confirmation only ?). Do note that on the dialog itself, you can use https://world.pages.gitlab.gnome.org/Rust/libadwaita-rs/stable/latest/docs/libadwaita/struct.Dialog.html#method.connect_close_attempt or connect_close and do some additional processing before closing the dialog

  • maybe set the text to be what's on the window
  • and/or check if the text has changed, and if so force a new save/cancel dialog so you can't accidentally erase things

This is not really something for the wrapper but rather for the file (you can change font color and background color in typst), but in the future, maybe it could put the color from the current tool as text color. I think that is a bit much for a first attempt though, as there are already huge changes.

One idea is to get the background color from the settings and put this just below the typst code preview. That way it's not dependent on the light/dark mode, but whether or not the typst svg would be visible on a blank page.

Comment thread crates/rnote-engine/Cargo.toml Outdated
Comment on lines +60 to +70
typst = { workspace = true, optional = true }
typst-kit = { workspace = true, optional = true }
typst-svg = { workspace = true, optional = true }

[dev-dependencies]
approx = { workspace = true }

[features]
cli = ["dep:clap"]
default = []
ui = ["dep:gtk4"]
ui = ["dep:gtk4", "dep:typst", "dep:typst-kit", "dep:typst-svg"]

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think making typst optional works in that case.

Remember that the rnote-cli + the thumbnailer must be capable of rendering a rnote file to pdf/svg

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

rnote-cli can render Typst content just fine without the typst crate. The reason is that when a user creates Typst content in the UI, the source is compiled to SVG and the resulting SVG is what gets stored in the .rnote file (in VectorImage.svg_data). The typst_source field is only metadata for re-editing. When rnote-cli exports or generates thumbnails, it renders the pre-compiled SVG data — exactly like any other VectorImage stroke. The typst crate is only needed for the compilation step (source → SVG), which only happens during editing in the UI

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As long as there isn't a way for incoherent states to occur (typst source not synced with the resulting svg) then it's fine.

I'll try to test this later (as a side note, can you close a rnote window where the typst source was modified but not committed yet ? Because it'd be expected that this should open some sort of save unsaved changes window)

Comment thread crates/rnote-engine/src/engine/import.rs
}

/// Update an existing Typst stroke with new SVG data and source code.
pub fn update_typst_stroke(

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For this one, half of it could be a method in VectorImage like update_image and the rest that would stay would be related to the widget flags and store (if it doesn't come from the widget flags handler)

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Another thing on typing : I'm not sure the best way to go is to add a field to a VectorImage (which can be or not be from a typst edition).

Maybe it's a little better to add a separate typst type.

Note for compatibility : this PR needs to bump the rnote file version as the extra field makes it (probably) forward compatible (because of the serde skip if the typst source is one) but not backwards if a typst element is added

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I honestly don't see how you would bump version numbers. It seems like they are simply the app version, and the code for previous rnote versions just checks for anything that isn't older than itself, at least how I understand it. Also, it is bidirectionally compatible, however the typst metadata gets deleted when saving from an older version

Comment thread crates/rnote-engine/src/pens/typewriter/penevents.rs Outdated
Comment thread crates/rnote-engine/src/typst.rs Outdated
<property name="transition_type">GTK_STACK_TRANSITION_TYPE_SLIDE_LEFT_RIGHT</property>
<property name="interpolate_size">True</property>
<property name="hhomogeneous">False</property>
<property name="vhomogeneous">False</property>

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't know if I prefer with or without the *homogeneous setting

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I honestly prefer it a lot, I have been using it for a few months now

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd see one argument against this: when using touch, the first button stays at the same place so it's probably a little easier to use from muscle memory (whereas this probably doesn't change anything from keyboard/mouse users).

I don't feel too strongly about either options, I'll let @flxzt decide on this.

Comment thread crates/rnote-ui/src/dialogs/typsteditor.rs Outdated
Comment thread crates/rnote-engine/src/engine/mod.rs Outdated
Comment thread crates/rnote-engine/src/engine/mod.rs Outdated
@Doublonmousse

Copy link
Copy Markdown
Collaborator

Another though : you could store the selected typst stroke in the typewriter states so that signaling to open the editor is easier :

  • note that the stroke was selected on handle_pen_down
  • send some signals on handle_pen_up (at that point you'd know it's both a pen up and a typst stroke was selected)

@Xyndra
Xyndra requested a review from Doublonmousse February 22, 2026 02:03
@astro-ray astro-ray mentioned this pull request Mar 4, 2026
@TimerErTim

Copy link
Copy Markdown

I really enjoy Typst and use Rnote frequently for my studies, so I am really looking forward to this. The PR has been going on for quite some while, is there something anyone of you could use assistance for?

@Doublonmousse

Copy link
Copy Markdown
Collaborator
  • There are conflicts to resolve (from us using hayro for pdf->svg import). Hopefully this doesn't create version conflicts
  • Maybe the following could be added
    • when unsaved changes are not commited, do a popup to confirm
    • change behavior when trying to close the app externally and the dialog is opened (currently nothing happens)
    • Should esc escape from the typst editor (with a confirm popup if unsaved changes aren't commited)
  • I'm having two x buttons now (don't really know why) on the typst editor
image

@Doublonmousse

Copy link
Copy Markdown
Collaborator

Another thing that'd be good : Display the typst version used.

I really don't know though how to tackle compatibility though (what can compile on a current version may not compile on the next ones because of deprecations so ... Given this is bundling a specific typst version, updates might not be always smooth - the svg is preserved but changing it if the rnote+typst version changed and it does not compile anymore may be an annoyance for users-)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Add typst support to typewriter

6 participants