Заполнение огромной таблицы в приложении SWT / JFace RCP

StackOverflow https://stackoverflow.com/questions/1726331

  •  19-09-2019
  •  | 
  •  

Вопрос

Как бы вы отнеслись к отображению огромного количества строк в таблице SWT?Огромный - это что-то выше 20 тысяч строк, 20 столбцов.Не спрашивайте меня, зачем мне нужно показывать так много данных, дело не в этом.Суть в том, как заставить его работать как можно быстрее, чтобы конечному пользователю не было скучно ждать.Каждая строка отображает экземпляр некоторого объекта, столбцы - это его свойства (некоторые).Я думал использовать шаблон JFace content / label provider, но боюсь, что это будет еще медленнее, чем прямое попадание в таблицу с данными.Вот как это происходит:

    Display.getDefault().asyncExec(new Runnable() {
       public void run() {
           List<MyObject> objects = model.getViewData();
           for(MyObject object: objects){
           TableItem item = new TableItem(table, SWT.NULL);
           item.setImage(0, img1);
           item.setBackground(color1);
               item.setText(0, object.getProperty0());
               item.setText(1, object.getProperty1());
               item.setText(2, object.getProperty2());
               ..... 
            }
       });

Рисование 20 тысяч записей на моем компьютере занимает около 20 секунд.Самая большая проблема с производительностью, которую я видел в Windows, вызвана невероятным количеством собственных оконных сообщений, отправляемых SWT при создании нового элемента таблицы и заполнении его текстом.Я нашел отличное решение для этого - скройте таблицу перед заполнением, а затем покажите ее, когда закончите.Простой вызов table.setVisible(false) перед циклом и table.setVisible(true) после цикла творит чудеса - скорость увеличивается в шесть-семь раз!

Я бы хотел ускорить это еще больше.Что бы вы предложили ?Кроме того, мне интересно, как этот трюк, скрывающий виджет, будет работать в реализациях SWT, отличных от Windows (он же Linux)?

Это было полезно?

Решение

SWT может сделать это за вас.Когда вы используете флаг SWT.VIRTUAL style, элементы создаются только при прокрутке в поле зрения.Вот как это сделать:

  1. Создайте таблицу в стиле SWT.VIRTUAL
  2. Установите количество строк, используя Table#setItemCount()
  3. Добавьте SWT.Прослушиватель setData, который заполняет элементы таблицы по требованию.

Вот фрагмент кода:

public static void main( String[] args ) {
    Display display = new Display();
    Shell shell = new Shell( display );
    shell.setLayout( new FillLayout() );
    final Table table = new Table( shell, SWT.VIRTUAL );
    table.setItemCount( 10000 );
    table.addListener( SWT.SetData, new Listener() {
        public void handleEvent( Event event ) {
            TableItem item = (TableItem)event.item;
            item.setText( "Item " + table.indexOf( item ) );
        }
    } );
    shell.setSize( 300, 500 );
    shell.open();
    while( !shell.isDisposed() ) {
        if( !display.readAndDispatch() ) {
            display.sleep();
        }
    }
    display.dispose();
}

Другие советы

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

Видишь эта статья (Редактировать:упс, я имел в виду эта статья) для примера JFace.

1 - используйте setText(String[]) вместо setText(int, String) одним вызовом вместо нескольких.

2 - используйте myTable.SetRedraw(false) до и myTable.SetRedraw(true) после процесса, чтобы остановить все операции перерисовки во время загрузки данных.

это проще и может повысить производительность!!

удачи.

на моей стороне, используя это, я загружаю 2500 строк по 20 столбцов менее чем за 300 мс.....на стандартном современном ПК.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top