Сделайте несколько зависимых / каскадных выпадающих списков selectOneMenu в JSF

Я пытаюсь сделать 4 зависимых меню.

Когда пользователь выбирает элемент из первого меню, второе меню показывает зависимые данные, а когда пользователь выбирает элемент из второго, третье показывает зависимые данные и так далее.

Пользователь увидит элементы только в первом меню, а остальные будут пустыми. Если он выберет пункт в первом меню, во втором отобразятся данные, но третий и четвертый останутся пустыми и т. Д. Пользователь должен в конечном итоге выбрать записи из всех 4 меню.

<h:selectOneMenu id="first" value="#{nodes.selectState"}>
    <f:selectItems value="#{nodes.stateList}"/>
    <f:ajax render="second">
</h:selectOneMenu>
<h:selectOneMenu id="second" value="#{nodes.selectCity"}>
    <f:selectItems value="#{nodes.cityList}"/>
    <f:ajax render="third">
</h:selectOneMenu>
<h:selectOneMenu id="third" value="#{nodes.selectRegion"}>
    <f:selectItems value="#{nodes.regionList}"/>
    <f:ajax render="fourth">
</h:selectOneMenu>
<h:selectOneMenu id="fourth" value="#{nodes.selectStation"}>
    <f:selectItems value="#{nodes.stationList}"/>
</h:selectOneMenu>

узлы Java Class

private String selectState; //+setters, getters
private String selectCity; //+setters, getters
private String selectRegion; //+setters, getters
private String selectStation; //+setters, getters
private List<SelectItem> stateList; //+setters, getters
private List<SelectItem> cityList; //+setters, getters
private List<SelectItem> regionList; //+setters, getters
private List<SelectItem> stationList; //+setters, getters

public getStateList(){
    stateList= new ArrayList<SelectItem>();
    stateList.add(new SelectItem("A"));
}

public getCityList(){
    CityList= new ArrayList<SelectItem>();
    if(selectState.equals("A")){
        CityList.add(new SelectItem("B"));
    }
}

public getRegionList(){
    RegionList= new ArrayList<SelectItem>();
    if(selectCity.equals("B")){
        RegionList.add(new SelectItem("C"));
   }
}

public getStationList(){
    StationList= new ArrayList<SelectItem>();
    if(selectRegion.equals("C")){
        StationList.add(new SelectItem("D"));
    }
}

он работает только в первых 2 меню, остальные 2 меню получают нулевые значения

4 ответа

Поместите компонент в область видимости и избавьтесь от любой бизнес-логики в методах получения.

Бин должен быть помещен в область видимости так, чтобы все предыдущие выборы и новые доступные элементы были запомнены, иначе вещи потерпят неудачу, если, например, rendered Атрибут зависит от условия, которое было установлено только в предыдущем запросе, или от того, требуется ли JSF проверять выбранный элемент по списку доступных элементов.

Методы получения не должны содержать бизнес-логики, так как они также будут вызываться на этапе проверки. Вы должны использовать <f:ajax listener> выполнять бизнес-логику на основе изменений. В методе слушателя также следует явно очистить выбранные значения дочерних выпадающих списков. Ты можешь использовать <f:ajax render> обновить содержимое дочерних выпадающих.

Итак, так:

<h:selectOneMenu id="state" value="#{nodes.selectedState}">
    <f:selectItem itemValue="#{null}" itemLabel="-- select --" />
    <f:selectItems value="#{nodes.availableStates}" />
    <f:ajax listener="#{nodes.changeState}" render="city region station" />
</h:selectOneMenu>
<h:selectOneMenu id="city" value="#{nodes.selectedCity}">
    <f:selectItem itemValue="#{null}" itemLabel="-- select --" />
    <f:selectItems value="#{nodes.availableCities}" />
    <f:ajax listener="#{nodes.changeCity}" render="region station" />
</h:selectOneMenu>
<h:selectOneMenu id="region" value="#{nodes.selectedRegion}">
    <f:selectItem itemValue="#{null}" itemLabel="-- select --" />
    <f:selectItems value="#{nodes.availableRegions}" />
    <f:ajax listener="#{nodes.changeRegion}" render="station" />
</h:selectOneMenu>
<h:selectOneMenu id="station" value="#{nodes.selectedStation}">
    <f:selectItem itemValue="#{null}" itemLabel="-- select --" />
    <f:selectItems value="#{nodes.availableStations}" />
</h:selectOneMenu>

с

@ManagedBean
@ViewScoped
public class Nodes {

    private String selectedState; // getter+setter
    private String selectedCity; // getter+setter
    private String selectedRegion; // getter+setter
    private String selectedStation; // getter+setter
    private List<SelectItem> availableStates; // getter (no setter necessary!)
    private List<SelectItem> availableCities; // getter (no setter necessary!)
    private List<SelectItem> availableRegions; // getter (no setter necessary!)
    private List<SelectItem> availableStations; // getter (no setter necessary!)

    @EJB
    private SomeService someService;

    @PostConstruct
    public void init() {
        availableStates = someService.listStates();
    }

    public void changeState(AjaxBehaviorEvent event) {
        availableCities = someService.listCities(selectedState);
        selectedCity = selectedRegion = selectedStation = null;
        availableRegions = availableStations = null;
    }

    public void changeCity(AjaxBehaviorEvent event) {
        availableRegions = someService.listRegions(selectedCity);
        selectedRegion = selectedStation = null;
        availableStations = null;
    }

    public void changeRegion(AjaxBehaviorEvent event) {
        availableStations = someService.listStations(selectedRegion);
        selectedStation = null;
    }

    // Generate necessary getters+setters here. You should not change them.
}

Смотрите также:

В вашем коде есть опечатка. Для третьего меню вы дали имя идентификатора как "первое" вместо "третье". Может быть, из-за этой проблемы.

Попробуйте это, это может помочь вам

Используя --Select City--, --Select Region--, --Select Station--, чтобы избежать исключения нулевого указателя.

    public getStateList(){
    stateList= new ArrayList<SelectItem>();
    stateList.add(new SelectItem("A"));
    }

    public getCityList(){
    CityList= new ArrayList<SelectItem>();
    if(selectState.equals("A"))
    {
      CityList.add(new SelectItem("B"));
    }
    else
    {
      CityList.add(new SelectItem("--Select City--"));
      selectCity = "--Select City--";
    }

    public getRegionList(){
    RegionList= new ArrayList<SelectItem>();
    if(selectCity.equals("B"))
    {
      RegionList.add(new SelectItem("C"));
    }
    else
    {
      RegionList.add(new SelectItem("--Select Region--"));
      selectRegion = "--Select Region--";
    }
    }

    public getStationList(){
    StationList= new ArrayList<SelectItem>();
    if(selectRegion.equals("C"))
    {
       StationList.add(new SelectItem("D"));
    }
    else
    {
      StationList.add(new SelectItem("Select Station"));
      selectStation = "--Select Station--";
    }
    }

Вы столкнулись с этой проблемой, потому что у вас есть два раза id="first", Исправьте это, и это должно работать.

Другие вопросы по тегам