PInvoke를 아시나요?

을 읽다가 공유 드리면 좋을거 같은 정보가 있어서 적습니다.

C/CPP 로 만든 DLL의 구조체나 클래스를 만들어 호출 하는 것을 마샬링이라고 합니다.

MS에서 제공하는 DLL 이 아닌 경우는 직접 마샬링 할수 밖에 없지만
MS에서 제공 하는 API의 경우 다 정해져 있는 상황에서
굳이 내가 그걸 또 마샬링 할 필요가 있을까요? 누군가 만들어 주면
가져다 쓰기만 하면 어떨까요?

네. 이미 있습니다.

해당 프로젝트는 CsWin32 로 변경 되어
더이상 지원 되지 않는다고 나오는데요.

저같은 경우는 예전부터 쓰던거라 익숙함을 버리지 못하고 그냥 쓰고 있습니다.

간단하게 사용법 보여 드리겠습니다. (mvvm이 중요한게 아니니 그냥 비하인드 코드로 작성했습니다.)


User32를 쓸거기 때문에 PInvoke.User32 를 nuget을 추가해 주시고요.

// xaml

<Window
    x:Class="WpfApp1.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    Title="MainWindow"
    Width="200"
    Height="200"
    KeyDown="Window_KeyDown"
    mc:Ignorable="d">
    <Grid>
        <Button Click="Button_Click" Content="Test" />
    </Grid>
</Window>

// cs

using PInvoke;
using System.Runtime.InteropServices;
using System.Windows;
using System.Windows.Input;

namespace WpfApp1;
public partial class MainWindow : Window
{
	public MainWindow()
	{
		InitializeComponent();
	}

	private void Button_Click(object sender, RoutedEventArgs e)
	{
		User32.INPUT input = new User32.INPUT();
		input.type = User32.InputType.INPUT_KEYBOARD;

		input.Inputs.ki.wVk = User32.VirtualKey.VK_A;
		User32.SendInput(1, [input], Marshal.SizeOf(input));

		input.Inputs.ki.dwFlags = User32.KEYEVENTF.KEYEVENTF_KEYUP;
		User32.SendInput(1, [input], Marshal.SizeOf(input));
	}

	private void Window_KeyDown(object sender, KeyEventArgs e)
	{
		MessageBox.Show(e.Key.ToString());
	}
}

동작을 동영상으로 찍었는데 첨부가 안되네요…;;;

보시다 싶이 이미 모든 구조체가 마샬링 되어 있고
값또한 enum으로 잡혀 있어서 쓰기가 매우 편리합니다.

개인적 생각으론 Microsoft.WindowsDesktop.App.WPF 프레임워크에
해당 기능을 넣어 주면 어떨까 싶습니다.

11 Likes

하…이걸 찾고 있었습니다.

ChatGPT 에게도 RECT 같은 그런 자료구조를…시간이 오래 지난만큼 누군가 해뒀거나 공식지원을 해줬을듯한데 모르니까 찾기는 어렵고 물어봐도 정의를 새로 해야한다고 하니…

감사합니다…!!

3 Likes

좋은 내용 감사합니다!!

좋은 샘플 감사합니다. 예전에 Win10 레이아웃 느낌을 내고 싶어서 WinUI 3로 뭐 하나 만들어보고 싶다! 라는 욕구가 들어서 잠깐 PInvoke 사용 시도를 해봤던 적이 있는데, 익숙하지 않아서 그런 지 어떻게 사용해야할 지 막막했었던 안좋은 기억만 있네요.

1 Like

https://www.sysnet.pe.kr/2/0/12540

이 글도 참고하면 좋습니다.

4 Likes

잘 알려진 Win32 API와 구조체들은 감사하게도 Microsoft에서 공식 라이브러리로 만들어 제공해주기 시작해서 아주 편해졌고, COM이나 ActiveX의 경우에는 DLL이나 OCX 안에 들어있는 타입 라이브러리를 해석해서 C# 바인딩을 만들어주는 도구가 닷넷 프레임워크 시절부터 꾸준히 제공되어왔었죠 ㅎㅎ

그리고 Windows 뿐 아니라, 맥의 경우에는 Cocoa 프레임워크에서 실제 앱 개발과 관련이 높은 기능을 따로 추려 Xamarin.Mac / Xamarin.iOS 솔루션의 토대가 되었고, 그게 계승되어서 지금은 MAUI (네. 품질이 물론 아쉽긴 합니다.)까지 이어져 오고 있습니다. ㅎㅎ

상호운용성이라는 주제만 놓고도 닷넷의 매우 깊은 부분까지 파고들면서 이야기할 수 있기 때문에 개인적으로는 이쪽 주제를 매우 좋아합니다. ㅎㅎ

5 Likes

세상에 이런게 있었다니… 감사합니다

1 Like