I have 2 CustomTables with same column names. They are created using expandratio width.
I added resizecolumnlisteners to them so when user column in table1 resize also table2 and vice versa. Problem is when resizing with
List<Values> list;// list of objects in table;
table1.addresizeColumnListener(new resizeColumnListener(){
private void resizeColumn(Event)
{
for(int i=0; i<list.size(); i++)
{
table2.setColumnWidth(list.get(i), table1.getColumnWidth(list.get(i)));
}
}
in table changes only column where listener is fired all others dont change, only when i click any column again all column's widths in table2 is set from table1.
I have too low stackoverflow reputation level to add a comment - so I'm writing this answer.
First of all: Which version of Vaadin do you use? I can't find the function which you used:
table1.addresizeColumnListener(...)
In Vaadin latest documentation is addColumnResizeListener.
And I have doubt why you want change size of all column after notification that one column has been changed? I imagine that after each column size change the Table.ColumnResizeEvent should be emit.
I think the problem you are facing is that when you re-size something in the browser, it will not get sent to the server straight away. The update to the server is sent to the server along with the next update request. That is why you get the delayed update to the UI (if I understood it correctly).
To fix this you can try the code below. Notice the setImmediate(true). This will basically tells Vaadin that you want any update to the table to be sent to the server immediately when the user modifies the table properties.
Try this:
table1.setImmediate(true);
table1.addColumnResizeListener(new ColumnResizeListener(){
#Override
public void columnResize(ColumnResizeEvent event) {
table2.setColumnWidth(event.getPropertyId(), event.getCurrentWidth());
}
});
table2.setImmediate(true);
table2.addColumnResizeListener(new ColumnResizeListener(){
#Override
public void columnResize(ColumnResizeEvent event) {
table1.setColumnWidth(event.getPropertyId(), event.getCurrentWidth());
}
});
Related
I am doing some integration tests, and I have replaced some tables with a grid. At this moment, I have some visible columns by default and other columns are hidden as follows:
column6.setHidable(true);
column6.setHidden(true);
Now I am trying to do some integration tests. For getting the grid, I can use the method (is the only grid present in this view):
$(GridElement.class).first();
This works fine. But for my test (with Vaadin Testbench), I need to check some values that are inside the hidden columns of the grid. I am talking about this button:
I have tried to use the Vaadin debug console to get the name of the button that allows the user to show/hide columns, but the debug console only can select the entire grid element, not this menu.
Also I have check if inside the GridElement exists any kind of already implemented method that give me access to this menu without any success.
Usually, chrome developer tools (or similar for firefox and ie / edge, etc) is your best friend in such cases. So far I'm not aware of anything dedicated for that particular button. However you can workaround this limitation by selecting the items which compose this feature by their specific classes:
The below test method shows a quick implementation which should give you a starting point:
public class GridManipulationTest extends TestBenchTestCase {
#Before
public void setUp() throws Exception {
System.setProperty("webdriver.chrome.driver", "D:\\Kit\\chromedriver_win32\\chromedriver.exe");
setDriver(new ChromeDriver());
}
#After
public void tearDown() throws Exception {
// TODO uncomment below after checking all works as expected
//getDriver().quit();
}
#Test
public void shouldOpenGridColumnVisibilityPopupAndSelectItems() {
// class for the grid sidebar button
String sideBarButtonClass = "v-grid-sidebar-button";
// class for the sidebar content which gets created when the button is clicked
String sideBarContentClass = "v-grid-sidebar-content";
// xpath to select the item corresponding to the necessary column
// there are perhaps more "elegant" solutions, but this is what I came up with at the time
String columnMenuItemXpath = "//*[contains(#class, 'column-hiding-toggle')]/span/div[text()='Name']";
// open the browser
getDriver().get("http://localhost:8080/");
// get the first available grid
GridElement firstGrid = $(GridElement.class).first();
// look for the grid's sidebar button and click it
firstGrid.findElement((By.className(sideBarButtonClass))).click();
// the sidebar content is created outside the grid structure so don't look for it using the grid search context
WebElement sidebarContent = findElement(By.className(sideBarContentClass));
// look for the expected column name and click it
sidebarContent.findElement(By.xpath(columnMenuItemXpath)).click();
}
}
And of course what it looks like in action
In the Grid widget in Vaadin 7.5.3, we can determine the current selection of rows by calling SelectionEvent::getSelected or Grid::getSelectedRows.
So how do we set the selection programmatically?
While that's true that official documentation for Grid class doesn't have this method stated, still you can do it programmatically. I won't argue whether it's a bug or not. Firstly you need to know what is your SelectionMode. Then you can select a row (or rows):
#Override
protected void init(VaadinRequest request) {
final VerticalLayout layout = new VerticalLayout();
Customer c = new Customer(1);
container = new BeanItemContainer<>(Customer.class, Arrays.asList(c, new Customer(2)));
grid = new Grid(container);
grid.setSelectionMode(SelectionMode.SINGLE);
SingleSelectionModel m = (SingleSelectionModel) grid.getSelectionModel();
m.select(c);
layout.addComponents(grid);
setContent(layout);
}
In newer Vaadin (in my case 7.5.6) there is select(Object) method directly in Grid interface.
Example:
Grid grid = new Grid(container);
grid.setSelectionMode(Grid.SelectionMode.SINGLE);
grid.select(row);
The row object for example could be taken from SelectionListener event or from added before object (as in #kukis answer).
Setter Method Missing (bug?)
The Book of Vaadin mentions the setter method Grid::setSelectedRows along with a getter.
The currently selected rows can be set with setSelectedRows() by a collection of item IDs, and read with getSelectedRows().
However, the Grid class doc does not list that method. Nor does NetBeans 8.0.2 suggest that method in its auto-complete.
So apparently a bug. See Ticket # 18,580.
I have a simple use case: in a multi select Table
when the user selects 1 row, a context menu with two actions must be returned (DELETE and DOWNLOAD)
when the user selects more than one row, only the DELETE Action should be in the context menu
This is the code I use:
contactList.setMultiSelect(true);
final Action delete = new Action("Delete", FontAwesome.TIMES);
final Action download = new Action("Download", FontAwesome.DOWNLOAD);
contactList.addActionHandler(new Action.Handler() {
#Override
public Action[] getActions(Object target, Object sender) {
final Table table = (Table)sender;
// if Table is in multi select mode, getValues() returns Set of item id's
if (table.isMultiSelect() && ((Set)table.getValue()).size() > 1) {
return new Action[] {delete};
} else {
return new Action[] {delete, download};
}
}
...
I see that getActions() is called by the Table component every time a row selection is made. It returns the correct Action array. However, in the UI, only one context menu is used, independent of the actions returned.
This topic is not covered in The Book of Vaadin. There is an old question but the solutions is way too complicated and the solution suggested by Joonas is not working (in fact the case i describe here).
Its a well-known issue in Vaadin from version 6. Most people (including me) work-around this by using ContextMenu Addon
I'm using SmartGWT 2.5.
I have a main grid that has its expandable rows in order to display subgrids.
I simply want to display the main grid with all its rows expanded from the start.
I tried to add a listener containing the following code:
ListGridRecord[] records = getRecords();
for (ListGridRecord rec : records) {
expandRecord(rec);
}
I tried with DataArrivedHandler and DrawAreaChangedHandler, but I just get javascript errors client-side or only parts of the rows are expanded. How can I fix this?
If you are talking about Grid Grouping, then you can use the following:
grid.setGroupStartOpen(GroupStartOpen.ALL);
listGrid.addDataArrivedHandler(new DataArrivedHandler() {
#Override
public void onDataArrived(DataArrivedEvent event) {
for (ListGridRecord rec : listGrid.getRecords()) {
listGrid.expandRecord(rec);
}
}
});
Should work (worked with previous versions..)
What error do you get?
Ok finally, I've put a timer of 100 ms within each handler.
The issue was that there was a delay before the full creation of the components (what I want to display is quite complex), and so when the handler was called, not everything was in place yet...
I have a webpage with multiple jqgrids each with inline editing enabled, "action" column (edit icons) enabled and pager disabled. I need to handle the delete event for each row so that I can process the delete without reloading server-side data. I've looked at the approach mentioned in jqGrid Delete a Row and it's very helpful except I have two questions that are stumping me -
Are there more details around the rp_ge parameter in the delOptions.onClickSubmit event?
My column has the delOptions set as this -
delOptions: {onclickSubmit: function(rp_ge, rowid) {return onRowDelete(rp_ge,rowid);}},processing:true }},
Is there a way to get the grid id from within that event? I'd like to have a generic function that I can use to handle delete events from all the grids on the page. The rp_ge parameter has a gbox which sometimes contains the grid id appended? But I have no idea what it is since i'm not able to figure out when it's populated, when it's not.
function onRowDelete(rp_ge, rowid) {
//hardcoded grid id.. don't like it.
var gridid = '#Grid_X';
//what is this gbox?? can i get grid id predictable from it?
//var gridid = rp_ge.gbox.replace("#gbox_", "");
var grid = $('#Grid_X');
rp_ge.processing = true;
var result = grid.delRowData(rowid);
if (result) {
$("#delmod" + grid[0].id).hide();
}
return true;
}
In the jqGrid Delete a Row approach, the code $("#delmod"+grid[0].id).hide(); is hiding the popup delete confirmation dialog manually. What I noticed is that when the dialog pops-up, jqgrid de-emphasizes the background page (makes it light greyish). But after the popup is manually closed (hidden actually?), the background remains de-emphasized. So it looks like the page doesn't have focus (or even disabled). Any way this can be fixed? This can also be seen on the demo that Oleg wrote.
Any help would be appreciated.
(PS - I would've commented on the same post but I don't have enough points to comment on someone else's answer yet.)
In answer to your second point.
Several examples by Oleg such as this one have the following modification.
$("#delmod" + grid[0].id).hide();
is replaced with
$.jgrid.hideModal(
"#delmod"+grid_id,
{gb:"#gbox_"+grid_id,jqm:rp_ge.jqModal,onClose:rp_ge.onClose}
);
This will return focus after the delete operation.