Complete control of cmd windows

Discussion forum for all Windows batch related topics.

Moderator: DosItHelp

Message
Author
einstein1969
Expert
Posts: 961
Joined: 15 Jun 2012 13:16
Location: Italy, Rome

Complete control of cmd windows

#1 Post by einstein1969 » 02 Oct 2022 09:21

Hello everyone,

I want to open this thread for two reasons:

1 - gather here the various techniques that are scattered around to manage the cmd window.

2 - solve a problem regarding the aspect ratio for drawing shapes using the new escape sequences of windows 10

I make an example as short as possible. The famous circle.

Here I have used almost none of the techniques that are out there on the web and here.

Code: Select all

@echo off & setlocal enableDelayedExpansion & if NOT "%1"=="" goto :subs

rem save this script in UTF-8

rem multithread

Start "" "%0" Red
Start "" "%0" Green
Start "" "%0" Blue
Start "" "%0" Yellow
Start "" "%0" Cyan
Start "" "%0" Magenta
Start "" "%0" White
Start "" "%0" Orange
Start "" "%0" Pink
Start "" "%0" Salmon
Start "" "%0" Navy
Start "" "%0" Gray

goto :eof

:subs

title %1

call :init

rem setting amount of char 50x50
set /A img.x=50, img.y=50

rem font size in pixels, change this for respect aspect ratio.
set /A xc=8, yc=16

set /A width=img.x*xc, height=img.y*yc

rem using aspect ratio for setting windows size
if !width! leq !height! (
	set /a res=width, img.y=img.y*xc/yc
) else set /a res=height, img.x=img.x*yc/xc

mode CON: COLS=!img.x! LINES=!img.y!

rem draw a circle (x-x0)^2+(y-y0)^2=r^2 . Implicit equation for simpler math.

rem set radius and center in cmd windows

set /A "R=res/2, X0=res/2, Y0=res/2"

rem setting step for better smoothing colors
set /A "mS=-(R*R), step=255*1000/-mS, stepL=128*1000/-mS"

For /L %%y in (1,1,!img.y!) do (

  For /L %%x in (1,1,!img.x!) do (

	rem calculate circle equation and color for smooting.
	rem This code generate multiple circlesof different color and simulate a 3D sphere.
        set /A px=%%x*xc, py=%%y*yc, x=px-x0, y=py-y0, S=y*y+x*x-R*R, C=-S*step/1000, CL=-S*stepL/1000"

	if !S! leq 0 (
		if "%1"=="Red" %plot% %%x %%y !C! 0 0
		if "%1"=="Green" %plot% %%x %%y 0 !C! 0
		if "%1"=="Blue" %plot% %%x %%y 0 0 !C!
		if "%1"=="Yellow" %plot% %%x %%y !C! !C! 0
		if "%1"=="Cyan" %plot% %%x %%y 0 !C! !C!
		if "%1"=="Magenta" %plot% %%x %%y !C! 0 !C!
		if "%1"=="White" %plot% %%x %%y !C! !C! !C!
		if "%1"=="Orange" %plot% %%x %%y !C! !CL! 0
		if "%1"=="Pink" %plot% %%x %%y !C! 0 !CL!
		if "%1"=="Salmon" %plot% %%x %%y !C! !CL! !CL!
		if "%1"=="Navy" %plot% %%x %%y 0 0 !CL!
		if "%1"=="Gray" %plot% %%x %%y !CL! !CL! !CL!
	)
  )
) 
%flush%

pause>nul
goto :eof

::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
:init

rem utf8
chcp 65001 >nul

rem for ansi sequence
for /F %%a in ('echo prompt $E^| %ComSpec%') do set "ESC=%%a"

rem clear environment for faster execution of SET command
set "Path=%SystemRoot%\system32"
for /F "Tokens=1 delims==" %%v in ('set') do if not %%v==ESC if not %%v==TMP if not %%v==Path set "%%v="

:: Hide the cursor
<nul set /p "=!ESC![?25l"


rem ALT+219
set "Char=█"
rem set "Char=*"

rem macro 

:: define LF as a Line Feed (newline) character
set ^"LF=^

^" Above empty line is required - do not remove

:: define a newline with line continuation
set ^"\n=^^^%LF%%LF%^%LF%%LF%^^"

::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
:: macro Plot=Screen.Setpixel X Y R G B

set "Buffer="

set Plot=for %%# in (1 2) do if %%#==2 (%\n%
	for /f "tokens=1-5 delims=, " %%1 in ("^!args^!") do ( %\n%
		if not defined Buffer (%\n%
			set "Buffer=^!ESC^![%%2;%%1H^!ESC^![38;2;%%3;%%4;%%5m^!Char^!" %\n%
		) else ( %\n%
			if "^!Buffer:~7000,1^!"=="" ( %\n%
				set "Buffer=^!Buffer^!^!ESC^![%%2;%%1H^!ESC^![38;2;%%3;%%4;%%5m^!Char^!" %\n%
			) else ( %\n%
				^<nul set /p "=^!Buffer^!^!ESC^![%%2;%%1H^!ESC^![38;2;%%3;%%4;%%5m^!Char^!^!ESC^![0m" %\n%
				set "Buffer=" %\n%
			) %\n%
		) %\n%
)) else set args=

::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
:: Flush flush the variable buffer.

set Flush=^<nul set /p "=^!Buffer^!^!ESC^![0m" ^& set "Buffer="

goto :eof
If you run the code you will most likely have a different result than mine and the circles will be ellipses.

This is because the cmd window fonts are not set as the script wants them.

In particular, the line that manages the size of the characters must be modified accordingly to the type of font that the cmd window is using. You can do this and relaunch the program and i the ellipse should become circles.

Code: Select all

rem font size in pixels, change this for respect aspect ratio.
set /A xc=8, yc=16
I wrote should because here I have found a strange problem that I want to bring to the attention of the most expert.

Image
The screen of my new laptop is 1920x1080 (FullHD) and in the screen settings if I put a recommended resizing of 125% it messes up all the work I have to do to recalculate the new aspect ratio. But I don't know where to get the data :(

Place the two images.

with 100% ----------------------------------------------------> with 125% (are ellipsoids)
ImageImage

3 - PS. Can any expert tell me the latest syntax to define the %\n% for macros?

Einstein1969
Last edited by einstein1969 on 02 Oct 2022 11:43, edited 1 time in total.

aGerman
Expert
Posts: 4678
Joined: 22 Jan 2010 18:01
Location: Germany

Re: Complete control of cmd windows

#2 Post by aGerman » 02 Oct 2022 10:22

Neat :D
latest syntax to define the %\n% for macros
I like this one:

Code: Select all

(set \n=^^^
%= This creates an escaped Line Feed - DO NOT ALTER =%
)
Steffen

einstein1969
Expert
Posts: 961
Joined: 15 Jun 2012 13:16
Location: Italy, Rome

Re: Complete control of cmd windows

#3 Post by einstein1969 » 02 Oct 2022 11:50

aGerman wrote:
02 Oct 2022 10:22
Neat :D
latest syntax to define the %\n% for macros
I like this one:

Code: Select all

(set \n=^^^
%= This creates an escaped Line Feed - DO NOT ALTER =%
)
Steffen
Hi aGerman and thanks.

So am I replacing the two definitions with this new one?

Code: Select all

:: define LF as a Line Feed (newline) character
set ^"LF=^

^" Above empty line is required - do not remove

:: define a newline with line continuation
set ^"\n=^^^%LF%%LF%^%LF%%LF%^^"
In the previous post I added that I can not find the data to be able to do the correction of the aspect ratio ...
.

aGerman
Expert
Posts: 4678
Joined: 22 Jan 2010 18:01
Location: Germany

Re: Complete control of cmd windows

#4 Post by aGerman » 02 Oct 2022 14:05

So am I replacing the two definitions with this new one?
Correct.
In the previous post I added that I can not find the data to be able to do the correction of the aspect ratio ...
The only possibility of getting the font size without a 3rd party utility is PowerShell.

Code: Select all

@echo off &setlocal

set GetConsoleFontSize=powershell -nop -ep Bypass -c ^"try{$w=Add-Type -Name WAPI -PassThru -MemberDefinition '^
%=% [DllImport(\"kernel32.dll\")] public static extern void GetCurrentConsoleFont(IntPtr hOut,int isMax,int[] info);^
%=% [DllImport(\"kernel32.dll\")] public static extern IntPtr GetStdHandle(int idx);';^
%=% [int[]]$info=0,0;$w::GetCurrentConsoleFont($w::GetStdHandle(-11),0,$info);exit $info[1];}catch{exit 0;}^"

%GetConsoleFontSize%
set /a "X=%errorlevel% & 0xFFFF, Y=(%errorlevel% >> 16) & 0xFFFF"
echo width %X%, height %Y%

pause
However, this requires that PowerShell and its dependencies can still be found. Thus, you must refactor your environment handling.

Steffen

einstein1969
Expert
Posts: 961
Joined: 15 Jun 2012 13:16
Location: Italy, Rome

Re: Complete control of cmd windows

#5 Post by einstein1969 » 03 Oct 2022 14:37

i'm going crazy, but if i run this code, it changes the font in the running part of powershell %GetConsoleFontSize%

Code: Select all

@echo off & setlocal enableDelayedExpansion & if NOT "%1"=="" goto :subs

Start "" "%0" Red

goto :eof

:subs
pause

call :init

set GetConsoleFontSize=powershell -nop -ep Bypass -c ^"try{$w=Add-Type -Name WAPI -PassThru -MemberDefinition '^
%=% [DllImport(\"kernel32.dll\")] public static extern void GetCurrentConsoleFont(IntPtr hOut,int isMax,int[] info);^
%=% [DllImport(\"kernel32.dll\")] public static extern IntPtr GetStdHandle(int idx);';^
%=% [int[]]$info=0,0;$w::GetCurrentConsoleFont($w::GetStdHandle(-11),0,$info);exit $info[1];}catch{exit 0;}^"

echo before getconsole
pause

%GetConsoleFontSize%

echo after getconsole
pause

goto :eof

::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
:init

rem utf8
chcp 65001 >nul

goto :eof
it is chcp 65001 ?

Image

Image

.

einstein1969
Expert
Posts: 961
Joined: 15 Jun 2012 13:16
Location: Italy, Rome

Re: Complete control of cmd windows

#6 Post by einstein1969 » 03 Oct 2022 14:53

more simple

Code: Select all

@echo off & setlocal enableDelayedExpansion


rem utf8
chcp 65001 >nul

set GetConsoleFontSize=powershell -nop -ep Bypass -c ^"try{$w=Add-Type -Name WAPI -PassThru -MemberDefinition '^
%=% [DllImport(\"kernel32.dll\")] public static extern void GetCurrentConsoleFont(IntPtr hOut,int isMax,int[] info);^
%=% [DllImport(\"kernel32.dll\")] public static extern IntPtr GetStdHandle(int idx);';^
%=% [int[]]$info=0,0;$w::GetCurrentConsoleFont($w::GetStdHandle(-11),0,$info);exit $info[1];}catch{exit 0;}^"

echo before getconsole
pause

%GetConsoleFontSize%

echo after getconsole
pause

goto :eof

aGerman
Expert
Posts: 4678
Joined: 22 Jan 2010 18:01
Location: Germany

Re: Complete control of cmd windows

#7 Post by aGerman » 03 Oct 2022 15:19

I can't reproduce this issue on Windows 11. However, if you assume setting the encoding to UTF-8 is the culprit, what if you update it after calling the PowerShell macro?

Code: Select all

@echo off & setlocal enableDelayedExpansion

set GetConsoleFontSize=powershell -nop -ep Bypass -c ^"try{$w=Add-Type -Name WAPI -PassThru -MemberDefinition '^
%=% [DllImport(\"kernel32.dll\")] public static extern void GetCurrentConsoleFont(IntPtr hOut,int isMax,int[] info);^
%=% [DllImport(\"kernel32.dll\")] public static extern IntPtr GetStdHandle(int idx);';^
%=% [int[]]$info=0,0;$w::GetCurrentConsoleFont($w::GetStdHandle(-11),0,$info);exit $info[1];}catch{exit 0;}^"

echo before getconsole
pause

%GetConsoleFontSize%

rem utf8
chcp 65001 >nul

echo after getconsole
pause

goto :eof
Steffen

einstein1969
Expert
Posts: 961
Joined: 15 Jun 2012 13:16
Location: Italy, Rome

Re: Complete control of cmd windows

#8 Post by einstein1969 » 04 Oct 2022 09:18

I'm on windows 10.

Ok it seems that putting the chcp 65001 after solves the problem and the circles are not ellipses even with the zoom at 125%.

There is only a bug that the font dimensions reported in the window properties are incorrect. (But the dimensions reported by the command in powershell are different but exact for the right aspect ratio at both 100% and 125%)

In this image the font size returned by powershell macro is 7x16 but the property windows show 8x16 at 125% of zoom. It's a BUG!
Image

I put here the updated script for those who want to play with it a bit. It is possible to change the font and rerun the script to generate new images with the right aspect ratio.

the updated script:

Code: Select all

@echo off & setlocal enableDelayedExpansion & if NOT "%1"=="" goto :subs

rem save this script in UTF-8

rem multithread

Start "Sphere" "%0" Red
::Start "Sphere" "%0" Green
::Start "Sphere" "%0" Blue
::Start "Sphere" "%0" Yellow
::Start "Sphere" "%0" Cyan
::Start "Sphere" "%0" Magenta
::Start "Sphere" "%0" White
::Start "Sphere" "%0" Orange
::Start "Sphere" "%0" Pink
::Start "Sphere" "%0" Salmon
::Start "Sphere" "%0" Navy
::Start "Sphere" "%0" Gray

goto :eof

:subs

title %1

call :init

rem setting amount of char 60x60
set /A img.x=60, img.y=60

rem font size in pixels, change this for respect aspect ratio.
set /A xc=FontSize.X, yc=FontSize.Y

set /A width=img.x*xc, height=img.y*yc

rem using aspect ratio for setting windows size
if !width! leq !height! (
	set /a res=width, img.y=img.y*xc/yc
) else set /a res=height, img.x=img.x*yc/xc

mode CON: COLS=!img.x! LINES=!img.y!

rem draw a circle (x-x0)^2+(y-y0)^2=r^2 . Implicit equation for simpler math.

rem set radius and center in cmd windows

set /A "R=res/2, X0=res/2, Y0=res/2"

rem setting step for better smoothing colors
set /A "mS=-(R*R), step=255*100000/-mS, stepL=128*100000/-mS"

For /L %%y in (1,1,!img.y!) do (

  For /L %%x in (1,1,!img.x!) do (

	rem calculate circle equation and color for smooting.
	rem This code generate multiple circlesof different color and simulate a 3D sphere.
        set /A px=%%x*xc, py=%%y*yc, x=px-x0, y=py-y0, S=y*y+x*x-R*R, C=-S*step/100000, CL=-S*stepL/100000"

	if !S! leq 0 (
		if "%1"=="Red" %plot% %%x %%y !C! 0 0
		if "%1"=="Green" %plot% %%x %%y 0 !C! 0
		if "%1"=="Blue" %plot% %%x %%y 0 0 !C!
		if "%1"=="Yellow" %plot% %%x %%y !C! !C! 0
		if "%1"=="Cyan" %plot% %%x %%y 0 !C! !C!
		if "%1"=="Magenta" %plot% %%x %%y !C! 0 !C!
		if "%1"=="White" %plot% %%x %%y !C! !C! !C!
		if "%1"=="Orange" %plot% %%x %%y !C! !CL! 0
		if "%1"=="Pink" %plot% %%x %%y !C! 0 !CL!
		if "%1"=="Salmon" %plot% %%x %%y !C! !CL! !CL!
		if "%1"=="Navy" %plot% %%x %%y 0 0 !CL!
		if "%1"=="Gray" %plot% %%x %%y !CL! !CL! !CL!
	)
  )
) 
%flush%

pause>nul
goto :eof

::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
:init

rem for ansi sequence
for /F %%a in ('echo prompt $E^| %ComSpec%') do set "ESC=%%a"

:: Hide the cursor
<nul set /p "=!ESC![?25l"

rem thanks aGerman
set GetConsoleFontSize=powershell -nop -ep Bypass -c ^"try{$w=Add-Type -Name WAPI -PassThru -MemberDefinition '^
%=% [DllImport(\"kernel32.dll\")] public static extern void GetCurrentConsoleFont(IntPtr hOut,int isMax,int[] info);^
%=% [DllImport(\"kernel32.dll\")] public static extern IntPtr GetStdHandle(int idx);';^
%=% [int[]]$info=0,0;$w::GetCurrentConsoleFont($w::GetStdHandle(-11),0,$info);exit $info[1];}catch{exit 0;}^"

%GetConsoleFontSize%

rem font size in pixels
set /a "FontSize.X=%errorlevel% & 0xFFFF, FontSize.Y=(%errorlevel% >> 16) & 0xFFFF"

rem clear environment for faster execution of SET command
(
set "Path=%SystemRoot%\system32"
for /F "Tokens=1 delims==" %%v in ('set') do if not %%v==ESC if not %%v==TMP if not %%v==Path set "%%v="
set /a "FontSize.X=%FontSize.X% , FontSize.Y=%FontSize.Y%"
)

rem this code must execute after GetConsoleFontSize macro, if not change font family, in window 10
chcp 65001 >nul

rem ALT+219
set "Char=█"
rem set "Char=*"

rem for macro definition/readability
(set \n=^^^
%= This creates an escaped Line Feed - DO NOT ALTER =%
)

::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
:: macro Plot=Screen.Setpixel X Y R G B

set "Buffer="

set Plot=for %%# in (1 2) do if %%#==2 (%\n%
	for /f "tokens=1-5 delims=, " %%1 in ("^!args^!") do ( %\n%
		if not defined Buffer (%\n%
			set "Buffer=^!ESC^![%%2;%%1H^!ESC^![38;2;%%3;%%4;%%5m^!Char^!" %\n%
		) else ( %\n%
			if "^!Buffer:~3500,1^!"=="" ( %\n%
				set "Buffer=^!Buffer^!^!ESC^![%%2;%%1H^!ESC^![38;2;%%3;%%4;%%5m^!Char^!" %\n%
			) else ( %\n%
				^<nul set /p "=^!Buffer^!^!ESC^![%%2;%%1H^!ESC^![38;2;%%3;%%4;%%5m^!Char^!^!ESC^![0m" %\n%
				set "Buffer=" %\n%
			) %\n%
		) %\n%
)) else set args=

::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
:: Flush flush the variable buffer.

set Flush=^<nul set /p "=^!Buffer^!^!ESC^![0m" ^& set "Buffer="

goto :eof
Now I would like to ask:

- Is it possible to access the screen size via batch. In my case 1920x1080?

(This way I can create a window large enough to make a circle that takes up the whole screen.)

.

einstein1969
Expert
Posts: 961
Joined: 15 Jun 2012 13:16
Location: Italy, Rome

Re: Complete control of cmd windows

#9 Post by einstein1969 » 04 Oct 2022 09:40

This is at near maximum smoothing capability with standard fonts TERMINAL/RASTER 4x6 with 200x200 chars, zoom 100%

Click on image to view at full resolution.
Image
https://i.imgur.com/Sg9skZi.png

aGerman
Expert
Posts: 4678
Joined: 22 Jan 2010 18:01
Location: Germany

Re: Complete control of cmd windows

#10 Post by aGerman » 04 Oct 2022 09:52

Several registry keys are suggested in the internet. None of them seem to be reliable. At least I didn't find any of them on my laptop. Things like that can be easily found out using PowerShell if you're interested in. However, I'm wondering if the screen size is what you actually need. Wouldn't it be easier to get the maximum console width and height as number of character cells?

Code: Select all

set GetLargestConsoleWindowSize=powershell -nop -ep Bypass -c ^"try{$w=Add-Type -Name WAPI -PassThru -MemberDefinition '^
%=% [DllImport(\"kernel32.dll\")] public static extern int GetLargestConsoleWindowSize(IntPtr hOut);^
%=% [DllImport(\"kernel32.dll\")] public static extern IntPtr GetStdHandle(int idx);';^
%=% exit ($w::GetLargestConsoleWindowSize($w::GetStdHandle(-11)));}catch{exit 0;}^"

%GetLargestConsoleWindowSize%
set /a "X=%errorlevel% & 0xFFFF, Y=(%errorlevel% >> 16) & 0xFFFF"
Steffen

Aacini
Expert
Posts: 1914
Joined: 06 Dec 2011 22:15
Location: México City, México
Contact:

Re: Complete control of cmd windows

#11 Post by Aacini » 04 Oct 2022 10:09

My Window.exe auxiliary program report the window size in pixels; you can download it from this link or directly in the .zip file below.

Code: Select all

@echo off

Window.exe GSize
set /A "width=%errorlevel% & 0xFFFF, height=%errorlevel%>>16"
echo Window size in pixels: %width% X %height%
This is the help text of Window.exe auxiliary program:

Code: Select all

Get or set some values related to console screen window.

Window
Show the window title. At end, return the cmd.exe PID in ERRORLEVEL.

Window Size [width height]
Set window size in characters.
At end, previous window size is returned as width+(height<<16) in ERRORLEVEL.

Window BSize [width height]
Set window buffer size in characters.
At end, previous buffer size is returned as width+(height<<16) in ERRORLEVEL.

Window GSize [MIN|MAX|REST|HIDE|SHOW|FULL]
Set window graphic size or show state.
At end, previous window client-area size in pixels is returned as
width+(height<<16) in ERRORLEVEL. 

Window GPos [x y]
Set window position in pixels.
At end, return previous window position in pixels as x+(y<<16) in ERRORLEVEL.
Window.zip
Window.exe auxiliary program and a couple .BAT example files
(2.95 KiB) Downloaded 593 times

Antonio

einstein1969
Expert
Posts: 961
Joined: 15 Jun 2012 13:16
Location: Italy, Rome

Re: Complete control of cmd windows

#12 Post by einstein1969 » 04 Oct 2022 13:00

aGerman wrote:
04 Oct 2022 09:52
Several registry keys are suggested in the internet. None of them seem to be reliable. At least I didn't find any of them on my laptop. Things like that can be easily found out using PowerShell if you're interested in. However, I'm wondering if the screen size is what you actually need. Wouldn't it be easier to get the maximum console width and height as number of character cells?

Code: Select all

set GetLargestConsoleWindowSize=powershell -nop -ep Bypass -c ^"try{$w=Add-Type -Name WAPI -PassThru -MemberDefinition '^
%=% [DllImport(\"kernel32.dll\")] public static extern int GetLargestConsoleWindowSize(IntPtr hOut);^
%=% [DllImport(\"kernel32.dll\")] public static extern IntPtr GetStdHandle(int idx);';^
%=% exit ($w::GetLargestConsoleWindowSize($w::GetStdHandle(-11)));}catch{exit 0;}^"

%GetLargestConsoleWindowSize%
set /a "X=%errorlevel% & 0xFFFF, Y=(%errorlevel% >> 16) & 0xFFFF"
Steffen
This is good information.

Do you know if it is possible to know the current console size? (the command MODE /STATUS lacks the Vertical dimension, in its place there is the dimension of the buffers)

For the resolution I have find old code too:
for /f "usebackq tokens=1,2 delims= " %%x in (`mshta "javascript:new ActiveXObject('Scripting.FileSystemObject').GetStandardStream(1).Write(screen.width+' '+screen.height);close();noflash"`) do @echo %%xx%%y

einstein1969
Expert
Posts: 961
Joined: 15 Jun 2012 13:16
Location: Italy, Rome

Re: Complete control of cmd windows

#13 Post by einstein1969 » 04 Oct 2022 13:09

Aacini wrote:
04 Oct 2022 10:09
My Window.exe auxiliary program report the window size in pixels; you can download it from this link or directly in the .zip file below.

Code: Select all

@echo off

Window.exe GSize
set /A "width=%errorlevel% & 0xFFFF, height=%errorlevel%>>16"
echo Window size in pixels: %width% X %height%
This is the help text of Window.exe auxiliary program:

Code: Select all

Get or set some values related to console screen window.

Window
Show the window title. At end, return the cmd.exe PID in ERRORLEVEL.

Window Size [width height]
Set window size in characters.
At end, previous window size is returned as width+(height<<16) in ERRORLEVEL.

Window BSize [width height]
Set window buffer size in characters.
At end, previous buffer size is returned as width+(height<<16) in ERRORLEVEL.

Window GSize [MIN|MAX|REST|HIDE|SHOW|FULL]
Set window graphic size or show state.
At end, previous window client-area size in pixels is returned as
width+(height<<16) in ERRORLEVEL. 

Window GPos [x y]
Set window position in pixels.
At end, return previous window position in pixels as x+(y<<16) in ERRORLEVEL.

Window.zip


Antonio
Hi Antonio. :)

Thanks for this contribution, however I am trying to use as little programs as possible outside the standard installed.

aGerman
Expert
Posts: 4678
Joined: 22 Jan 2010 18:01
Location: Germany

Re: Complete control of cmd windows

#14 Post by aGerman » 04 Oct 2022 14:36

Code: Select all

set GetConsoleWindowSize=powershell -nop -ep Bypass -c "$sz=$host.UI.RawUI.WindowSize;exit ($sz.Width -bor ($sz.Height -shl 16));"

%GetConsoleWindowSize%
set /a "X=%errorlevel% & 0xFFFF, Y=(%errorlevel% >> 16) & 0xFFFF"
Steffen

aGerman
Expert
Posts: 4678
Joined: 22 Jan 2010 18:01
Location: Germany

Re: Complete control of cmd windows

#15 Post by aGerman » 05 Oct 2022 03:41

Since loading a PowerShell process is comparatively slow it might be worth to gather all information with only one call.
It took me some minutes to figure out how the macro has to look like for processing in a FOR /F loop. However, finally I succeeded :)

Code: Select all

@echo off &setlocal

set ConsoleInfo=powershell -nop -ep Bypass -c ^"$w=Add-Type -Name WAPI -PassThru -MemberDefinition '^
%===% [DllImport(\"kernel32.dll\"^)] public static extern void GetCurrentConsoleFont(IntPtr hOut,int isMax,int[] info^);^
%===% [DllImport(\"kernel32.dll\"^)] public static extern IntPtr CreateFile(string name,int acc,int share,IntPtr sec,int how,int flags,IntPtr tmplt^);^
%===% [DllImport(\"kernel32.dll\"^)] public static extern void CloseHandle(IntPtr h^);';^
%=% [int[]]$info=0,0;$h=$w::CreateFile('CONOUT$',0xC0000000,2,[IntPtr]::Zero,3,0,[IntPtr]::Zero^);$w::GetCurrentConsoleFont($h,0,$info^);$w::CloseHandle($h^);^
%=% $r=$host.UI.RawUI;$c=$r.WindowSize;$l=$r.MaxPhysicalWindowSize;^
%=% \"cfx^=$($info[1] -band 0xFFFF^)^,cfy^=$(($info[1] -shr 16^) -band 0xFFFF^)^,ccx^=$($c.Width^)^,ccy^=$($c.Height^)^,clx^=$($l.Width^)^,cly^=$($l.Height^)\";^"

for /f %%i in ('%ConsoleInfo%') do set /a "%%i"
echo console font size: %cfx%, %cfy%
echo console current size: %ccx%, %ccy%
echo console largest size: %clx%, %cly%

pause
Steffen

Post Reply