7

2 台のモニター (HP EliteDisplay E190i) があり、どちらも 2 台のコンピューター (2x VGA + DP) に接続されています。
これらのモニターは DVI もサポートしているため、愚かなトグル ボタンの代わりに、コンピューターを切り替えるたびにモニターのメニューをナビゲートする必要があります。私は以前はもっと質素なモニターを使っていて、切り替えはとても簡単でしたが、ナビゲーション全体に慣れることができず、よく混乱してしまいます...

これが取引です-コマンドを実行してコンピューターをすばやく切り替えることができるようにしたいです。明らかに、これを直接実行することはできません (コンピューターは相互に接続されていません) が、モニターが省電力モードになると (または OS がオフになると)、モニターは使用可能な入力のスキャンを開始します。このようにして、他のコンピューターにロックインし、問題を解決します。

十分な紹介ですが、このソリューションを試してみましたが、うまくいきましたが、完璧ではありませんでした:

  • モニターが実際にオフになるまでに数秒かかるフェードアウトアニメーションがありました
  • 上記のフェード アウト アニメーションの間、マウス/キーボードに触れないでください。そうしないと、キャンセルされてしまいます

モニターをスリープ状態にする前にこの回答に従って入力を無効にしてから、5秒後に再度有効にしようとしましたが、次の理由でそれも機能しませんでした:

  • 管理者権限でアプリケーションを実行する必要がありました。そうしないと、入力がブロックされません
  • 管理者権限で実行しているときに入力がブロックされたとしても、フェードアウト アニメーション中にマウスを動かしたり、キーボードのいくつかのキーを押してキャンセルすることができました (ポインターが動かなかったり、キーボード入力が無視されたりしても)。

これが私のコードです:

[DllImport("user32.dll")]
private static extern int SendMessage(int hWnd, int hMsg, int wParam, int lParam);

[DllImport("user32.dll")]
private static extern int BlockInput(int fBlockIt);

static void Main()
{
    SendMessage(0xFFFF, 0x112, 0xF170, 2);
    try
    {
        int result = BlockInput(1);
        Console.WriteLine(result);
        Thread.Sleep(5000);
    }
    finally
    {
        BlockInput(0);
    }
}

両方のコンピューターで Windows 7 Enterprise x64 を使用しています。

この儀式全体を機能させる方法はありますか?

4

1 に答える 1

0

ばかげてあなたの質問を完全に読んでいなかったので、回答を編集する必要がありました。

単純な TCP サーバー/クライアント ソケットを介して相互に要求を送信する両方のコンピューターに常駐するアプリケーションを作成することをお勧めします。

これにより、たとえば、PC 1 のボタンを押してスリープ状態にし、モニターに対して同じことを行い、PC 2 にメッセージを送信してウェイクアップし、モニター入力を盗むことができます。この速度に関しては、いくつかの変数に依存すると思いますが、後で作業することができます。

TCP クライアント/サーバー:

using System;
using System.Net;
using System.Net.Sockets;
using System.Diagnostics;
using System.IO;

namespace ClientSocket_System
  {
   class tcpClientSocket
   {

    #region Global Variables

    TcpClient tcpService;
    IPEndPoint serverEndPoint;
    NetworkStream netStream;

    #endregion


    public void commToServer()
    {
        tcpService = new TcpClient();
        serverEndPoint = new IPEndPoint(IPAddress.Parse("xxx.xxx.xxx.xx"), xxxx); //Enter IP address of computer here along with a port number if needed
        try
        {
            tcpService.Connect(serverEndPoint);
            netStream = tcpService.GetStream();
            ASCIIEncoding encoder = new ASCIIEncoding();
            byte[] buffer = encoder.GetBytes("SwitchComputers");
            netStream.Write(buffer, 0, buffer.Length);
            netStream.Flush();
            tcpService.Close();
        }
        catch(Exception ex)
        {
        }
    }
   }
}

そしてサーバー:

using System.Net;
using System.Net.Sockets;
using System.Diagnostics;
using System.IO;

namespace ClientSocket_System
{
    class tcpServerTerminal
    {



        private TcpListener tcpListener;
        private Thread listenThread;
        private TcpClient tcpService;
        string msgFromClient;



        public void ServerStart()
        {
            tcpListener = new TcpListener(IPAddress.Any, 5565);
            listenThread = new Thread(new ThreadStart(ListenForClients));
            listenThread.Start();
        }

        public void ListenForClients()
        {
            tcpListener.Start();

            while (true)
            {
                //blocks until a client has connected to the server
                TcpClient client = this.tcpListener.AcceptTcpClient();

                //create a thread to handle communication 
                //with connected client
                Thread clientThread = new Thread(new ParameterizedThreadStart(HandleClientComm));
                clientThread.Start(client);
            }
        }

        public void HandleClientComm(object client)
        {
            tcpService = (TcpClient)client;

            NetworkStream netStream = tcpService.GetStream();

            byte[] message = new byte[4096];
            int bytesRead;

            while (true)
            {
                bytesRead = 0;

                try
                {
                    //blocks until a client sends a message
                    bytesRead = netStream.Read(message, 0, 4096);
                }
                catch
                {
                    //a socket error has occured
                    break;
                }

                if (bytesRead == 0)
                {
                    //the client has disconnected from the server
                    break;
                }

                //message has successfully been received
                ASCIIEncoding encoder = new ASCIIEncoding();

                msgFromClient = encoder.GetString(message, 0, bytesRead);

                if (msgFromClient == "SwitchComputers")
                {

                    //RUN CODE HERE TO ACTION PC SLEEP AND MONITOR SLEEP

                    msgFromClient = null;
                }
            }
        }

        public void SocketSend()
        {
            NetworkStream streamToClient = tcpService.GetStream();
            ASCIIEncoding encoder = new ASCIIEncoding();
            byte[] buffer = encoder.GetBytes("SwitchComputers");

            streamToClient.Write(buffer, 0, buffer.Length);
            streamToClient.Flush();
        }

    }
}

少なくとも検討する価値があるかもしれませんが、上記のコードは正確には洗練されていませんが、ホームネットワークを介して両方のコンピューターのアクションを制御し、特定のコマンドを同時に実行できるようにすることができます:スリープ/ウェイクなど.

これにより、調査の新しい方向性が得られることを願っています。

また、入力をブロックするためのコードを次のようにフォーマットするのがベストプラクティスだと思います。

[return: MarshalAs(UnmanagedType.Bool)]
[DllImport("user32.dll", CharSet=CharSet.Auto, ExactSpelling=true)]
public static extern bool BlockInput([In, MarshalAs(UnmanagedType.Bool)] bool fBlockIt);
于 2016-03-16T12:00:13.847 に答える