Paragraph.BringIntoView () работает только в фокусе - PullRequest
1 голос
/ 23 октября 2009

Я работаю над текстовым редактором, который основан на RichEditBox. Я реализовал функциональность «Перейти к строке», которая в конечном итоге разрешается в TextPointer.Paragraph.BringIntoView();

Наряду с этим я также устанавливаю позицию каретки. Я обнаружил, что BringIntoView работает только тогда, когда я сначала нажимаю на RichEditBox (фокусирую его) В противном случае это, кажется, игнорируется. Я вижу, что позиция каретки была откорректирована с помощью кода вокруг BringIntoView.

Кто-нибудь знает, в чем причина / природа этой проблемы? Как я могу преодолеть это?

Ответы [ 2 ]

1 голос
/ 13 октября 2013

Нашел обходной путь для этого, не уверенный, будет ли он работать в чистой среде WPF, в моем случае я использую WPF в основном для Windows Forms, используя при необходимости WPF UserControls.

Вместо немедленного вызова BringIntoFocus () отложите его на более поздний момент, добавив в очередь, которая обрабатывается таймером. Например:

System.Windows.Forms.Timer DeferredActionTimer = new System.Windows.Forms.Timer() { Interval = 200 };

Queue<Action> DeferredActions = new Queue<Action>();

void DeferredActionTimer_Tick(object sender, EventArgs e) {
  while(DeferredActions.Count > 0) {
    Action act = DeferredActions.Dequeue();
    act();
  }
}

В конструкторе форм или в событии OnLoad добавьте:

DeferredActionTimer.Tick += new EventHandler(DeferredActionTimer_Tick);
DeferredActionTimer.Enabled = true;

Наконец, вместо прямого вызова TextPointer.Paragraph.BringIntoView();, назовите это так:

DeferredActions.Enqueue(() => TextPointer.Paragraph.BringIntoView());

Обратите внимание, что таймер Windows Forms запускает события в главном потоке (через цикл обработки сообщений). Если вам нужно использовать другой таймер, вам нужно немного дополнительного кода. Я бы порекомендовал вам использовать System.Timers.Timer, а не System.Threading.Timer (он немного более ориентирован на многопоточность). Вы также должны были бы обернуть действие в Dispatcher.Invoke структуру. В моем случае таймер WinForms работает как брелок.

0 голосов
/ 26 октября 2009

Разве вы не можете просто сначала указать фокусировку RichTextBox (?), Используя Keyboard.Focus(richTextBox) или richTextBox.Focus()?

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...