2010-01-25 51 views
4

在Javascript中,我正在做一个SVG形状并添加一个单击处理程序,以这样的:使用ClickHandler与本地Javascript对象?

var rect = document.createElementNS('http://www.w3.org/2000/svg','rect'); 
    rect.addEventListener('click', myClickHandler, false); 

这个伟大的工程。我正在尝试在GWT中制作覆盖Rect类。如果可能的话,我想简单地做这样的事情:

public class SVGRect extends JavaScriptObject { 

    public native void addClickHandler(ClickHandler handler) /*-{ 
     addEventListener('click', handler, false); 
    }-*/; 
} 

这样我可以通过一个“正常”的GWT处理这一类,并使用它从外面任何其他正常GWT UI元素。我不知道如何将ClickHandler对象连接到对象的本地JavaScript实现?

感谢

回答

3

因为你需要一个ClickEvent传递给ClickHandler.onClick并从JavaScript获得由此带来的问题(AFAICT) - 我有一个稍微不同的,更加“通用”的方法去:

创建一个简单的回调接口:

public interface Callback { 
    void execute(); 
} 

您可以然后直接通过它,并调用它像这样:

public native void addClickHandler(Callback callback) /*-{ 
     addEventListener('click', function() { 
      [email protected]::execute()(); 
     }, false); 
}-*/; 

或创建一个中间步骤:

public void addClickHandler(Callback callback) { 
    _addClickHandler(getCallback(callback)); 
} 

private native void _addClickHandler(JavaScriptObject callback) /*-{ 
    addEventListener('click', callback, false); 
}-*/; 

// This can be moved to a better place 
private native static JavaScriptObject getCallback(Callback callback) /*-{ 
    return function() 
    { 
     [email protected]::execute()(); 
    }; 
}-*/; 

,当然,你会使用这样的:

SVGRect svg = getMeSVGRect(); 
svg.addClickHandler(new Callback() { 
    @Override 
    public void execute() { 
     // Do some stuff 
    } 
}); 

就个人而言,我倾向于第二种方案 - 而这是更多的代码,我比如保持我的native/JSNI方法是私有的(除非它是覆盖对象或类似的东西),并且代码更具可读性并且不易出错(不需要使用时髦的语法从native/JSNI代码中调用Java函数)。

+0

太棒了,谢谢! – user246114 2010-01-25 17:33:57