Describe the bug
The code sample below shows what might be a bug which is that, only on macOS Terminal.app, trying to render a View to the full-width of the terminal causes wrapping which breaks what I'm trying to achieve. All other terminals (including iTerm, kitty, Alacritty) render as expected.
I may be using the APIs incorrectly or not using an API I should be.
Setup
Please complete the following information along with version numbers, if applicable.
- OS: macOS 15
- Shell: zsh, fish
- Terminal Emulator: Terminal.app
- Terminal Multiplexer: None
To Reproduce
Steps to reproduce the behavior:
- Create a go package and
go run the source
Source Code
package main
import (
"fmt"
"strings"
"time"
"github.com/charmbracelet/bubbles/progress"
"github.com/charmbracelet/bubbles/spinner"
tea "github.com/charmbracelet/bubbletea"
"github.com/charmbracelet/lipgloss"
)
type model struct {
n int
current int
spinner spinner.Model
progress progress.Model
done bool
width int
}
type tickMsg struct{}
func newModel() model {
s := spinner.New()
s.Spinner = spinner.Dot
p := progress.New()
return model{
n: 10,
spinner: s,
progress: p,
width: 80,
}
}
func (m model) Init() tea.Cmd {
return tea.Batch(m.spinner.Tick, tick())
}
func (m model) Update(msg tea.Msg) (tea.Model, tea.Cmd) {
switch msg := msg.(type) {
case tea.KeyMsg:
return m, tea.Quit
case tea.WindowSizeMsg:
m.width = msg.Width
return m, nil
case tickMsg:
if m.current >= m.n {
m.done = true
return m, tea.Quit
}
m.current++
percent := float64(m.current) / float64(m.n)
cmd := m.progress.SetPercent(percent)
return m, tea.Batch(cmd, tick())
default:
var cmds []tea.Cmd
var cmd tea.Cmd
m.spinner, cmd = m.spinner.Update(msg)
cmds = append(cmds, cmd)
progressModel, cmd := m.progress.Update(msg)
m.progress = progressModel.(progress.Model)
cmds = append(cmds, cmd)
return m, tea.Batch(cmds...)
}
}
func (m model) View() string {
if m.done || m.current >= m.n {
return ""
}
status := fmt.Sprintf("%s Running... ", m.spinner.View())
progressBarWidth := m.width / 2
m.progress.Width = progressBarWidth
progressBar := m.progress.View()
statusWidth := lipgloss.Width(status)
progressWidth := lipgloss.Width(progressBar)
gapWidth := m.width - statusWidth - progressWidth
// This is what we want to call
gap := strings.Repeat(" ", gapWidth)
// This is what we have to call on macOS Terminal.app
// gap := strings.Repeat(" ", gapWidth - 1)
return status + gap + progressBar
}
func tick() tea.Cmd {
return tea.Tick(300*time.Millisecond, func(time.Time) tea.Msg {
return tickMsg{}
})
}
func main() {
if _, err := tea.NewProgram(newModel()).Run(); err != nil {
fmt.Printf("Error: %v\n", err)
}
}
Expected behavior
I expect to be able to do my width calculation like shown in the source code snippet and to see rendering like what's shown in the iTerm 2 GIF.
Screenshots
Here's Terminal.app, showing that the line wraps which makes the rendering look wonky:

Here's iTerm2, showing the desired behavior:

Describe the bug
The code sample below shows what might be a bug which is that, only on macOS Terminal.app, trying to render a
Viewto the full-width of the terminal causes wrapping which breaks what I'm trying to achieve. All other terminals (including iTerm, kitty, Alacritty) render as expected.I may be using the APIs incorrectly or not using an API I should be.
Setup
Please complete the following information along with version numbers, if applicable.
To Reproduce
Steps to reproduce the behavior:
go runthe sourceSource Code
Expected behavior
I expect to be able to do my width calculation like shown in the source code snippet and to see rendering like what's shown in the iTerm 2 GIF.
Screenshots
Here's Terminal.app, showing that the line wraps which makes the rendering look wonky:
Here's iTerm2, showing the desired behavior: