diff --git a/internal/image/block.go b/internal/image/block.go index ffb7a04..9c91a7a 100644 --- a/internal/image/block.go +++ b/internal/image/block.go @@ -9,8 +9,6 @@ import ( "os" "runtime" "strings" - - "golang.org/x/term" ) const ( @@ -24,16 +22,11 @@ type rgbColor struct { } // writeBlocks resizes the image and outputs it as terminal blocks. -func writeBlocks(img image.Image) error { +func writeBlocks(img image.Image, termWidth, termHeight int) error { trueColor := supportsTrueColor() - termWidth, termHeight, err := term.GetSize(int(os.Stdout.Fd())) - if err != nil { - return err - } - cols, rows := imageBlockOutputDimensions(img, termWidth, termHeight) - // Each terminal block represents 2 vertical pixels. + cols, rows := imageBlockOutputDimensions(img, termWidth, termHeight) targetWidth := cols targetHeight := rows * 2 diff --git a/internal/image/image.go b/internal/image/image.go index bddebad..b200766 100644 --- a/internal/image/image.go +++ b/internal/image/image.go @@ -30,23 +30,23 @@ func Render(ctx context.Context, b []byte, nativeOnly bool) error { return nil } - termWidthPx, termHeightPx, err := getTermSizeInPixels() + size, err := getTerminalSize() if err != nil { return err } - if termWidthPx == 0 || termHeightPx == 0 { + if size.widthPx == 0 || size.heightPx == 0 { // If we're unable to get the terminal dimensions in pixels, // render the image using blocks. - return writeBlocks(img) + return writeBlocks(img, size.cols, size.rows) } switch detectEmulator().Protocol() { case protoInline: - return writeInline(img, termWidthPx, termHeightPx) + return writeInline(img, size.widthPx, size.heightPx) case protoKitty: - return writeKitty(img, termWidthPx, termHeightPx) + return writeKitty(img, size.widthPx, size.heightPx) default: - return writeBlocks(img) + return writeBlocks(img, size.cols, size.rows) } } @@ -144,3 +144,10 @@ func convertToRGBA(img image.Image) *image.RGBA { return out } } + +type terminalSize struct { + cols int + rows int + widthPx int + heightPx int +} diff --git a/internal/image/term_unix.go b/internal/image/term_unix.go index 0549daa..b5f5992 100644 --- a/internal/image/term_unix.go +++ b/internal/image/term_unix.go @@ -8,11 +8,16 @@ import ( "golang.org/x/sys/unix" ) -// getTermSizeInPixels returns the size of the terminal in pixels on unix. -func getTermSizeInPixels() (int, int, error) { +func getTerminalSize() (terminalSize, error) { + var ts terminalSize ws, err := unix.IoctlGetWinsize(int(os.Stdout.Fd()), unix.TIOCGWINSZ) if err != nil { - return 0, 0, err + return ts, err } - return int(ws.Xpixel), int(ws.Ypixel), nil + + ts.cols = int(ws.Col) + ts.rows = int(ws.Row) + ts.widthPx = int(ws.Xpixel) + ts.heightPx = int(ws.Ypixel) + return ts, nil } diff --git a/internal/image/term_windows.go b/internal/image/term_windows.go index fb0a821..8129363 100644 --- a/internal/image/term_windows.go +++ b/internal/image/term_windows.go @@ -2,7 +2,23 @@ package image -// getTermSizeInPixels always returns a zero width & height on windows. -func getTermSizeInPixels() (int, int, error) { - return 0, 0, nil +import ( + "os" + + "golang.org/x/sys/windows" +) + +func getTerminalSize() (terminalSize, error) { + var ts terminalSize + + var info windows.ConsoleScreenBufferInfo + handle := windows.Handle(int(os.Stdout.Fd())) + err := windows.GetConsoleScreenBufferInfo(handle, &info) + if err != nil { + return ts, err + } + + ts.cols = int(info.Window.Right - info.Window.Left + 1) + ts.rows = int(info.Window.Bottom - info.Window.Top + 1) + return ts, nil } diff --git a/internal/update/update_windows.go b/internal/update/update_windows.go index 62652d6..29d0284 100644 --- a/internal/update/update_windows.go +++ b/internal/update/update_windows.go @@ -247,6 +247,6 @@ func unlockFile(f *os.File) error { } // canReplaceFile always returns true on windows. -func canReplaceFile(path string) bool { +func canReplaceFile(_ string) bool { return true }