Отправить нажатие клавиши на другой элемент управления

Легкий для вас, ребята.

У меня есть текстовое поле поверх списка.

Текстовое поле используется для фильтрации данных в списке.

Итак... Когда пользователь вводит текстовое поле, я хотел бы «ловить» нажатия клавиш вниз/вверх/pagedown/pageup и перенаправлять их в список.

Я знаю, что могу использовать Win32 API и отправить сообщение WM_KeyDown. Но для этого должен быть какой-то способ .NET.


person vIceBerg    schedule 12.08.2009    source источник
comment
Выбранный лучший ответ не является лучшим решением во всех ситуациях! См. ответ SendMessage() ниже.   -  person schlebe    schedule 05.05.2020


Ответы (4)


Метод SendKeys.Send().

 private void textBox1_KeyPress(object sender, KeyPressEventArgs e)
        {
            listBox1.Focus();
            SendKeys.Send(e.KeyChar.ToString());
        }

Вот код, с помощью которого вы можете выбрать элемент списка.

private void Form1_Load(object sender, EventArgs e)
        {
            textBox1.AutoCompleteMode = AutoCompleteMode.SuggestAppend;
            textBox1.AutoCompleteSource=AutoCompleteSource.CustomSource;
            string[] ar = (string[])(listBox1.Items.Cast<string>()).ToArray<string>();
            textBox1.AutoCompleteCustomSource.AddRange(ar);
        }
        private void textBox1_TextChanged(object sender, EventArgs e)
        {
            listBox1.Text  = textBox1.Text;
        }
person kv-prajapati    schedule 12.08.2009
comment
Как мне сообщить SendKeys.Send, чтобы отправить нажатие клавиши элементу управления списком? - person vIceBerg; 12.08.2009
comment
И если я хочу, чтобы фокус оставался в текстовом поле, я делаю textbox.focus() сразу после этого? Странно, что у sendkey нет перегрузки для передачи ему управления... - person vIceBerg; 12.08.2009

Вы можете использовать привязку данных

            listBox1.DataBindings.Add("DataSource", textBox1, "Text", true, DataSourceUpdateMode.OnPropertyChanged).
            Format += (sender, e) =>
            {
                e.Value = _strings.FindAll(s => s.StartsWith((string) e.Value));
            };
person Jacob Seleznev    schedule 12.08.2009
comment
Привязка данных для отправки нажатия клавиши другому элементу управления?? - person vIceBerg; 12.08.2009
comment
Нет, чтобы отфильтровать данные в списке. Если вы привязываете свойство Text текстового поля к свойству DataSource списка и используете DataSourceUpdateMode.OnPropertyChanged, вы можете добиться этого. - person Jacob Seleznev; 12.08.2009
comment
О... Я думаю, я не могу этого сделать. Поскольку элементы списка уже заполнены списком‹›, привязанным к свойству источника данных... - person vIceBerg; 12.08.2009
comment
Вам нужно каким-то образом отфильтровать содержимое списка в событии Format для привязки. - person Jacob Seleznev; 12.08.2009

В нашем приложении wpf у нас есть текстовое поле, которое фильтрует список, мы используем событие previewkeyup. Внутри кода мы можем проверить, какая клавиша была нажата (не держите мой код передо мной, это что-то вроде e.Key == Key.UpArrow, в любом случае для этого есть встроенный класс в C#). Если это одна из горячих клавиш, мы соответствующим образом манипулируем пользовательским элементом управления.

Для списка мы поместили его в пользовательский элемент управления и реализовали интерфейс, назвали его NavigateableListbox или что-то в этом роде, заставили его реализовать MoveUp(), MoveDown(), PageUp(), PageDown() и т. д., поэтому событие текстового поля просто сообщает, если e.Key = Key.UpArrow {mylistbox.MoveUp()}

person Eric    schedule 12.08.2009

Метод SendKeys.Send() работает не во всех ситуациях, потому что метод Send() может быть адресован другому элементу управления !

В 2020 году лучшее решение, чтобы быть уверенным на 100%, — это использовать функцию SendMessage().

В VB.Net я использую следующий код

Public Declare Auto Function SendMessage Lib "user32.dll"
    ( ByVal hWnd As IntPtr
    , ByVal wMsg As Int32
    , ByVal wParam As Int32
    , ByVal s As Int32
    ) As Int32

Private Const WM_CHAR As Int32 = &H102

SendMessage(txtInput.Handle, WM_CHAR, AscW(sValue.Chars(0)), 0)

Где txtInput — образец Textbox элемента управления.

В моем случае я нажимаю на элемент html <div>, определенный в элементе управления WebView, который меняет цвет, когда я нажимаю на него или когда перемещаю мышь. Когда я нажимаю на этот <div>, вызывается метод ScriptNotify() VB.Net для ввода некоторых символов в Textbox с помощью функции SendMessage().

Я думаю, что в старом решении иногда WebView получает фокус до вызова метода SendKeys.Send(), поэтому распространяемый ключ не отправляется в txtInput Textbox.

Вы можете использовать старое решение, но будьте уверены, что однажды функция SendKeys.Send() отправит то, что вы хотите, другому дескриптору.

person schlebe    schedule 05.05.2020