Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: expose the renderer interface #1094

Merged
merged 14 commits into from
Aug 21, 2024
Merged

feat: expose the renderer interface #1094

merged 14 commits into from
Aug 21, 2024

Conversation

aymanbagabas
Copy link
Member

@aymanbagabas aymanbagabas commented Aug 19, 2024

This adds the ability to use a custom renderer using a modified version of the existing renderer interface. This also keeps track of enabled capabilities and ensure they are turned off on program exit. It only turns off enabled capabilities rather.

The new API looks like:

// Renderer is the interface for Bubble Tea renderers.
type Renderer interface {
	// Close closes the renderer and flushes any remaining data.
	Close() error

	// Render renders a frame to the output.
	Render(string) error

	// SetOutput sets the output for the renderer.
	SetOutput(io.Writer)

	// Flush flushes the renderer's buffer to the output.
	Flush() error

	// InsertAbove inserts lines above the current frame. This only works in
	// inline mode.
	InsertAbove(string) error

	// Resize sets the size of the terminal.
	Resize(w int, h int)

	// Request a full re-render. Note that this will not trigger a render
	// immediately. Rather, this method causes the next render to be a full
	// Repaint. Because of this, it's safe to call this method multiple times
	// in succession.
	Repaint()

	// ClearScreen clear the terminal screen. This should always have the same
	// behavior as the "clear" command which is equivalent to `CSI 2 J` and
	// `CSI H`.
	ClearScreen()

	// SetMode sets a terminal mode on/off. The mode argument is an int
	// consisting of the mode identifier.
	// For example, to set alt-screen mode, you would call SetMode(1049, true).
	SetMode(mode int, on bool)

	// Mode returns whether the render has a mode enabled.
	// For example, to check if alt-screen mode is enabled, you would call
	// Mode(1049).
	Mode(mode int) bool
}

This also introduces some performance gains by not writing unnecessary sequences on enable/disable terminal modes. For example, we always hide the cursor when the program runs, it doesn't make sense to write the sequence again when the model sends a HideCursor command, we already know it's hidden. Don't always disable mouse if it wasn't enabled in the first place.

@aymanbagabas aymanbagabas marked this pull request as ready for review August 19, 2024 19:36
@aymanbagabas aymanbagabas force-pushed the custom-renderer branch 2 times, most recently from ac75d33 to 28b8d7e Compare August 19, 2024 21:03
options.go Show resolved Hide resolved
Use Render instead of Write/WriteString
Only disable enabled capabilities. Keep track of mouse mode state.
@aymanbagabas aymanbagabas requested a review from caarlos0 August 20, 2024 21:31
Use Mode/SetMode instead of EnableAltScreenBuffer/DisableAltScreenBuffer
etc. This uses less code and makes it more usable in the future to
accommodate for more terminal capabilities and modes.
@aymanbagabas aymanbagabas merged commit 1f5a28f into master Aug 21, 2024
18 checks passed
@aymanbagabas aymanbagabas deleted the custom-renderer branch August 21, 2024 20:26
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.

3 participants