Skip to content

Instantly share code, notes, and snippets.

@alphaKAI
Created January 10, 2019 17:05
Show Gist options
  • Save alphaKAI/2947bdc587e919e9fda5c4ff0741e6cc to your computer and use it in GitHub Desktop.
Save alphaKAI/2947bdc587e919e9fda5c4ff0741e6cc to your computer and use it in GitHub Desktop.
Get width and height of terminal for Windows(cmd.exe), macOS, Linux in F#
type window_size = {
x: uint16;
y: uint16;
}
open System.Runtime.InteropServices
[<Struct; StructLayout(LayoutKind.Sequential)>]
type winsize =
struct
val ws_row: uint16
val ws_col: uint16
val ws_xpixel: uint16
val ws_ypixel: uint16
end
// for UNIX
[<DllImport("libc")>]
extern int ioctl(int, int, winsize&)
// Windows
[<Struct; StructLayout(LayoutKind.Sequential)>]
type COORD =
struct
val X: int16
val T: int16
end
[<Struct; StructLayout(LayoutKind.Sequential)>]
type SMALL_RECT =
struct
val Left: int16
val Top: int16
val Right: int16
val Bottom: int16
end
[<Struct; StructLayout(LayoutKind.Sequential)>]
type CONSOLE_SCREEN_BUFFER_INFO =
struct
val dwSize: COORD
val dwCursorPosition: COORD
val wAttributes: int16
val srWindow: SMALL_RECT
val dwMaximumWindowSize: COORD
end
open System
[<DllImport("kernel32.dll", SetLastError = true)>]
extern IntPtr GetStdHandle(int nStdHandle)
let STD_OUTPUT_HANDLE = -11
[<DllImport("kernel32.dll", SetLastError = true)>]
extern bool GetConsoleScreenBufferInfo(IntPtr hConsoleOutput, CONSOLE_SCREEN_BUFFER_INFO& ConsoleScreenBufferInfo);
let get_window_size () =
if (RuntimeInformation.IsOSPlatform OSPlatform.OSX || RuntimeInformation.IsOSPlatform OSPlatform.Linux) then
let STDIN_FILENO = 0
let TIOCGWINSZ =
if RuntimeInformation.IsOSPlatform OSPlatform.OSX then
1074295912
else
21523
let mutable ws = new winsize ()
ioctl(STDIN_FILENO , TIOCGWINSZ, &ws) |> ignore
{
x=ws.ws_col;
y=ws.ws_row;
}
else
let mutable csbi = new CONSOLE_SCREEN_BUFFER_INFO ()
GetConsoleScreenBufferInfo(GetStdHandle(STD_OUTPUT_HANDLE), &csbi) |> ignore
let columns = csbi.srWindow.Right - csbi.srWindow.Left + int16 1
let rows = csbi.srWindow.Bottom - csbi.srWindow.Top + int16 1
{
x = uint16 columns;
y = uint16 rows;
}
let ws = get_window_size ()
printfn "lines : %d" ws.y
printfn "columns : %d" ws.x
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment