如何扩展从@FacesComponent 调度的 AjaxBehaviorEvent?

How to extend AjaxBehaviorEvent dispatched from @FacesComponent?

当我使用 <cc:clientBehavior name="chartUpdated" event="change" targets="chartdata"/>Composite Component 发送 ajax 事件时,我捕获了它Facelet 页面 使用 <f:ajax event="chartUpdated" listener="#{bean.updateListener}">。在 backing bean 中,我捕获类型为 AjaxBehaviorEvent 的事件。

public void updateListener(AjaxBehaviorEvent event){
      ...
}

我明白我可以扩展 AjaxBehaviorEvent 并在其中传递已更改的对象。 For example, Primefaces's Scheduler uses this approach:

  <p:ajax event="eventMove" listener="#{scheduleView.onEventMove}" update="messages" />

和支持 bean:

 public void onEventMove(ScheduleEntryMoveEvent event) {
        FacesMessage message = new FacesMessage(FacesMessage.SEVERITY_INFO, "Event moved", "Day delta:" + event.getDayDelta() + ", Minute delta:" + event.getMinuteDelta());

        addMessage(message);
    }

是否可以通过将 复合组件@FacesComponent 一起使用来实现相同的功能?

提前致谢!

很高兴再次见到你:)

接上一个 question:

覆盖 queueEvent() 以过滤有趣的事件(来自特定组件的更改)并将它们的排队推迟到验证阶段,以便能够获取转换和验证的值:

@FacesComponent("rangeComponent")
public class RangeComponent extends UIInput implements NamingContainer
{
    private final List<AjaxBehaviorEvent> customEvents = new ArrayList<>();
    ...

    @Override
    public void queueEvent(FacesEvent event)
    {
        FacesContext context = getFacesContext();
        if(event instanceof AjaxBehaviorEvent)
        {
            Map<String, String> params = context.getExternalContext().getRequestParameterMap();
            String eventName = params.get("javax.faces.behavior.event");
            Object eventSource = event.getSource();

            if("change".equals(eventName) && (from.equals(eventSource) || to.equals(eventSource)))
            {
                customEvents.add((AjaxBehaviorEvent) event);
                return;
            }
        }

        super.queueEvent(event);
    }

    @Override
    public void validate(FacesContext context)
    {
        super.validate(context);

        if(from.isValid() && to.isValid())
        {
            for(AjaxBehaviorEvent event : customEvents)
            {
                SelectEvent selectEvent = new SelectEvent(this, event.getBehavior(), this.getValue());

                if(event.getPhaseId().equals(PhaseId.APPLY_REQUEST_VALUES))
                {
                    selectEvent.setPhaseId(PhaseId.PROCESS_VALIDATIONS);
                }
                else
                {
                    selectEvent.setPhaseId(PhaseId.INVOKE_APPLICATION);
                }

                super.queueEvent(selectEvent);
            }
        }
    }

    ...
}

然后将特定的事件侦听器添加到您的托管 bean:

@ManagedBean
@ViewScoped
public class RangeBean implements Serializable
{
    private static final long serialVersionUID = 1L;

    private String range = "01/01/2015-31/12/2015";

    public void onSelect(SelectEvent event)
    {
        Messages.addGlobalInfo("[{0}] selected: [{1}]", event.getComponent().getId(), event.getObject());
    }

    public String getRange()
    {
        return range;
    }

    public void setRange(String range)
    {
        this.range = range;
    }
}