dotnet / pinvoke

A library containing all P/Invoke code so you don't have to import it every time. Maintained and updated to support the latest Windows OS.
MIT License
2.12k stars 222 forks source link

Make Kernel32::ReadConsoleOutput can read more than one CHAR_INFO. #589

Closed aaasoft closed 2 years ago

aaasoft commented 2 years ago

Kernel32::ReadConsoleOutput's second parameter[out PInvoke.Kernel32.CHAR_INFO lpBuffer] can only get one PInvoke.Kernel32.CHAR_INFO。So I add a method change second parameter to System.IntPtr.Now we can read more than one CHAR_INFO at a time.

Read Console Output Sample:

using PInvoke;
using System.Diagnostics;
using System.Runtime.InteropServices;
using System.Text;
using static PInvoke.Kernel32;

short MAX_READ_LINES = 10;
var hOut = GetStdHandle(StdHandle.STD_OUTPUT_HANDLE);
CONSOLE_SCREEN_BUFFER_INFO csbi;
if (!GetConsoleScreenBufferInfo(hOut, out csbi))
{
    Console.WriteLine("GetConsoleScreenBufferInfo Failed!");
    return;
}
IntPtr hBuffer = Marshal.AllocHGlobal(Marshal.SizeOf<CHAR_INFO>() * csbi.dwSize.X * MAX_READ_LINES);
SMALL_RECT smallRect = new SMALL_RECT() { Right = csbi.dwSize.X, Bottom = MAX_READ_LINES };
if (!PInvoke.Kernel32.ReadConsoleOutput(
    hOut, hBuffer,
    new COORD() { X = csbi.dwSize.X, Y = MAX_READ_LINES },
    new COORD() { X = 0, Y = 0 }, ref smallRect))
{
    Console.WriteLine($"ReadConsoleOutput Failed!csbi.dwSize.X:{csbi.dwSize.X},csbi.dwSize.Y:{csbi.dwSize.Y}");
    return;
}
StringBuilder sb = new StringBuilder();
for (var i = 0; i < csbi.dwSize.X * MAX_READ_LINES; i++)
{
    var charInfo = Marshal.PtrToStructure<CHAR_INFO>(hBuffer);
    sb.Append(charInfo.Char.UnicodeChar);
    hBuffer += Marshal.SizeOf<CHAR_INFO>();
}
Console.WriteLine("Console Content:" + sb.ToString());
dnfadmin commented 2 years ago

CLA assistant check
All CLA requirements met.

AArnott commented 2 years ago

Thank you for reporting the bug and offering a fix. Rather than hand-author multiple overloads we use [FriendlyFlags] to do this. I'm closing this PR but please take a look at #591 for an adaptation of your fix that should resolve the issue you ran into.

aaasoft commented 2 years ago

Thank you for reporting the bug and offering a fix. Rather than hand-author multiple overloads we use [FriendlyFlags] to do this. I'm closing this PR but please take a look at #591 for an adaptation of your fix that should resolve the issue you ran into.

Very good.[FriendlyFlags] is better.🤝