2012-09-11 44 views
0

我有一個動態表單,我正在Wicket中寫入一些表單,這些表單與「點擊此處添加更多問題」類型的按鈕重複。我已經寫了一個非常基本的(我對Wicket仍然很陌生)的AJAXy監聽器,它主要工作,但我無法弄清楚如何刪除甚至隱藏ListView中的項目。動態添加和刪除沒有AJAX的組件?

這讓我想知道,有什麼辦法只是有一些JS複製表單域?在我使用Wicket組件重新構造窗體之前,我使用Jquery Dynamic Form插件重複了值。這工作很好,很容易理解(一個重要的優點)。不過,我想不通這會如何影響檢票,如果我只是用這個插件,而不是像

//Issue box magic 
    final MarkupContainer rowPanel = new WebMarkupContainer("issuesPanel"); 
    rowPanel.setOutputMarkupId(true); 
    form.add(rowPanel); 
    ArrayList numIssues = new ArrayList(); 
    numIssues.add(new Object()); 
    numIssues.add(new Object()); 
    numIssues.add(new Object()); 
    final ListView lv = new ListView("issuesBox", numIssues) { 
     @Override 
     protected void populateItem(ListItem item) { 
      int index = item.getIndex() + 1; 

      item.add(new DropDownChoice("issues", combinedIssues)); 
      item.add(new TextField<String>("note")); 
     } 
    }; 
    lv.setReuseItems(true); 
    rowPanel.add(lv); 
    form.add(new AjaxSubmitLink("addIssue", form) { 
     @Override 
     public void onSubmit(AjaxRequestTarget target, Form form) { 
      lv.getModelObject().add(new Object()); 
      if (target != null) 
       target.add(rowPanel); 
     } 
    }.setDefaultFormProcessing(false)); 
    form.add(new AjaxSubmitLink("removeIssue", form) { 
     @Override 
     public void onSubmit(AjaxRequestTarget target, Form form) { 
      //Wicket gets very angry when you remove components, so just hide it (recommended way) 
      if (target != null) { 
       Component lastObject = (Component)lv.get(lv.getList().size() - 1); 
       lastObject.setVisible(false); 
       log.debug("Components " + lv.get); 
      } 

     } 
    }.setDefaultFormProcessing(false)); 

的jQuery插件是非常容易使用,但我怎麼能告訴檢票,有超過場它認爲有?

注意我也試圖避免AJAX調用只是添加一個新問題,在我使用應用程序的淤積中可能會成爲一個問題。

有什麼建議嗎?

回答

3

你不能只通過ajax在html中添加表單元素。使用Wicket,您可以在html和Java中使用強制樹,並且兩者必須匹配。最後,Wicket在提交表單時必須知道這些值是多少。

不知道我理解你的特殊要求,但我想類似的問題可能是向某人添加地址。在這裏,我將創建一個AdressEditPanel,其中包含一個表單,其中包含一個地址所需的所有字段。該小組將有一個PersonAdress(作爲示例)Object as Model。

在Person上,您將擁有一個Adresses集合並使用ListView來呈現和編輯每個Adress。在ListView的populateItem()函數中,您可以將一個AdressEditPanel實例添加到該項目。

如果你需要爲一個人添加一個地址,只需在地址集合中添加一個條目並重新顯示錶單(我會首先使用Ajax,一旦它工作,只需要最小的改變就可以切換到ajax )。

希望幫助

+1

所以在提交階段沒有辦法告訴Wicket「嘿,這裏有3個字段比你想象的還要多」沒有AJAX訪問服務器?這似乎非常有限。 – TheLQ

+1

據我所知,不,這是不行的。不,我不認爲這是限制性的。您需要服務器端的組件進行驗證和轉換。並存儲這些值。在我所有的檢票項目中,這個阿賈克斯出行永遠不會有問題。你有什麼要求,你認爲他們是限制? – bert

+0

噢,好的。感謝您的幫助 – TheLQ

0

如果您在修改模型對象後調用ListView上的removeAll(),則應該解決您的問題。例如

new AjaxSubmitLink("addIssue", form) { 
     @Override 
     public void onSubmit(AjaxRequestTarget target, Form form) { 
      lv.getModelObject().add(new Object()); 
      lv.removeAll(); 
      if (target != null) 
       target.add(rowPanel); 
     } 

但是我不知道這是否會導致問題形成驗證,但我認爲它應該是安全的。

UPDATE

如果要應用相同的技術去除鏈接,你應該寫這樣的事情:

new AjaxSubmitLink("removeIssue", form) { 
     @Override 
     public void onSubmit(AjaxRequestTarget target, Form form) { 

      if (target != null) { 
       lv.getModelObject().remove(lv.getList().size() - 1); 
       lv.removeAll(); 
       target.add(rowPanel); 

      } 

     } 
    } 

但是沒有AJAX這是不可能的。唯一的方法是使用JS,並在服務器端讀取來自窗體的請求參數。

+0

我什麼問題,這是解決困惑...添加已經工作,消除的問題 – TheLQ

+0

如果刪除的問題,比你應該使用refreshingView代替。 – bert

+0

相同的代碼也適用於刪除元素。請參閱JavaDoc中的setReuseItems方法,它表示在修改ListView模型對象時應調用removeAll()。在我的評論中添加了刪除鏈接。 –