Обновить представление Eclipse 4 RCP при завершении работы мастера

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

Желаемое поведение похоже на то, как представление проводника пакетов eclipse обновляется после создания нового проекта.

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

MPart ingredientsView = partService.showPart("com.personal.recipes.part.ingredientsview", PartState.ACTIVATE); 
IngredientsView iv = (IngredientsView) ingredientsView.getObject(); 
iv.updateView();

Хотя это работает в других местах, при вызове из мастера «partService» имеет значение null, а приложение NPE отсутствует.

Итак, каков запрещенный метод принудительного обновления представлений e4 после изменения их содержимого?

РЕДАКТИРОВАТЬ: я пытался использовать ContextInjectionFactory, как @greg-449 показал в своем ответе, но я не уверен, где его разместить в моем коде или как определить контекст. Я запускаю мастер с кнопки на панели инструментов и помещаю в свой обработчик следующий код:

    @Execute
public void execute(Shell shell) {
    IEclipseContext context = EclipseContextFactory.create();
    IWizard ingredientWizard = ContextInjectionFactory.make(IngredientWizard.class, context);

    WizardDialog wizardDialog = new WizardDialog(shell, ingredientWizard);
    wizardDialog.open();
    }

Однако, когда я попытался получить услугу детали с помощью @Inject EPartService partService; Я получил InjectionException, в котором говорится, что ошибок не обнаружено.

Как только инъекция станет доступной, использование EventBroker выглядит как выход.


person BiggPlanet    schedule 21.05.2014    source источник


Ответы (2)


Внедрение выполняется только в объекты, о которых знает модель приложения. Таким образом, это не делается в Wizards или Dialogs, если вы не делаете это «вручную» с помощью ContextInjectionFactory при создании диалога:

IWizard wizard = ContextInjectionFactory.make(YourWizardClass.class, eclipseContext);

WizardDialog dialog = new WizardDialog(shell, wizard);

Это сделает инъекцию в ваш класс мастера, предоставив вам доступ к файлу EPartService.

Вы также можете использовать «брокер событий» (IEventBroker) для трансляции события всему, что вас интересует, вместо того, чтобы искать конкретное представление.

person greg-449    schedule 21.05.2014
comment
Ваш ответ привел меня к довольно простому решению. Я просто внедрил EPartService в свой обработчик, взял ссылку на представление и передал ее моему мастеру через его конструктор. Теперь я могу без проблем вызвать свой метод обновления, и он работает как шарм. Предложение от @Stefan может быть еще более элегантным подходом, поэтому вместо этого я рассмотрю возможность создания объекта-оболочки в моей модели и передачи его мастеру таким же образом. Таким образом, у меня будет легкий доступ к вызовам событий. Большое спасибо за вашу помощь! - person BiggPlanet; 23.05.2014

enter code hereЛучший способ обновить представление — использовать модель для содержимого представления. Похоже, ваш мастер позволяет редактировать или создавать ингредиенты. Когда вы завершаете работу своего мастера, вы, вероятно, изменяете некоторые данные об ингредиентах. Модель ингредиента должна быть проинформирована об этих изменениях. Если представление использует поставщика содержимого, который наблюдает за этой моделью, оно будет автоматически обновляться, когда модель увидит обновление (это шаблон наблюдателя). Как это работает, зависит от характера ваших данных. Вы можете использовать PropertyChange-Support в Java.

Для этого позвольте поставщику контента реализовать интерфейс org.eclipse.jface.util.IPropertyChangeListener и запускать события изменения свойств при изменении данных.

ОБНОВИТЬ

My ContentProvider реализует интерфейс изменения свойств. Всякий раз, когда получено событие изменения свойства, средство просмотра обновляется (асинхронно). Все мои операции сохранения обрабатываются диспетчерами данных, подобными шаблону шлюза табличных данных Фаулера, но иногда для более чем одной таблицы. Диспетчер данных запускает событие изменения свойства. Таким образом, пользовательскому интерфейсу (мастеру) не нужно знать о сохранении

person Stefan    schedule 22.05.2014
comment
Спасибо за ответ @Stefan. У меня есть модель с использованием XCore, и я использую ее для обновления своих представлений и редакторов относительно существующих объектов. Но проблема, с которой я сталкиваюсь, заключается в обновлении представления при добавлении объекта new. Представление просто содержит TreeViewer, который обращается к моей базе данных для создания ее содержимого. Я хочу обновить представление после того, как пользователь завершит работу мастера, чтобы он обращался к БД за любыми новыми данными. Могу ли я добавить прослушиватель непосредственно в TreeViewer? Как мне уведомить представление о том, что произошло событие, которое должно привести к обновлению? - person BiggPlanet; 23.05.2014
comment
@BiggPlanet Используйте брокера событий e4 для передачи событий всему, что хочет их обработать — см. здесь - person greg-449; 23.05.2014
comment
@BiggPlanet: My ContentProvider реализует интерфейс изменения свойства. Всякий раз, когда получено событие изменения свойства, средство просмотра обновляется (асинхронно). Все мои операции сохранения обрабатываются диспетчерами данных, подобными шаблону шлюза табличных данных Фаулера, но иногда для более чем одной таблицы. Диспетчер данных запускает событие изменения свойства. Таким образом, пользовательскому интерфейсу (мастеру) не нужно знать о сохранении. - person Stefan; 24.05.2014