Vaadin Grid 鼠标中键单击
Vaadin Grid middle mouse click
我正在尝试在我的 vaadin 网格中模拟正常的浏览器行为,其中包括单击鼠标中键以在新选项卡中打开:
addItemClickListener(e -> {
boolean newTab = e.getMouseEventDetails().getButton() == MouseEventDetails.MouseButton.MIDDLE || e.getMouseEventDetails().isCtrlKey();
//open in window or new tab
});
但是,vaadin 没有注册鼠标中键。我怎样才能让它发挥作用?
该功能已包含在 vaadin-grid(进入 Vaadin 10)中,在 Vaadin 8 中将无法使用。
对于 Vaadin 8,您可以使用某些客户端扩展来拦截事件,或者使用 ComponentRenderer
为每个组件添加 Panel
(可行,但并不理想 because it degrades performance):
grid.addColumn(item->{
Panel p = new Panel(item.getName());
p.setStyleName(ValoTheme.PANEL_BORDERLESS);
p.addClickListener(ev->{
System.out.println(ev.getButtonName());
});
return p;
}).setRenderer(new ComponentRenderer());
另一方面,客户端扩展允许侦听 javascript 事件(例如 MouseEvent
)并触发服务器事件作为响应。创建扩展是一个相当复杂的主题(因为它使用了通常对开发人员隐藏的 API 的一部分)但是它允许直接访问呈现的 DOM,否则这是不可能的。
文档中的以下资源可以为您提供一个起点:
Creating a component extension (which describes a simple extension with Java code only) and Integrating JavaScript Components and Extension(解释了如何将本机 JavaScript 代码添加到您的扩展)。
在我的具体案例中我是如何解决问题的:
服务器端:
public class MyGrid<T> extends Grid<T> {
public MyGrid(String caption, DataProvider<T, ?> dataProvider) {
super(caption, dataProvider);
MiddleClickExtension.extend(this);
}
public static class MiddleClickExtension<T> extends AbstractGridExtension<T> {
private MiddleClickExtension(MyGrid<T> grid) {
super.extend(grid);
registerRpc((rowKey, columnInternalId, details) -> grid.fireEvent(
new ItemClick<>(grid, grid.getColumnByInternalId(columnInternalId), grid.getDataCommunicator().getKeyMapper().get(rowKey), details)),
MiddleClickGridExtensionConnector.Rpc.class);
}
public static void extend(MyGrid<?> grid) {
new MiddleClickExtension<>(grid);
}
@Override
public void generateData(Object item, JsonObject jsonObject) {
}
@Override
public void destroyData(Object item) {
}
@Override
public void destroyAllData() {
}
@Override
public void refreshData(Object item) {
}
}
}
客户端:
@Connect(MyGrid.MiddleClickExtension.class)
public class MiddleClickGridExtensionConnector extends AbstractExtensionConnector {
@Override
protected void extend(ServerConnector target) {
getParent().getWidget().addDomHandler(event -> {
if (event.getNativeButton() == NativeEvent.BUTTON_MIDDLE) {
event.preventDefault();
CellReference<JsonObject> cell = getParent().getWidget().getEventCell();
getRpcProxy(Rpc.class).middleClick(cell.getRow().getString(DataCommunicatorConstants.KEY), getParent().getColumnId(cell.getColumn()),
MouseEventDetailsBuilder.buildMouseEventDetails(event.getNativeEvent(), event.getRelativeElement()));
}
}, MouseDownEvent.getType());
}
@Override
public GridConnector getParent() {
return (GridConnector) super.getParent();
}
public interface Rpc extends ServerRpc {
void middleClick(String rowKey, String columnInternalId, MouseEventDetails details);
}
}
我正在尝试在我的 vaadin 网格中模拟正常的浏览器行为,其中包括单击鼠标中键以在新选项卡中打开:
addItemClickListener(e -> {
boolean newTab = e.getMouseEventDetails().getButton() == MouseEventDetails.MouseButton.MIDDLE || e.getMouseEventDetails().isCtrlKey();
//open in window or new tab
});
但是,vaadin 没有注册鼠标中键。我怎样才能让它发挥作用?
该功能已包含在 vaadin-grid(进入 Vaadin 10)中,在 Vaadin 8 中将无法使用。
对于 Vaadin 8,您可以使用某些客户端扩展来拦截事件,或者使用 ComponentRenderer
为每个组件添加 Panel
(可行,但并不理想 because it degrades performance):
grid.addColumn(item->{
Panel p = new Panel(item.getName());
p.setStyleName(ValoTheme.PANEL_BORDERLESS);
p.addClickListener(ev->{
System.out.println(ev.getButtonName());
});
return p;
}).setRenderer(new ComponentRenderer());
另一方面,客户端扩展允许侦听 javascript 事件(例如 MouseEvent
)并触发服务器事件作为响应。创建扩展是一个相当复杂的主题(因为它使用了通常对开发人员隐藏的 API 的一部分)但是它允许直接访问呈现的 DOM,否则这是不可能的。
文档中的以下资源可以为您提供一个起点: Creating a component extension (which describes a simple extension with Java code only) and Integrating JavaScript Components and Extension(解释了如何将本机 JavaScript 代码添加到您的扩展)。
在我的具体案例中我是如何解决问题的:
服务器端:
public class MyGrid<T> extends Grid<T> {
public MyGrid(String caption, DataProvider<T, ?> dataProvider) {
super(caption, dataProvider);
MiddleClickExtension.extend(this);
}
public static class MiddleClickExtension<T> extends AbstractGridExtension<T> {
private MiddleClickExtension(MyGrid<T> grid) {
super.extend(grid);
registerRpc((rowKey, columnInternalId, details) -> grid.fireEvent(
new ItemClick<>(grid, grid.getColumnByInternalId(columnInternalId), grid.getDataCommunicator().getKeyMapper().get(rowKey), details)),
MiddleClickGridExtensionConnector.Rpc.class);
}
public static void extend(MyGrid<?> grid) {
new MiddleClickExtension<>(grid);
}
@Override
public void generateData(Object item, JsonObject jsonObject) {
}
@Override
public void destroyData(Object item) {
}
@Override
public void destroyAllData() {
}
@Override
public void refreshData(Object item) {
}
}
}
客户端:
@Connect(MyGrid.MiddleClickExtension.class)
public class MiddleClickGridExtensionConnector extends AbstractExtensionConnector {
@Override
protected void extend(ServerConnector target) {
getParent().getWidget().addDomHandler(event -> {
if (event.getNativeButton() == NativeEvent.BUTTON_MIDDLE) {
event.preventDefault();
CellReference<JsonObject> cell = getParent().getWidget().getEventCell();
getRpcProxy(Rpc.class).middleClick(cell.getRow().getString(DataCommunicatorConstants.KEY), getParent().getColumnId(cell.getColumn()),
MouseEventDetailsBuilder.buildMouseEventDetails(event.getNativeEvent(), event.getRelativeElement()));
}
}, MouseDownEvent.getType());
}
@Override
public GridConnector getParent() {
return (GridConnector) super.getParent();
}
public interface Rpc extends ServerRpc {
void middleClick(String rowKey, String columnInternalId, MouseEventDetails details);
}
}