shestakov / Kilo

A keyboard layout indicator for Windows 7+
29 stars 6 forks source link

Перехват языка подсветка панели задач при работе по RDP #6

Open artyompetrov opened 4 years ago

artyompetrov commented 4 years ago

Вообще инструментом я перестал пользоваться, т.к. большую часть времени работаю на удаленных машинах по rdp, а на все удаленные машины Kilo не поставишь. Коллеги как считаете, возможно ли каким либо образом влиять на происходящее внутри rdp сессии? Ну или какой костыль можно придумать чтобы решить эту проблему? Есть у кого-нибудь идеи?

zapominai commented 4 years ago

Я решил эту проблему так: вывел программно на экран индикацию, которую точно не пропустишь и увидишь даже при удалённом подключении, при этом она не мешает работе.

Так это выглядит: image прозрачный розовый квадрат в центре означает, что сейчас включена русская раскладка. При этом сквозь него можно кликать он не перекрывает элементы управления.

В настройках можно задать интенсивность прозрачности, цвет и размер области: image

Плюс к этому, на всех машинах где работаю, всё же установил свою программу, чтобы цвет панели задач тоже менялся при переключении раскладки.

А ещё я научился программно, через iaccessible, считывать состояние стандартного виндовского индикатора, теперь могу получать верную текущую раскладку в любых приложениях, ролик про это.

artyompetrov commented 4 years ago

Похоже что-то рисовать поверх экрана это единственный способ. Думаю рамка по краям экрана в 1-2 пикселя будет весьма заметна, при этом не будет находится в рабочей области. А прямоугольник каким методом рисуется? Нашел несколько методов, и не один мне не понравился пока, везде какие-то сайдэффекты. https://stackoverflow.com/questions/14385838/draw-on-the-screen-without-a-form тут описано два метода, метод один протестировал - рисунок затирается другими программами при их перерисовке, по таймеру рисовать не получается, все мигает на экране.

zapominai commented 4 years ago

У меня сделано через обычную Form, с особыми стилями и настройками. Пробовал рисовать без них, так же столкнулся с миганием и перекрытием другими апликухами. С формами начал возиться после того, как упёрся, что для корректной отрисовки нужно вешать хук на событие перерисовки окна. А после неработающего хука на переключение раскладки уже не доверяю им.

        public partial class ColorForm : Form
        internal static ColorForm init(Boolean setParent = true)
        {
            var _colorForm = new ColorForm();
            _colorForm.ShowInTaskbar = false;
            NativeMethods.EnableWindow(_colorForm.Handle, false);

            int style = NativeMethods.GetWindowLong(_colorForm.Handle, NativeConstants.GWL_STYLE);
            int styleEx = NativeMethods.GetWindowLong(_colorForm.Handle, NativeConstants.GWL_EXSTYLE);

            NativeMethods.SetWindowLong(_colorForm.Handle, NativeConstants.GWL_STYLE, style & ~NativeConstants.WS_CAPTION & ~NativeConstants.WS_SIZEBOX);
            NativeMethods.SetWindowLong(_colorForm.Handle, NativeConstants.GWL_EXSTYLE, styleEx | NativeConstants.WS_EX_TOOLWINDOW); // hide from alt + tab

            // Show in minimaze desktop state (win+D)
            if (setParent)
            {
                IntPtr nWinHandle = NativeMethods.FindWindowEx(IntPtr.Zero, IntPtr.Zero, "Progman", null);
                nWinHandle = NativeMethods.FindWindowEx(nWinHandle, IntPtr.Zero, "SHELLDLL_DefView", null);
                NativeMethods.SetParent(_colorForm.Handle, nWinHandle);
            }
           // ...
                    var flyForm = ColorForm.init(false);
                    flyForm.FormBorderStyle = FormBorderStyle.None;
                    flyForm.TopMost = true;
                    foreach (var item in flyForms.Select((value, index) => new { Value = value, Index = index }))
                    {
                        var tform = item.Value;
                        tform.BackColor = colors[currentIndex];
                        var color1 = colors[currentIndex];
                        int iCol1 = (color1.A + 1 << 24) | (color1.B << 16) | (color1.G << 8) | color1.R;
                        tform.TransparencyKey = Color.FromArgb(iCol1);

                        var opacity = (Double)Settings.Default.flyTrancparency / 100;
                        tform.Opacity = opacity;
artyompetrov commented 4 years ago

для корректной отрисовки нужно вешать хук на событие перерисовки окна

Я подумал про это, надо будет как-то для общего развития протестировать рисование на экране без windows форм.

Спасибо за примеры, надеюсь руки дойдут закоммитить новые функции в данный репозиторий.