2017-07-26 155 views
0

我試圖瞭解ZKoss如何在使用MVVM模式的情況下工作。在MVVM中未觸發ZK Combobox事件

我使用JDK8 ZK8.0.2.2 CE和wildfly 10

我有一個組合框和一個網格。我希望組合框onSelect事件觸發網格更新。網格用組合框中選定的項目作爲參數進行更新。

問題是,應該由onSelect調用的@Command方法永遠不會被調用,並且永遠不會觸發更新。

另一件事:如果我得到了數據綁定的正確工作方式,則Combobox上的onSelect參數甚至不是必需的。 Grid通過參數model =「@ load(vm.allMedia)」綁定到ViewModel(allMedia)中的ListModel。

因此,如果所有媒體更改,網格應自動更新(類似於JavaFX中發生的綁定屬性)。顯然這沒有發生。

這是.zul文件:

<?xml version="1.0" encoding="UTF-8"?> 
<zk xmlns="http://www.zkoss.org/2005/zul"> 
    <window apply="org.zkoss.bind.BindComposer" viewModel="@id('vm') @init('mediadb.gui.MediaViewModel')"> 
     <vbox pack="center" align="top" width="990px" height="600px"> 
      <panel title="Search" border="normal" vflex="true"> 
       <panelchildren> 
        <label value="Type" class="boxlabel" /> 
        <combobox id="cmbType" width="150px" model="@load(vm.allType)" selectedItem="@bind(vm.actualType)" 
         onSelect="@Command('updateTable')"> 
         <template name="model"> 
          <comboitem label="@load(each.label)" /> 
         </template> 
        </combobox> 
       </panelchildren> 
      </panel> 
      <panel title="Media" border="normal" vflex="true"> 
       <panelchildren> 
        <grid id="mediaGrid" mold="paging" autopaging="true" 
          emptyMessage="No results" pagingPosition="both" 
          vflex="true" model="@load(vm.allMedia)"> 
         <columns sizable="true"> 
          <column hflex="1" label="ID" align="center" sort="auto(id)" /> 
          <column hflex="3" label="Serial#" align="center" sort="auto(serialNumber)" /> 
          <column hflex="3" label="Support Label" align="center" sort="auto(supportLabel)" /> 
          <column hflex="3" label="User Label" align="center" sort="auto(userLabel)" /> 
          <column hflex="2" label="Added" align="center" sort="auto(addDate)" /> 
         </columns> 
         <template name="model"> 
          <row vflex="1"> 
           <label value="@load(each.id)" /> 
           <label value="@load(each.serialNumber)" /> 
           <label value="@load(each.supportLabel)" /> 
           <label value="@load(each.userLabel)" /> 
           <label value="@load(each.addDate) @converter('formatedDate', format='dd/MM/yyyy')" /> 
          </row> 
         </template> 
        </grid> 
       </panelchildren> 
      </panel> 
     </vbox> 
    </window> 
</zk> 

,這是模型視圖:

package mediadb.gui; 

import mediadb.db.DataProvider; 
import mediadb.entity.MdbCategory; 
import mediadb.entity.MdbMedia; 
import java.beans.PropertyVetoException; 
import java.io.IOException; 
import java.sql.SQLException; 
import java.util.ArrayList; 
import java.util.List; 
import java.util.logging.Level; 
import java.util.logging.Logger; 
import org.zkoss.bind.annotation.Command; 
import org.zkoss.bind.annotation.Init; 
import org.zkoss.bind.annotation.NotifyChange; 
import org.zkoss.zul.ListModel; 
import org.zkoss.zul.ListModelList; 

public class MediaViewModel { 

    private DataProvider db = null; 
    private ListModel<MdbCategory> allType = null; 
    private ArrayList<MdbMedia> allMediaData = null; 
    private ListModel<MdbMedia> allMedia = null; 
    private MdbCategory actualType = null; 

    @Init 
    public void init() { 
     try { 
      db = DataProvider.getInstance(); 
      allType = new ListModelList<>(db.getCategories()); 
      actualType = allType.getElementAt(0); 

      allMediaData = new ArrayList(); 
      allMedia = new ListModelList<>(allMediaData); 

     } catch (IOException | SQLException | PropertyVetoException e) { 
      Logger.getLogger(MediaViewModel.class.getName()).log(Level.SEVERE, null, e); 
     } 
    } 

    @Command 
    public void updateTable() { 
     allMediaData.clear(); 
     allMediaData.addAll(db.getMedia(actualType.getLabel())); 
    } 

    public ListModel<MdbCategory> getAllType() { 
     return allType; 
    } 

    public void setAllType(ListModel<MdbCategory> allType) { 
     this.allType = allType; 
    } 

    public MdbCategory getActualType() { 
     return actualType; 
    } 

    public void setActualType(MdbCategory actualType) { 
     this.actualType = actualType; 
    } 

    public ListModel<MdbMedia> getAllMedia() { 
     return allMedia; 
    } 
} 

(我省略數據bean,這是問題的跑題DB訪問。 )

我做錯了嗎?有沒有更好的方法來做到這一點?

在此先感謝。

回答

1

@Command在你的代碼中有一個大寫的C字母改爲@command,它應該工作正常。

改變成:

<combobox id="cmbType" width="150px" model="@load(vm.allType)" 
    selectedItem="@bind(vm.actualType)" onSelect="@command('updateTable')"> 

不要忘記你的updateTable方法

@Command 
@NotifyChange({"allMediaData","allMedia"}) 
public void updateTable() { 
    allMediaData.clear(); 
    allMediaData.addAll(db.getMedia(actualType.getLabel())); 
    allMedia.AddAll(allMediaData); 
} 
+0

都能跟得上添加@NotifyChange("allMediaData"),它仍然無法正常工作。我按照你的建議改變了論據(我不知道它們區分大小寫),但它的行爲完全一樣。 – NoWone

+0

感謝您的努力,仍然沒有運氣。我已經嘗試過,實際上(即使它不應該是必要的,因爲當Grid閱讀時綁定到allMedia對象 - 如果我理解正確)。 – NoWone

+0

@NoWone你有沒有嘗試將所有數據添加到AllMedia updateTable方法?嘗試更新我的新答案 –