GWT中的自定义渲染器

GWT中的自定义渲染器,gwt,widget,Gwt,Widget,我正在尝试创建一个小部件,它将以与本机值不同的格式呈现其关联的值。例如,如果值(在数据库中)是“abcde”,我希望在屏幕上显示“ab.cd.e”,如果用户键入“abcde”,我也希望显示“ab.cd.e”。如果用户输入“ab.cd.e”,那么我只想在数据库中存储“abcde”。我是在GWT编辑器框架中执行此操作的。我试图使用这个答案中的建议,但我无法让它发挥作用。以下是UiBinder文件中的内容: 在相关的Java单元中: @UiField 文本框我的文本框; ... initWidge

我正在尝试创建一个小部件,它将以与本机值不同的格式呈现其关联的值。例如,如果值(在数据库中)是“abcde”,我希望在屏幕上显示“ab.cd.e”,如果用户键入“abcde”,我也希望显示“ab.cd.e”。如果用户输入“ab.cd.e”,那么我只想在数据库中存储“abcde”。我是在GWT
编辑器框架中执行此操作的。我试图使用这个答案中的建议,但我无法让它发挥作用。以下是UiBinder文件中的内容:


在相关的Java单元中:

@UiField
文本框我的文本框;
...
initWidget(binder.createAndBindUi(this));
新的MyValueBox(myTextBox);
下面是MyValueBox小部件的定义:

公共类MyValueBox扩展了ValueBox{
//=========================================================================
公共静态类MyRenderer扩展了AbstractRenderer{
私有静态MyRenderer\u实例;
私有静态MyRenderer实例(){
if(_instance==null){
_实例=新的MyRenderer();
}
返回_实例;
}
@凌驾
公共字符串呈现(最终字符串文本){
//执行此操作之前需要进行验证!
返回text.substring(0,2)+“+text.substring(2,4)+”
+文本。子字符串(4);
}
}
//=========================================================================
公共静态类MyParser实现解析器{
私有静态MyParser_实例;
私有静态MyParser实例(){
if(_instance==null){
_instance=newmyparser();
}
返回_实例;
}
@凌驾
公共字符串解析(最终CharSequence文本)引发ParseException{
返回“已解析字符串”;
}
}
//=========================================================================
公共MyValueBox(最终文本框valueBox){
super(valueBox.getElement(),MyRenderer.instance(),MyParser.instance());
}
}
如您所见,我正在尝试包装使用
UiBinder
创建的
TextBox
,但我看不到任何效果。我知道我遗漏了一些非常简单的东西,还有一种更简单的方法来实现这一点,但我被难住了。谢谢你的建议

--编辑--


我最终决定使用一个
CellWidget
,除了在面板上使用之外,它还有一个额外的优势,那就是我可以在cell小部件(例如,DataGrid)中使用该代码。我在这里记录了我的解决方案:

您缺少在UIBinder中声明自定义小部件的功能。您需要将包绑定到xml声明,将您的包添加到标准声明(称为“g”):


然后,在UIBinder中声明文本框时,应使用声明的urn和类的名称:

<myurn:MyValueBox ui:field='myTextBox' width='300px'/>
public class CustomText extends ValueBoxBase<String>
{
    public CustomText() {
        super(Document.get().createTextInputElement(),CustomRenderer.instance(),
           CustomParser.instance());
      }

    private static class CustomRenderer extends AbstractRenderer<String>
    {
        private static CustomRenderer INSTANCE;

        public static CustomRenderer instance() {    
            if (INSTANCE == null) {
                INSTANCE = new CustomRenderer();
            }
            return INSTANCE;
        }

        @Override
        public String render(String text)
        {
            return "rendered string";
        }    
    }

    private static class CustomParser implements Parser<String>
    {
        private static CustomParser INSTANCE;

        public static CustomParser instance() {
            if (INSTANCE == null) {
                INSTANCE = new CustomParser();
            }
            return INSTANCE;
        }

        @Override
        public String parse(CharSequence text) throws ParseException
        {
            return "parsed string";
        }

    }
}

=======编辑=====

您应该扩展ValueBoxBase,而不是包装TextBox,这样您就可以按照自己的意愿控制渲染器和解析器,现在您就可以从UIBinder中将自定义框用作小部件了:

<myurn:MyValueBox ui:field='myTextBox' width='300px'/>
public class CustomText extends ValueBoxBase<String>
{
    public CustomText() {
        super(Document.get().createTextInputElement(),CustomRenderer.instance(),
           CustomParser.instance());
      }

    private static class CustomRenderer extends AbstractRenderer<String>
    {
        private static CustomRenderer INSTANCE;

        public static CustomRenderer instance() {    
            if (INSTANCE == null) {
                INSTANCE = new CustomRenderer();
            }
            return INSTANCE;
        }

        @Override
        public String render(String text)
        {
            return "rendered string";
        }    
    }

    private static class CustomParser implements Parser<String>
    {
        private static CustomParser INSTANCE;

        public static CustomParser instance() {
            if (INSTANCE == null) {
                INSTANCE = new CustomParser();
            }
            return INSTANCE;
        }

        @Override
        public String parse(CharSequence text) throws ParseException
        {
            return "parsed string";
        }

    }
}
公共类CustomText扩展了ValueBoxBase
{
公共文本(){
super(Document.get().createTextInputElement(),CustomRenderer.instance(),
CustomParser.instance());
}
私有静态类CustomRenderer扩展了AbstractRenderer
{
私有静态定制实例;
公共静态CustomRenderer实例(){
if(实例==null){
实例=新的CustomRenderer();
}
返回实例;
}
@凌驾
公共字符串呈现(字符串文本)
{
返回“呈现字符串”;
}    
}
私有静态类CustomParser实现语法分析器
{
私有静态定制解析器实例;
公共静态CustomParser实例(){
if(实例==null){
INSTANCE=newcustomparser();
}
返回实例;
}
@凌驾
公共字符串解析(CharSequence文本)引发ParseException
{
返回“已解析字符串”;
}
}
}

我不清楚如何创建MyValueBox实例-MyValueBox类有一个构造函数,它接受一个参数,我当然可以删除这个参数,但是我仍然需要调用继承的构造函数,它接受一个
元素作为第一个参数。。。我该怎么做?为什么要在构造函数中发送文本框?我可以看看MyValueBox的构造函数吗?但是,您可以查看以了解如何通过构造函数发送参数。我正在将
文本框
发送到构造函数,以便将
文本框
包装到具有渲染器的小部件中。我看不到在
文本框
上覆盖渲染的方法。