6.8.4 nightly not showing my default button on Form

Normally, I’d not comment on a nightly build, but I am using a 6.8.4 nightly (vaadin-6.8.4.nightly-20120922-c24517.jar, as well as the 0920 version) build that has a fix for initial fragments not firing. This does not happen under 6.8.3 (or previous versions).

But now I noted that my “default” buttons in Chameleon Theme are not showing up correctly (it’s just a tiny, non-working button) when a Form is first loaded. If I click the REFRESH button my browser (shows it happens on FF, Chrome and IE9) it then shows up fine. It doesn’t seem to be related to out of date CSS or the like because if I navigate away and then return to the same Form, the button won’t be showing again until a REFRESH. I noted when it’s tiny if I click it, nothing happens, but on REFRESH when it’s visible again, it works as expected.

Here’s a quick youtube that shows what I’m seeing in the hopes it can be fixed before it’s released (needs full screen and high resolution for best viewing):


http://www.youtube.com/watch?v=Igoc53G7ptI

Checked again and it’s still happening with the latest nightly: vaadin-6.8.4.nightly-20120925-c24575.jar

You should try adding ?debug and see if you get a Javascript exception from somewhere. It could explain why the rendering stops before rendering the button completely. I don’t see any changes in 6.8.4 which could cause this though. As always, the best way is to try to get it reproduced in a small test case and create a ticket for it (and include the test).

Well, it happens in 6.8.4 and not at all in 6.8.3 (or 6.8.2 – and earlier – which I fall back to because 6.8.3 broke initial fragments firing). Unfortunately, I don’t have a test case built. It does happen on all browsers, though.

I just tried again with ?debug and did AL and it show 0 errors but also fixed the button. Of course, if I leave the view and return, the bad button reappears. I tried the H button and clicked on the “mini” default button and saw no errors but it also “fixed” it. The FL button made no change.

In FF debug, the mini button shows this for the component (with the v-button-caption span being grayed out):

[font=Courier New]

[/font]

When the button is showing correctly, it looks like this:

[font=Courier New]

Save
[/font]

Here’s the AL output including the expanded view down to the Save button that is then fixed:


Making UIDL Request with params: 83c0f493-73c4-433f-86dd-6144f84821dc
Server visit took 29ms
JSON parsing took 0ms
-Response:
-change format=uidl pid=PID0
-com.vaadin.terminal.gwt.client.ui.VWindow id=PID0 height=765px width=1249px style=MainWindow caption=Open eSignForms - Users name=main theme=esf resizable=true main=true layoutRelativeHeight=true layoutRelativeWidth=true
+variables
-com.vaadin.terminal.gwt.client.ui.VVerticalLayout id=PID547 height=100.0% width=100.0% margins=0 alignments={} expandRatios={PID552:1,}
+com.vaadin.terminal.gwt.client.ui.VHorizontalLayout
-com.vaadin.terminal.gwt.client.ui.VSplitPanelHorizontal id=PID552 height=100.0% width=100.0% style=small immediate=true margins=0 position=200.0px minimumPosition=0.0% maximumPosition=100.0% reversed=false
+com.vaadin.terminal.gwt.client.ui.VTree
-com.vaadin.terminal.gwt.client.ui.VTabsheet id=PID554 height=100.0% width=100.0% style=open-only-closable immediate=true
+variables
-tabs
-tab icon=theme://icons/fatcow16/user.png caption=Users key=11 selected=true
-com.vaadin.terminal.gwt.client.ui.VSplitPanelVertical id=PID555 height=100.0% width=100.0% style=small icon=theme://icons/fatcow16/user.png margins=0 position=40.0% minimumPosition=0.0% maximumPosition=100.0% reversed=false
+com.vaadin.terminal.gwt.client.ui.VPanel
-com.vaadin.terminal.gwt.client.ui.VForm id=PID568 width=100.0% style=UserForm
+com.vaadin.terminal.gwt.client.ui.VGridLayout
-com.vaadin.terminal.gwt.client.ui.VVerticalLayout id=PID587 width=100.0% margins=0 alignments={} expandRatios={}
+com.vaadin.terminal.gwt.client.ui.VHorizontalLayout id=PID588 style=footer margins=0 alignments={} expandRatios={}
-com.vaadin.terminal.gwt.client.ui.VHorizontalLayout id=PID592 style=footer margins=0 alignments={} expandRatios={}
-com.vaadin.terminal.gwt.client.ui.VButton id=PID593 style=default caption=Save icon=theme://icons/fatcow16/accept.png description=Click to save any changes.
-variables
state=false
+com.vaadin.terminal.gwt.client.ui.VButton
+com.vaadin.terminal.gwt.client.ui.VButton
+com.vaadin.terminal.gwt.client.ui.VButton
+com.vaadin.terminal.gwt.client.ui.VButton
+com.vaadin.terminal.gwt.client.ui.VGridLayout id=PID598 width=100.0% style=mainFooter margins=0 h=2 w=3 structuralChange=false colExpand={0:700,1:100,2:200,} rowExpand={0:500,1:500,} alignments={0:5,1:20,2:34,3:5,4:34,}
+com.vaadin.terminal.gwt.client.ui.VUriFragmentUtility id=PID606 immediate=true
+actions
************************
Layouts analyzed on server, total top level problems: 0
************************
Processing time was 641ms for 15935 characters of JSON
Referenced paintables: 61
Warning: Icon load event was not propagated because VCaption owner is unknown.

Does the button by any chance have any ShortcutHandlers?

There was some work on them in 6.8.3 which could have something to do with the issue you are having. Especially, if the widgetset hasn’t been re-compiled. So could you please double-check that the widgetset has really been updated after you’ve updated Vaadin.

Finally, if possible could you run DevMode while reproducing the bug? Do you get any stacktraces there? I have a hunch that it could be a NPE being thrown somewhere before the Button gets painted but it is really hard to say without any testcase or stacktrace.

Do you by any chance use any ShortcutHandlers on that button?

There was some work on them on Vaadin 6.8.3 so they could be the culprit to your issue? Especially, if you still have an old widgetset. So please, could you double-check that the widgetset really has been updated and not lingering in any cache or something like that.

Another thing you could try is to run DevMode and reproduce the bug. Do you get any stacktraces there? My hunch is that there is a NPE being thrown just before the Button is rendered but it is really hard to know where or why without a testcase or stacktrace.

Yes, the button has:


saveButton.setStyleName(ChameleonTheme.BUTTON_DEFAULT);
saveButton.setClickShortcut(KeyCode.ENTER);

It was working fine under 6.8.3 (and earlier).

I just tried the official 6.8.4 build, recompiled the widgetset, removed everything in the deployment area so it has a completely new, and the problem remains the same.

Not sure what DEVMODE means as far as the stack trace. I added ?debug and noted the following:


Widget set is built on version: 6.8.4
Starting application openeSignFormsVaadinvaadin-553734685
Vaadin application servlet version: 6.8.4

AL continues to show no errors, but then “fixes” it by being re-rendered, just like if I reload the page.

I just commented out the KeyCode.ENTER setting and the button then renders fine, but of course it’s no longer acting as the default button.

If you can give me more details on what you mean by DevMode/stacktraces/NPE I’d be happy to check it out and report back.

Development Mode (DevMode for short) is an invaluable tool when debugging those kinds of wierd debugging issues and working on the client side of Vaadin. It sort of allows you to compile the widgetset “on-the-fly”, set breakpoints and view stacktraces originating from the client side Vaadin code. Very useful when doing client side stuff or tracking down those Javascript issues. There is more information about what and how the development works in
Book Of Vaadin, Chapter 11.8.6
.

You can easily create a devmode launch script if your using the Vaadin eclipse plugin. Just right click on the project, select properties and under the Vaadin category there is a button that will create a devmode lauch script under the root folder of your project. Then just run the launch script and add ?gwt.codesvr=localhost:9997 to your application URL to run your application through devmode.

Sounds like you guys already know about this problem since it was pointed out it has to do with keyboard shortcuts.

Here’s a test program that reproduces it, including the fact that if you comment out the shortcut, it works fine. It also seems to work fine if the Form footer is visible all the time rather than created invisible and made visible only when it’s item data source is set:

package com.example.vaadintest;

import java.util.Arrays;

import com.vaadin.Application;
import com.vaadin.data.Item;
import com.vaadin.data.Property;
import com.vaadin.data.util.HierarchicalContainer;
import com.vaadin.event.ShortcutAction.KeyCode;
import com.vaadin.ui.*;
import com.vaadin.ui.Button.ClickEvent;
import com.vaadin.ui.Button.ClickListener;

public class VaadintestApplication extends Application {
	
	Button defaultButton;
	Button otherButton;
	
	@Override
	public void init() {
		Window mainWindow = new Window("Vaadin Test Application", new VerticalLayout());
		mainWindow.getContent().setSizeFull();
		mainWindow.setSizeFull();
		setMainWindow(mainWindow);
		
    	HierarchicalContainer container = new HierarchicalContainer();
    	container.addContainerProperty("t1", String.class, "");
    	container.addContainerProperty("t2", String.class, "");
    	
		Item item = container.addItem("r1");
    	item.getItemProperty("t1").setValue("Row1 t1");
    	item.getItemProperty("t2").setValue("Row1 t2");

		item = container.addItem("r2");
    	item.getItemProperty("t1").setValue("Row2 t1");
    	item.getItemProperty("t2").setValue("Row2 t2");
    	
		MyForm form = new MyForm();
		MyTable table = new MyTable(form,container);
		
		VerticalSplitPanel splitPanel = new VerticalSplitPanel();
		splitPanel.setFirstComponent(table);
		splitPanel.setSecondComponent(form);
		splitPanel.setSplitPosition(50, HorizontalSplitPanel.UNITS_PERCENTAGE);
		
		mainWindow.addComponent(splitPanel);
	}
	
	public class MyTable extends Table {
		final MyForm form;
		
		public MyTable(MyForm pform,HierarchicalContainer container) {
			this.form = pform;
			setContainerDataSource(container);
			setSelectable(true);
			setImmediate(true);
			setSizeFull();
			
			addListener( new Property.ValueChangeListener() {

				@Override
				public void valueChange(com.vaadin.data.Property.ValueChangeEvent event) {
					final Item item = getItem(getValue());
					form.setItemDataSource(item);
				}
				
			});
		}
	}
	
	public class MyForm extends Form implements ClickListener {
		final GridLayout layout;
		
		public MyForm() {
			setWidth(100, UNITS_PERCENTAGE);
			setImmediate(true);
			
	    	setFormFieldFactory( new DefaultFieldFactory() {

				@Override
				public Field createField(Item item, Object propertyId, Component uiContext) {
	                TextField t = new TextField();
	                t.setWidth(100, Form.UNITS_PERCENTAGE);
	                t.setCaption((String)propertyId);
	    			t.setImmediate(false);
	    			return t;
	    	    }
	    	 });
	    	
			layout = new GridLayout(2,1);
			layout.setWidth(100, UNITS_PERCENTAGE);
	    	layout.setColumnExpandRatio(0, 0.5f);
	    	layout.setColumnExpandRatio(1, 0.5f);
	    	layout.setMargin(true);
	    	layout.setSpacing(true);
	    	setLayout(layout);
	    	
			HorizontalLayout footer = new HorizontalLayout();
	    	footer.setSpacing(true);
	    	footer.setMargin(false);
	    	footer.setVisible(false);
	    	setFooter(footer);
	    	
	    	defaultButton = new Button("Default Button", (ClickListener)this);
	    	defaultButton.setClickShortcut(KeyCode.ENTER); // Comment this line out and it works fine
    		footer.addComponent(defaultButton);
    		
	    	otherButton = new Button("Other button", (ClickListener)this);
    		footer.addComponent(otherButton);
		}
		
		@Override
	    public void setItemDataSource(Item newDataSource) {
	    	if (newDataSource != null) {
	    		super.setItemDataSource(newDataSource);
	    		layout.setVisible(true);
	    		getFooter().setVisible(true);
	    	} else {
	    		super.setItemDataSource(null);
	    		layout.setVisible(false);
	    		getFooter().setVisible(false);
	    	}
	    }
		
	    @Override
	    protected void attachField(Object propertyId, Field field) {
	        if (propertyId.equals("t1")) {
	            layout.addComponent(field, 0, 0);
	        } else if (propertyId.equals("t2")) {
	        	layout.addComponent(field, 1, 0);
	        }
	    }

		@Override
		public void buttonClick(ClickEvent event) {
			// TODO Auto-generated method stub
			
		}

	}
}

I noted that some other code I have that sets/resets the Button.setClickShortcut(KeyCode.ENTER) on a button sometimes fails, too. I suspect it’s the same underlying bug related to the button not always being visible (as the Form is part of a Table listing so it’s only visible when a row is clicked) yet the button shortkey is set/reset. We noted this under 6.8.3 (did not retest on 6.8.4 as we’ve not moved forward with it because of the main bug reported on this).

Anyway, hope this is being worked on or resolved in the next build. Let me know if a ticket needs to be entered or whether you have all the info you need.

The change causing all these problems have been reverted in 6.8.5. You should test a 6.8.5 nightly version if you have not already. If there are still issues in that version, please report them at
http://dev.vaadin.com

Thanks, Artur. I just gave vaadin-6.8.5.nightly-20121009-c24781.jar a try and sure enough, it all seems to be working again. I’ve only done rudimentary testing on it, but the fragments not firing on startup are working again, and the click shortcut for our “default” button is also displaying and working as expected, including tests that add/remove the shortcut handler based on focus in other textareas so hitting ENTER in those fields doesn’t cause the button to fire.

Looking forward to the 6.8.5 release now! Thanks!