jasonpang / Interceptor

C# wrapper for a Windows keyboard driver. Can simulate keystrokes and mouse clicks in protected areas like the Windows logon screen (and yes, even in games). Wrapping http://oblita.com/Interception
MIT License
286 stars 84 forks source link

Updated to work with .Net 5.0 (Abort is obsolete), Along with other random changes/fixes. #23

Open kevinf100 opened 2 years ago

kevinf100 commented 2 years ago

Also pull request #5 Since abort is no longer in .net 5.0, if we remove the abort the thread throws an exception when the driver is unloaded. Instead we can flag we unloaded and check if we unloaded. Also I think this exception was unreachable before. If for some reason we leave the while loop we call Unload which than kills itself.

kevinf100 commented 2 years ago

Also did fixes.

kevinf100 commented 2 years ago

22 Should be fixed.

21 Fixed.

20 Should be fixed from fixing #21. (Needs more testing)

10 Fixed.

DThomas44 commented 2 years ago

@kevinf100 Placing this here since I can't seem to find issues tab on your fork.

Running your version, this is working in Windows 11 with 1 oddity I have found: After the first call to SendText(), the next call will be delayed until some physical input is detected (mouse or keyboard).

Messages that are queued up execute once per physical input received. For example, if I send 6 messages, the first will send, then if I press a physical key, message 2 will print on key down, message 3 on key up, etc. until all sent messaged are printed.

I have KeyboardFilterMode set to All & do not have a MouseFilterMode set at all, as I only want to deal with sending keys in my use case.

As I'm writing a remote input application, there may not be any physical input happening on the target machine.

kevinf100 commented 2 years ago

@DThomas44

using System;
using System.Threading;
using Interceptor;

namespace InterSwap
{
    class Program
    {
        static void Main(string[] args)
        {
            // Tell the driver to capture all input.
            var input = new Input
            {
                //MouseFilterMode = MouseFilterMode.All,
                KeyboardFilterMode = KeyboardFilterMode.All
            };

            input.Load();
            Thread.Sleep(2000);
            for (var i = 0; i < 10; i++)
            {
                Console.WriteLine($"Test{i}");
                input.SendText($"Test{i}");
                input.SendKey(Keys.Enter);
                Thread.Sleep(1000);
            }
            input.Unload();

            Console.WriteLine("Done!");
        }

    }
}

Using this and not touching mouse or keyboard SendKey works just fine and does all 10 inputs. Might be possible your PC default _keyBoardId is not 2. Try finding that and change that yourself.. After one real keyboard press I saved it and reuse it until it gets a new keyboard input. Perhaps the new default not working?

Edit - Testing a bit more and looking around, I don't see why it would be stalling until a keyboard press. Default detecting is working and changing.

DThomas44 commented 2 years ago

Thank you for checking. Turns out my application flow was off. I still don't understand what the actual cause of the issue was, but after moving stuff around a bit, everything is working as expected. As this is my first real shot at using C#, no real surprise there.

kevinf100 commented 2 years ago

Thank you for checking. Turns out my application flow was off. I still don't understand what the actual cause of the issue was, but after moving stuff around a bit, everything is working as expected. As this is my first real shot at using C#, no real surprise there.

My best guess is something to do with a new thread being made when the library loads that just on an infinite loop. Sounds like whenever that loop loops (when a mouse or keyboard input is received.) your whole program resumes. Not sure what is going on, but this uses the lower level Thread and not TaskFactory.