Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > .NET Frameworks (точка нет фреймворки) > Общие вопросы .NET
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 04.04.2010, 22:23   #1
Casper-SC
Форумчанин
 
Регистрация: 04.07.2007
Сообщений: 549
По умолчанию Горячие клавиши. Не ясно как реализовать?

Вот нашёл в интернете такой класс, но что-то я вообще не въезжаю как им пользоваться, нет ну кое-что понимаю, но в целом картина не построилась:
Код:
using System;
using System.Diagnostics;
using System.Windows.Forms;
using System.Runtime.InteropServices;

namespace WindowsFormsApplication1
{


    class Hooks
    {
        private const int WH_KEYBOARD_LL = 13;
        private const int WM_KEYDOWN = 0x0100;
        private static LowLevelKeyboardProc _proc = HookCallback;
        private static IntPtr _hookID = IntPtr.Zero;

        private static IntPtr SetHook(LowLevelKeyboardProc proc)
        {
            using (Process curProcess = Process.GetCurrentProcess())
            using (ProcessModule curModule = curProcess.MainModule)
            {
                return SetWindowsHookEx(WH_KEYBOARD_LL, proc, GetModuleHandle(curModule.ModuleName), 0);
            }
        }

        private delegate IntPtr LowLevelKeyboardProc(int nCode, IntPtr wParam, IntPtr lParam);

        private static IntPtr HookCallback(int nCode, IntPtr wParam, IntPtr lParam)
        {
            if ((nCode >= 0) && (wParam == (IntPtr)WM_KEYDOWN))
            {
                int vkCode = Marshal.ReadInt32(lParam);
                if (((Keys)vkCode == Keys.LWin) || ((Keys)vkCode == Keys.RWin))
                {
                    //Console.WriteLine("{0} blocked!", (Keys)vkCode);
                    return (IntPtr)1;
                }
            }
            return CallNextHookEx(_hookID, nCode, wParam, lParam);
        }

        [DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
        private static extern IntPtr SetWindowsHookEx(int idHook, LowLevelKeyboardProc lpfn, IntPtr hMod, uint dwThreadId);

        [DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
        private static extern bool UnhookWindowsHookEx(IntPtr hhk);

        [DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
        private static extern IntPtr CallNextHookEx(IntPtr hhk, int nCode, IntPtr wParam, IntPtr lParam);

        [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
        private static extern IntPtr GetModuleHandle(string lpModuleName);
    }

}
    //Пример использования
        //public static void Main()
        //{
        //    _hookID = SetHook(_proc);
        //    Application.Run();
        //    UnhookWindowsHookEx(_hookID);
        //}
Находил на КодПроджект.ком примеры, но в них нельзя поставить как горячую клавишу PrintScreen, кстати нужны все возможные комбинации, не только эта кнопка. Или может я не в ту степь пошёл и хуки мне не нужны? А в этом примере, что выше вообще ничё не ясно, где там эти самые клавиши и т.д. Может кто нибудь помочь? Может у кого есть класс готовый и ему не жалко его выложить?
Я даже хотел бы сам научиться API функции использовать, но не видел нормального учебника на русском расчитанного не на телепатов.
Casper-SC вне форума Ответить с цитированием
Старый 04.04.2010, 23:58   #2
dampirik
Форумчанин
 
Регистрация: 02.07.2009
Сообщений: 722
По умолчанию

Ну а Keys.PrintScreen чем плоха? считываете данные с клавиатуры если нажата кнопка PrintScreen то тото....
dampirik вне форума Ответить с цитированием
Старый 05.04.2010, 00:25   #3
Casper-SC
Форумчанин
 
Регистрация: 04.07.2007
Сообщений: 549
По умолчанию

Oo Ничего себе, как это я не заметил... Видимо я или не тот класс смотрел и запомнил, что в Keys нету PrintScreen (где-то я видел, там вообще мало кнопок можно было выбрать).
Casper-SC вне форума Ответить с цитированием
Старый 05.04.2010, 00:28   #4
dampirik
Форумчанин
 
Регистрация: 02.07.2009
Сообщений: 722
По умолчанию

В Keys входят все стандартные кнопки)) главное правильно обратиться...
dampirik вне форума Ответить с цитированием
Старый 05.04.2010, 00:36   #5
Casper-SC
Форумчанин
 
Регистрация: 04.07.2007
Сообщений: 549
По умолчанию

Щас буду колдовать над классом, так, чтобы можно было менять кнопки в зависимости от моих настроек и использовать из любого места программы, пока что я всего навсего поменял некоторые модификаторы доступа на public и теперь использовать можно так:
Код:
//установить хук
Hooks._hookID = Hooks.SetHook(Hooks._proc);
Код:
//убрать хук
Hooks.UnhookWindowsHookEx(Hooks._hookID);
Но что-то не нравиться мне такой способ, как то наперекосяк получается

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

Последний раз редактировалось Casper-SC; 05.04.2010 в 00:40.
Casper-SC вне форума Ответить с цитированием
Старый 05.04.2010, 00:53   #6
dampirik
Форумчанин
 
Регистрация: 02.07.2009
Сообщений: 722
По умолчанию

А что вообще хочешь сделать?
dampirik вне форума Ответить с цитированием
Старый 05.04.2010, 01:26   #7
Casper-SC
Форумчанин
 
Регистрация: 04.07.2007
Сообщений: 549
По умолчанию

Короче таймер проверяет каждую секунду список "будильников" (скажем так). Когда жму горячую клавишу, делается скриншот. Допустим будильнику нужно сработать в 12:00, я 5 раз нажал горячую клавишу, пока 5 скриншотов делаются и сохраняются, уже 12:01 и будильник не срабатывает. Тут конечно можно добавить в проверку последнюю дату/время срабатывания, и если текущее системное время уже больше, того, что установлено в будильнике как время срабатывания и дата/время последнего срабатывания не равно установленному на срабатывание, то всё равно сработать. Но это стока всего писать придётся, у меня там 6 замудрённых режимов.

А при нормальном срабатывании, просто присваивать lastAlarm = timeAlarm; как-то так. Вообще это выход или всё таки лучше в отдельных потоках фоткать экран?

Последний раз редактировалось Casper-SC; 05.04.2010 в 01:28.
Casper-SC вне форума Ответить с цитированием
Старый 05.04.2010, 11:46   #8
dampirik
Форумчанин
 
Регистрация: 02.07.2009
Сообщений: 722
По умолчанию

Мне кажется Вы очень сильно усложняете поставленную перед вами задачу...
Есть стандартный таймер у него есть инвент инвент тик... время тика настраиваеться...
В него и вводим проверку ваших будильников их старт если что не так... или стоп стоп можно организовать по флугу если он равен 5
Флаг же выставляеться при нажатиии на кнопку, один раз флаг+1...
ну как-то так...
dampirik вне форума Ответить с цитированием
Старый 05.04.2010, 16:11   #9
Casper-SC
Форумчанин
 
Регистрация: 04.07.2007
Сообщений: 549
По умолчанию

Ну в общем я так и делаю.
Код:
        //таймер проверяет все включённые будильники в списке на срабатывание
        void timerCheckTime_Tick(object sender, EventArgs e)
        {
            for (int i = 0; i < this.listViewAlarm.Items.Count; i++) //прогоняем на проверку весь список
            {
                if (((AlarmClock)this.listViewAlarm.Items[i].Tag).EnabledAlarmClock) //если включён
                {
                    if (((AlarmClock)this.listViewAlarm.Items[i].Tag).CheckAlarmClock()) //проверяем будильник на срабатывание
                    {
                        this.listViewAlarm.Items[i].SubItems[1].Text = 
                            ((AlarmClock)this.listViewAlarm.Items[i].Tag).NextDate;
                        CreateMessageSignal(i);
                    }
                }
            }
            Application.DoEvents();
        }
Он работает каждую секунду. Я чуть-чуть перепутал, 12:00:00, делаю 5 скриншотов, а уже 12:00:01 и всё уже не сработал будильник, так как всё процессорное время скушали скриншоты и ровно в 12 таймер просто не успел проверить. Вот про что я.

Цитата:
Флаг же выставляеться при нажатиии на кнопку, один раз флаг+1...
ну как-то так...
А вот это, что - то не понятна мысль, про что речь конкретно?

Последний раз редактировалось Casper-SC; 05.04.2010 в 16:14.
Casper-SC вне форума Ответить с цитированием
Старый 05.04.2010, 18:46   #10
dampirik
Форумчанин
 
Регистрация: 02.07.2009
Сообщений: 722
По умолчанию

Ну смотри на "делание" скриншотов... можно выделить поток но смысла...они будут вставать в очередь и все... и те через час работы у тебя комп помрет...... возможно стоит оптимизировать сриншоты... создать аналог своей функции...
dampirik вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Горячие клавиши. Lazio Помощь студентам 2 08.09.2010 02:20
Как заблокировать горячие клавиши Alt+F11 kovalevskivf Microsoft Office Excel 2 20.05.2009 11:26
Как назначить "горячие" клавиши ekzobyte Общие вопросы Delphi 16 18.03.2009 21:15
Горячие клавиши Altera Общие вопросы Delphi 5 13.09.2008 21:27