简体   繁体   English

Wicket:隐藏组件而不必添加所有子组件

[英]Wicket: hide a component without having to add all its children

I've been doing a project in Wicket, and I often find myself in an annoying situation. 我一直在Wicket上做一个项目,但我经常感到自己很烦。 Let's say I have a piece of markup that I only show when some condition applies, like the following example: 假设我有一个标记,仅在某些条件适用时才显示,例如以下示例:

<div wicket:id="myContainer">
    <div wicket:id="label1"></div>
    <div wicket:id="label2"></div>
    <div wicket:id="label3"></div>
    <div wicket:id="label4"></div>
</div>

and in my Java code: 在我的Java代码中:

WebMarkupContainer myContainer = new WebMarkupContainer("myContainer");
add(myContainer);

if(myDataObject != null){
    myContainer.add(new Label("label1", myDataObject.getData1());
    myContainer.add(new Label("label2", myDataObject.getData2());
    myContainer.add(new Label("label3", myDataObject.getData3());
    myContainer.add(new Label("label4", myDataObject.getData4());
} else{
    //HAVING TO DO THIS IS ABSURD!
   myContainer.add(new Label("label1", "");
   myContainer.add(new Label("label2", "");
   myContainer.add(new Label("label3", "");
   myContainer.add(new Label("label4", "");
   myContainer.setVisible(false);
}

As you can see, I'm forced to add dummy components to the container even in the cases where I'm not gonna show it, otherwise Wicket will throw an exception, saying I have components in the markup that I haven't added in code. 如您所见,即使在我不想显示的情况下,我也不得不向容器中添加虚拟组件,否则Wicket会抛出异常,说我在标记中有未添加的组件。码。

To me, this is ridiculous, having to instantiate extra components that I'm not gonna show is wasteful, time-consuming and makes the code less readable unnecessarily. 对我来说,这太荒谬了,不得不实例化我不会显示的额外组件是浪费,费时的,并且使代码不必要的可读性降低。

I'm hoping that it's just my ignorance of Wicket and that someone can tell me a method that allows me to "discard a component and all children". 我希望这只是我对Wicket的无知,并且有人可以告诉我一种允许我“丢弃组件和所有子组件”的方法。

You could improve you code a lot, so it becomes less painful :) 您可以极大地改善代码,从而减轻痛苦:)

This is a nice place to use the CompoundPropertyModel . 这是使用CompoundPropertyModel的好地方。

Also, just control the visibility in the onConfigure() of the container. 另外,只需在容器的onConfigure()中控制可见性onConfigure()

WebMarkupContainer myContainer = new WebMarkupContainer("myContainer", new CompoundPropertyModel(myDataObject))
{
    public void onConfigure()
    {
        setVisible( this.getModelObject() != null);
    }
}

add(myContainer);

myContainer.add(new Label("data1"));
myContainer.add(new Label("data2"));
myContainer.add(new Label("data3"));
myContainer.add(new Label("data4"));

Alternative 另类

The way you use your WebMarkupContainer suggests you could also use a Panel there to build a nice display component for this "myDataObject" 使用WebMarkupContainer的方式建议您也可以在其中使用Panel来为此“ myDataObject”构建一个不错的显示组件

Java 爪哇

public class MyDataObjectPanel extends Panel
{
    public MyDataObjectPanel(String id, IModel<MyDataObject> myDataObjectModel)
    {
        super(id,  new CompoundPropertyModel(myDataObjectModel);
        this.add(new Label("data1"));
        this.add(new Label("data2"));
        this.add(new Label("data3"));
        this.add(new Label("data4"));
    }

    public void onConfigure()
    {
        setVisible( this.getModelObject() != null);
    }

}

HTML 的HTML

<wicket:panel>
    <div wicket:id="data1"></div>
    <div wicket:id="data2"></div>
    <div wicket:id="data3"></div>
    <div wicket:id="data4"></div>
</wicket:panel>

Then all places where you want to display it, just use this panel. 然后在所有要显示它的地方,只需使用此面板即可。


I would advise against this (because it makes you code more complicated and I don't think you'll win a lot of performance), but if you really care for not adding elements to the wicket-component-tree, you could the next code. 建议不要这样做(因为这会使您的代码更复杂,并且我认为您不会获得很多性能),但是如果您真的很想不在wicket-component-tree中添加元素,则可以码。 It decides whether to display the specialized component or not and replaces the actual component: 它决定是否显示专用组件,并替换实际组件:

 public class MainComponent { @Override protected void onConfigure() { MyDataObject obj = getDataObjectFromSomeModel(); if (obj == null) { this.addOrReplace( new EmptyPanel("dataPanelId").setVisible(false)); } else { this.addOrReplace( new MyDataObjectPanel("dataPanelId")); } } } 

I don't have time to try it right now but I'm pretty sure that 我现在没有时间尝试,但我很确定

} else{
  myContainer.setVisible(false);
}

should work. 应该管用。 Wicket won't complain that children are missing if the parent component is not rendered at all. 如果根本不渲染父组件,Wicket不会抱怨孩子丢失。

Don't assume that the cost is high. 不要以为成本很高。

Invisible components don't execute many methods, with the most important methods being onRender() and onComponentTag(). 不可见的组件不会执行许多方法,其中最重要的方法是onRender()和onComponentTag()。 Models don't execute getObject(). 模型不执行getObject()。 The cost visible from the point of view html generation is zero. 从html生成的角度来看,可见的成本为零。 Additional info: https://ci.apache.org/projects/wicket/guide/7.x/guide/componentLifecycle.html 其他信息: https : //ci.apache.org/projects/wicket/guide/7.x/guide/componentLifecycle.html

My knowledge is checked against current version 7.5.0 我的知识已经根据当前版本7.5.0进行了检查

I think Components (invisible) must exist, this is normal Wicket philosophy. 我认为组件(不可见)必须存在,这是正常的Wicket哲学。 Invisible Components are lightweight. 隐形组件重量轻。

BTW I'm not sure Your myDataObject is wicket Model. 顺便说一句,我不确定您的myDataObject是wicket模型。 I agree with recommendation in doc: use models . 我同意doc中的建议: 使用模型

Code will be cleaner without such 'if' - I prefer not using branched instantiation - but with correct model. 如果没有这样的“如果”,代码将变得更干净-我更喜欢不使用分支实例化-而是使用正确的模型。

Avoid too much "active" code in constructor, for example don't get values, let be conditionally (lazy) fetched via Model. 避免在构造函数中使用过多的“活动”代码,例如,不要获取值,而应通过Model有条件(懒惰)获取代码。 Catching exceptions thrown in Wicket constructors is ugly. 捕获在Wicket构造函数中引发的异常是丑陋的。 But application can catch exceptions in rendering phase very well. 但是应用程序可以很好地在渲染阶段捕获异常。

And in last words, remember, these are two policies to make component hidden, one static, the second dynamic: https://ci.apache.org/projects/wicket/guide/7.x/guide/keepControl.html#keepControl_1 最后要记住,这是两个使组件隐藏的策略,一个是静态的,第二个是动态的: https : //ci.apache.org/projects/wicket/guide/7.x/guide/keepControl.html#keepControl_1

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 是否可以将JComponent及其所有子组件绘制到另一个组件? - Is it possible to paint a JComponent and all its children to another component? 创建嵌入文本字段及其FeedbackPanel的Wicket组件 - Create Wicket component embedding a Textfield and its FeedbackPanel 是否可以在 Hibernate 中添加/删除 OneToMany 关系的子项而不加载所有子项? - Is it possible in Hibernate to add/remove children of a OneToMany relationship without loading all the children? Wicket:渲染/刷新RepeatingView而没有html标签 - Wicket : render/refresh RepeatingView without having html tag 隐藏其所有子组件时隐藏的Wicket容器 - Wicket container that is hidden when all its child components are hidden 如何在不添加Wicket组件的情况下修改属性? - how can i modify attributes without adding the component in Wicket? 在javafx中禁用节点而不禁用其子节点 - disabling a node without disable its children in javafx 检票口:隐藏 HTML 中的评论 - Wicket: hide comments in HTML wicket-动态添加选项卡而不渲染所有选项卡 - wicket - adding tabs dynamicly without rendering all tabs java gson-是否可以在没有所有字段的情况下从字符串反序列化对象 - java gson - is it possible to deserialize an object from a string without having all of its fields
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM