Медленное WPF Textbox - PullRequest
       13

Медленное WPF Textbox

3 голосов
/ 19 ноября 2010

Я занимаюсь разработкой простого средства просмотра последовательных данных, которое будет использоваться для наблюдения за данными, передаваемыми на один из последовательных портов компьютера. Я написал тестовое приложение с использованием C # и WPF; он просто помещает последнюю прочитанную строку в текстовый блок. Тем не менее, он пропускает все остальные строки. Моя теория состоит в том, что новые данные помещаются в текстовый блок до того, как WPF отобразит окно. Тем не менее, я попробовал каждую комбинацию приоритетов потоков, которую только могу себе представить, и, в лучшем случае, приложение отображает все остальные строки; в худшем случае он показывает каждые 20 строк.

Я работаю на многоядерном компьютере. Мое приложение состоит из текстового блока и кнопки, чтобы открыть / закрыть порт. (Я попытался заменить текстовый блок текстовым полем, и я наблюдаю ту же проблему)

Мой обработчик данных :

private void MainWindow_DataReceived(object sender, System.IO.Ports.SerialDataReceivedEventArgs e)
{
    string message = sp.ReadLine();
    if (string.IsNullOrWhiteSpace(message))
        return;

    this.Dispatcher.BeginInvoke(DispatcherPriority.Send, (ThreadStart)delegate()
    {
        text.Text = message;
        this.InvalidateVisual();
    });
}

Наивысшим приоритетом для этого приложения является обработка устойчивой пропускной способности большого количества данных; уместен ли WPF в этой ситуации? Если это так, что я делаю не так?

Ответы [ 2 ]

3 голосов
/ 19 ноября 2010

Один из продуктов моей компании отображает "почти в реальном времени" обновления данных с сервера, и есть несколько вещей, которые вы можете попробовать ....

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

вы можете сделать это так:

добавить свойство зависимости:

public static readonly DependencyProperty MessageTextProperty = 
    DependencyProperty.Register("MessageText", typeof(string), typeof(MyWidowClass), 
    new UIPropertyMetadata(string.Empty));

        public string MessageText
        {
            get { return (int)GetValue(MessageTextProperty ); }
            set { SetValue(MessageTextProperty , value); }
        }

в текстовом поле xaml:

<TextBox Text="{Binding Path=MessageText, ElementName=xNameOfMyWindow}"/>

где xNameOfMyWindow - атрибут x: Name вашего оконного тега

теперь ваш код будет выглядеть так:

private void MainWindow_DataReceived(object sender, System.IO.Ports.SerialDataReceivedEventArgs e)
{
    string message = sp.ReadLine();
    if (string.IsNullOrWhiteSpace(message))
        return;
    this.MessageText = message;
}
2 голосов
/ 06 марта 2015

Я понимаю, что это действительно поздно для игры здесь, но после борьбы с этой проблемой в течение месяца я наткнулся на источник своих проблем с медленным обновлением текстового поля:

Отключение переноса текста полностью устранило проблему блокировки пользовательского интерфейса:

TextWrapping = "Nowrap"

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

Надеюсь, это поможет.

...