Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Making a WPF window click-through, but not its controls

Tags:

c#

wpf

winapi

First of all I want to define what I mean by transparent to clicks in the text bellow: It means the clicks go through my window without any processing, directly to whichever window is bellow it. I need this behaviour because this application is meant to be an overlay over a game.

I searched the questions relating to making a window transparent to clicks. I was wondering if there was a way to make the window itself to be transparent to clicks, but not its controls (such as text boxes and buttons).

Here is the markup for the window:

<Window x:Class="QuestBrowser.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="Quest Browser"
        Height="350" Width="525"
        AllowsTransparency="True" WindowStyle="None" Topmost="True">
    <Window.Background>
        <SolidColorBrush Color="White" Opacity="0.1"/>
    </Window.Background>
    <Grid>
        <Grid.RowDefinitions>
            <RowDefinition/>
            <RowDefinition/>
        </Grid.RowDefinitions>
        <TextBox Name="inputTxtBox"></TextBox>
    </Grid>
</Window>

And bellow is the code that makes the window transparent to clicks (pretty much copy-pasted from other question, because I'm not good at all at low level Windows programming).

namespace Win32Utils
{
    public static class WindowHelper
    {
        const int WS_EX_TRANSPARENT = 0x00000020;
        const int GWL_EXSTYLE = (-20);

        public static void SetWindowExTransparent(IntPtr hwnd)
        {
            var extendedStyle = GetWindowLong(hwnd, GWL_EXSTYLE);
            SetWindowLong(hwnd, GWL_EXSTYLE, extendedStyle | WS_EX_TRANSPARENT);
        }
    }
}

The method WindowHelper.SetWindowExTransparent is called from within my override of the method Window.OnSourceInitialized (as instructed in the post where I got the code for a transparent window from):

protected override void OnSourceInitialized(EventArgs e)
{
    base.OnSourceInitialized(e);
    var hwnd = new WindowInteropHelper(this).Handle;
    WindowHelper.SetWindowExTransparent(hwnd);
}

This does make the window transparent to clicks, but all controls I put into it are transparent as well (for example, the TextBox). Is there a way to make the Window surface transparent to clicks, but ensure the TextBox still receives mouse and keyboard input normally?

I wanted to avoid mouse and keyboard hooks for both user privacy reasons and because, as I said, I don't understand much about the Windows API. If hooks are the only way, I would really appreciate a "For Dummies"-style explanation on how they work.

like image 395
FinnTheHuman Avatar asked Dec 29 '15 11:12

FinnTheHuman


1 Answers

Can you try this

<Window x:Class="WpfApplication1.Window1"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="Window1"
        Height="300"
        Width="300"
        AllowsTransparency="True"
        WindowStyle="None" >
    <Window.Background>
        <SolidColorBrush Color="#FFB0B0B0"
                         Opacity="0.05" />
    </Window.Background>
    <Grid>
        <Button Content="Button"
                HorizontalAlignment="Left"
                Margin="39,125,0,0"
                VerticalAlignment="Top"
                Width="75" />
        <Label Content="Label"
               HorizontalAlignment="Left"
               Margin="114,50,0,0"
               VerticalAlignment="Top" />
        <TextBox HorizontalAlignment="Left"
                 Height="23"
                 Margin="101,201,0,0"
                 TextWrapping="Wrap"
                 Text="TextBox"
                 VerticalAlignment="Top"
                 Width="120" />

    </Grid>
</Window>

What It basically does Is create a transparent window.(Click through and Invisble). But controls are visible and not-click through. Or you can try How to create a semi transparent window in WPF that allows mouse events to pass through

like image 155
AEonAX Avatar answered Oct 20 '22 01:10

AEonAX