Гобелен: события из палитры
Я использую компоненты палитры на странице и хочу, чтобы доступные элементы в двух из них менялись в зависимости от того, что выбрано в первой.
Каков наилучший способ достичь этого? Какие события генерируются компонентом палитры, которые я мог бы прослушать, адаптировать модель палитры и выполнить обновление зоны? Я думал, что это будет работать так же, как для отдельных компонентов, которые делают что-то вроде этого:
void onValueChanged() {
// do something
}
К сожалению, это не работает для палитр.
Я использую Tapestry 5.4-beta-6, но я думаю, что ничего не изменилось с ранних версий.
2 ответа
Я наконец использовал didChange
элемент вместе с похожим миксином, как миксин Observe. Я выложил демо на Github для всех, кому интересно.
Всего несколько заметок:
- Я использовал 5.4 beta 6, он уже имеет необходимые события на стороне клиента.
- Я не мог заставить его работать с помощью модуля JavaScript Tapestry, поэтому я все еще использую javascriptSupport.addInitializerCall.
- Оставшаяся проблема заключается в том, что при обновлении второй палитры обновлением зоны будут сброшены все изменения, внесенные пользователем в эту палитру, поскольку они хранятся только на стороне клиента (в скрытом поле). Мне все еще нужно разобраться в этом, но это не является частью первоначального вопроса.
Я бы, наверное, сделал это с миксином.
public class PaletteChange {
@Parameter
private String zone;
@InjectContainer
private Palette palette;
public void afterRender() {
Link eventLink = componentResources.createEventLink("change");
JSONObject args = new JSONOBject(
"id", pallete.getClientId(),
"url", eventLink,
"zone", zone
);
javascriptSupport.addScript("palleteChange(%s)", args);
}
Object onChange(@RequestParameter("value") String value) {
CaptureResultCallback<Object> callback = new CaptureResultCallback<Object>();
resources.triggerEvent("change", new String[] { value }, callback);
return callback.getResult();
}
}
Javascript
function palleteChange(spec) {
var field = $('#' + spec.id + '/select[1]');
field.on('change', function() {
var zoneManager = Tapestry.findZoneManagerForZone(spec.zone);
var params = { value: field.val() };
zoneManager.updateFromURL(spec.url, params);
});
}
Тогда используйте миксин в своем коде
<t:palette t:id="myPalette" t:mixins="paletteChange" zone="myZone" ... />
<t:zone t:id="myZone">
...
</t:zone>
страница
@Inject
private Zone myZone;
Block onChangeFromMyPalette(String value) {
doStuff(value);
return myZone.getBody();
}
Смотрите здесь для аналогичного mixin.