Vaadin

Vaadin Example Application

An application is a computer program created to perform a group of useful tasks for an end user. Application could be a vast topic to cover, just because a simple “Hello World” program is an application. Most applications do much more than only print a hello message on the user interface.

The “Hello world” application is useful as an initial program when you are learning a new programming language to illustrate the basic syntax for constructing a working program and get it to run on a computer. The first “Hello World” application was created by Brian Kernigham in a internal memorandum of Bell Laboratories “Programming in C a tutorial”.

1. The tools

  • Java JDK 8
  • Latest Eclipse Mars
  • Vaadin 7.6.6
  • Tomcat Server 8

2. Introduction

In this example we are going to create a sample Vaadin application to show common widgets interacting with each other. We generate a character sheet for an RPG game using random values. If the values appeal to us, we could save them for later use. This application could be useful to you if you play tabletop RPG games but further than that, is an application to illustrate some common Vaadin widgets working together.

3. Prerequisites

  • JDK installed
  • Eclipse Mars installed and working
  • Vaadin plug-in installed
  • Tomcat 8 installed and running

4. Set up the project

In the file menu choose File -> New -> Other

1 New Project
1 New Project

Now from the list choose Vaadin 7 project

2 Vaadin Project
2 Vaadin Project

Hit next and name your project then hit finish.

5. Coding the example

Class variables

	private Table attr;
	private Table savedAttr;
	private Item str;
	private Item con;
	private Item nte;
	private Item agi;
	private Item wis;
	private Random rnd;

We declared two tables and five items to manage our data, also a random instance to generate random numbers.

Layouts

		final VerticalLayout layout = new VerticalLayout();
		layout.setMargin(true);
		setContent(layout);

		HorizontalLayout topHorLay = new HorizontalLayout();
		topHorLay.setSizeFull();
		topHorLay.setSpacing(true);
		
		VerticalLayout butLay = new VerticalLayout();
		butLay.setSizeFull();
		butLay.setSpacing(true);
		Label butLabel = new Label("Is this OK?");
		butLabel.setStyleName("h2");

We create the layouts, a main vertical layout, a horizontal layout for the first row of the main layout and a vertical layout to place the buttons of the application.

CellStyleGenerator

		CellStyleGenerator myCellColors = new CellStyleGenerator() {
			
			@Override
			public String getStyle(Table source, Object itemId, Object propertyId) {
				if(propertyId!=null){
					Item item = source.getItem(itemId);
					if(item.getItemProperty(propertyId).getValue().getClass()==Integer.class){
						Integer cellValue = (Integer)item.getItemProperty(propertyId).getValue();
						if(cellValue > 15 && cellValue  17){
							return "green";
						}
						if(cellValue < 8){
							return "red";
						}
					}
				}
				return null;
			}
		};

This CellStyleGenerator changes the color of individual cells based on it’s value. First we check that the cell is no empty with if(propertyId!=null). Then we get the Item in the cell with Item item = source.getItem(itemId);.

We then Check the value of the Item and verify that is an integer with if(item.getItemProperty(propertyId).getValue().getClass()==Integer.class).

If the value is an Integer, we cast it to a local variable with Integer cellValue = (Integer)item.getItemProperty(propertyId).getValue(); and based on the value of the variable we set the colors of the cells in the table.

Attributes Table

		attr = new Table("Attributes");
		attr.addContainerProperty("Attribute", String.class, null);
		attr.addContainerProperty("Value", Integer.class, 0);
		attr.setPageLength(attr.size());
		attr.setSelectable(false);
		attr.setImmediate(true);
		attr.setFooterVisible(false);
		attr.setCellStyleGenerator(myCellColors);

This table is going to have the generated values, one string column with the name of the attribute and an integer column holding the value of that attribute. We create the table with attr = new Table("Attributes");. attr is a class field. attr.addContainerProperty("Attribute", String.class, null); defines the first value data type as string.

attr.addContainerProperty("Value", Integer.class, 0); defines the second column data type as integer. With attr.setPageLength(attr.size()); we constrain the size of the table on the screen to the size of the data contained on it.

attr.setSelectable(false);, the user cannot select the rows on the table.attr.setImmediate(true); set immediate tells the application to send any changes on the table to the server, when they occur. Hide the footer of the table attr.setFooterVisible(false);.

And tell the table to use our custom cell style generator attr.setCellStyleGenerator(myCellColors);.

Helper initialization

		rnd = new Random();
		createCharacterTable();

rnd = new Random(); initializes the random number generator. createCharacterTable();, calls a custom method to fill the table with the initial values. This is explained later on this article.

Table of saved attributes

		savedAttr = new Table("Saved Rolls");
		savedAttr.setSizeFull();
		savedAttr.addContainerProperty("Name", String.class, "");
		savedAttr.addContainerProperty("Strength", Integer.class, 0);
		savedAttr.addContainerProperty("Constitution", Integer.class, 0);
		savedAttr.addContainerProperty("Intelligence", Integer.class, 0);
		savedAttr.addContainerProperty("Agility", Integer.class, 0);
		savedAttr.addContainerProperty("Wisdom", Integer.class, 0);
		savedAttr.setCellStyleGenerator(myCellColors);

This table is going to have the saved data of our application.savedAttr = new Table("Saved Rolls"); creates the table.savedAttr.setSizeFull(); sets the size of the table to fit all the space available.

  • savedAttr.addContainerProperty("Name", String.class, "");, adds a string column to hold the name of our character.
  • savedAttr.addContainerProperty("Strenght", Integer.class, 0); adds an integer column to hold the strength attribute.
  • savedAttr.addContainerProperty("Constitution", Integer.class, 0);,  adds an integer column to hold the constitution attribute.
  • savedAttr.addContainerProperty("Intelligence", Integer.class, 0);, adds an integer column to hold the intelligence attribute.
  • savedAttr.addContainerProperty("Agility", Integer.class, 0); adds an integer column to hold the agility attribute.
  • savedAttr.addContainerProperty("Wisdom", Integer.class, 0); adds the column of the wisdom attribute.
  • savedAttr.setCellStyleGenerator(myCellColors); attachs the custom cell styles to the table.

Button reroll

		Button reroll = new Button("Reroll");
		reroll.setWidth("200px");
		reroll.setIcon(FontAwesome.DIAMOND);
		reroll.addStyleName("friendly");
		reroll.addClickListener(new ClickListener() {
			
			@SuppressWarnings("unchecked")
			@Override
			public void buttonClick(ClickEvent event) {
				str.getItemProperty("Value").setValue(getReroll());
				con.getItemProperty("Value").setValue(getReroll());
				nte.getItemProperty("Value").setValue(getReroll());
				agi.getItemProperty("Value").setValue(getReroll());
				wis.getItemProperty("Value").setValue(getReroll());
				
			}
		});

With this button we randomize all attributes with new values. Button reroll = new Button("Reroll"); creates the button. reroll.setWidth("200px"); sets the width of the button to “200px”. reroll.setIcon(FontAwesome.DIAMOND); assigns an icon to the button using fontawesome that is shipped with Vaadin out of the box.

reroll.addStyleName("friendly"); adds the Vaadin friendly style to the button, this style is predefined in Vaadin. reroll.addClickListener(new ClickListener() adds the listener to the button, inside the listener we call str.getItemProperty("Value").setValue(getReroll()); to get a new strength value using getReroll() method that is explained later.

The same procedure is done with all attributes in the table to get new random values.

Name TextField

		TextField name = new TextField("Character Name");
		name.setRequired(true);
		name.setWidth("200px");

With TextField name = new TextField("Character Name"); we create the text field to input the name of the character. name.setRequired(true); sets the field required. name.setWidth("200px"); sets the width of the field the same as the buttons.

Button save

		Button save = new Button("Save");
		save.addStyleName("primary");
		save.setIcon(FontAwesome.SAVE);
		save.setWidth("200px");
		save.addClickListener(new ClickListener()

Create a new button with Button save = new Button("Save");. save.addStyleName("primary"); assigns style primary to the button. save.setIcon(FontAwesome.SAVE); sets an icon for font awesome.

save.setWidth("200px"); sets the width to the button to 200 pixels.
save.addClickListener(new ClickListener() adds a click listener to the button.

Save click listener

			public void buttonClick(ClickEvent event) {
				int istr = (int) str.getItemProperty("Value").getValue();
				int icon = (int) con.getItemProperty("Value").getValue();
				int inte = (int) nte.getItemProperty("Value").getValue();
				int iagi = (int) agi.getItemProperty("Value").getValue();
				int iwis = (int) wis.getItemProperty("Value").getValue();
				
				if((istr != 0) && (icon != 0) && (inte != 0) && (iagi != 0) && (iwis != 0)){
					if(name.isEmpty()){
						Notification.show("The name is required");
					}else{
						String cName = name.getValue();
						if(findDuplicates(cName)){
							Notification.show("Name is duplicated");
						}else{
							Object savedAttrId = savedAttr.addItem();
							Item nSavAttr = savedAttr.getItem(savedAttrId);
							nSavAttr.getItemProperty("Name").setValue(cName);
							nSavAttr.getItemProperty("Strenght").setValue(istr);
							nSavAttr.getItemProperty("Constitution").setValue(icon);
							nSavAttr.getItemProperty("Intelligence").setValue(inte);
							nSavAttr.getItemProperty("Agility").setValue(iagi);
							nSavAttr.getItemProperty("Wisdom").setValue(iwis);
							name.setValue("");
							Notification.show("Character saved!");
						}
					}
				}else{
					Notification.show("You must generate a character first");
				}
				
			}

When the save button is clicked the click listener is called by the framework. int istr = (int) str.getItemProperty("Value").getValue(); gets the value of strength and cast it to an integer. int icon = (int) con.getItemProperty("Value").getValue(); gets the value of constitution and cast it to an integer. int icon = (int) nte.getItemProperty("Value").getValue(); gets the value of intelligence and cast it to an integer.

int inte = (int) agi.getItemProperty("Value").getValue(); gets the value of agility and cast it to an integer. int iwis = (int) wis.getItemProperty("Value").getValue(); gets the value of wisdom and cast it to an integer.
if((istr != 0) && (icon != 0) && (inte != 0) && (iagi != 0) && (iwis != 0)) checks the values has been generated.

Otherwise a notification is send to the user. name.isEmpty() checks the name is no empty. If the name is empty a notification is triggered.String cName = name.getValue() gets the name into a string variable. findDuplicates(cName) check if the name is already used.

When all conditions are meet then we proceed to save the character into the saved rolls table. Object savedAttrId = savedAttr.addItem(); creates a new object from the saved attributes table. Item nSavAttr = savedAttr.getItem(savedAttrId); gets the item from the container.

nSavAttr.getItemProperty("Name").setValue(cName); sets the value of the name into the saved attribute container, also we set all other properties from the container with the values we already have.

nSavAttr.getItemProperty("Strenght").setValue(istr); sets the strength. nSavAttr.getItemProperty("Constitution").setValue(icon); sets the constitution.

nSavAttr.getItemProperty("Intelligence").setValue(inte); sets the intelligence. nSavAttr.getItemProperty("Agility").setValue(iagi); sets the agility. nSavAttr.getItemProperty("Wisdom").setValue(iwis);.

Now we set the name text field to an empty string and send a notification to the user indicating that the character has been saved.

Add the widgets to the layouts

		butLay.addComponent(butLabel);
		butLay.addComponent(reroll);
		butLay.addComponent(save);
		butLay.addComponent(name);
		
		topHorLay.addComponent(attr);
		topHorLay.addComponent(butLay);
		
		layout.addComponent(topHorLay);
		layout.addComponent(savedAttr);

We add the buttons to the vertical butLay layout and then we add the attr table and the butLay to the horizontal topHorLay layout. Finally we add the topHorLay layout and the savedAttr table to the main layout.

createCharacterTable method

	private void createCharacterTable()
	{
		Object strItemId = attr.addItem();
		str = attr.getItem(strItemId);
		str.getItemProperty("Attribute").setValue("STR");
		str.getItemProperty("Value").setValue(0);
		
		Object conItemId = attr.addItem();
		con = attr.getItem(conItemId);
		con.getItemProperty("Attribute").setValue("CON");
		con.getItemProperty("Value").setValue(0);

		Object nteItemId = attr.addItem();
		nte = attr.getItem(nteItemId);
		nte.getItemProperty("Attribute").setValue("INT");
		nte.getItemProperty("Value").setValue(0);
	
		Object agiItemId = attr.addItem();
		agi = attr.getItem(agiItemId);
		agi.getItemProperty("Attribute").setValue("AGI");
		agi.getItemProperty("Value").setValue(0);

		Object wisItemId = attr.addItem();
		wis = attr.getItem(wisItemId);
		wis.getItemProperty("Attribute").setValue("WIS");
		wis.getItemProperty("Value").setValue(0);
	
	}

This method populate the attr table with two columns attribute and value and each row is an attribute used.

getReroll method

	private int getReroll(){
		return rnd.nextInt(19)+1;
	}

This method generates random integers to get the values of the attributes.

findDuplicates method

	private boolean findDuplicates(String newName){
		for(Iterator i = savedAttr.getItemIds().iterator(); i.hasNext();){
			
			int iid = (Integer) i.next();
			Item item = savedAttr.getItem(iid);
			String curName = (String) item.getItemProperty("Name").getValue();
			
			if(newName.toLowerCase().equals(curName.toLowerCase())){
				return true;
			}
			
		}
		return false;
	}

This method returns true if a name already exist in the saved attributes table.

6. The complete source code

VaadinappexampleUI.java

package com.example.vaadinappexample;

import javax.servlet.annotation.WebServlet;

import java.util.Iterator;
import java.util.Random;
import com.vaadin.annotations.Theme;
import com.vaadin.annotations.VaadinServletConfiguration;
import com.vaadin.data.Item;
import com.vaadin.server.FontAwesome;
import com.vaadin.server.VaadinRequest;
import com.vaadin.server.VaadinServlet;
import com.vaadin.ui.Button;
import com.vaadin.ui.HorizontalLayout;
import com.vaadin.ui.Label;
import com.vaadin.ui.Notification;
import com.vaadin.ui.Table;
import com.vaadin.ui.Table.CellStyleGenerator;
import com.vaadin.ui.TextField;
import com.vaadin.ui.UI;
import com.vaadin.ui.VerticalLayout;
import com.vaadin.ui.Button.ClickEvent;
import com.vaadin.ui.Button.ClickListener;

@SuppressWarnings("serial")
@Theme("vaadinappexample")
public class VaadinappexampleUI extends UI {

	@WebServlet(value = "/*", asyncSupported = true)
	@VaadinServletConfiguration(productionMode = false, ui = VaadinappexampleUI.class, widgetset = "com.example.vaadinappexample.widgetset.VaadinappexampleWidgetset")
	public static class Servlet extends VaadinServlet {
	}

	private Table attr;
	private Table savedAttr;
	private Item str;
	private Item con;
	private Item nte;
	private Item agi;
	private Item wis;
	private Random rnd;
	
	@Override
	protected void init(VaadinRequest request) {
		final VerticalLayout layout = new VerticalLayout();
		layout.setMargin(true);
		setContent(layout);

		HorizontalLayout topHorLay = new HorizontalLayout();
		topHorLay.setSizeFull();
		topHorLay.setSpacing(true);
		
		VerticalLayout butLay = new VerticalLayout();
		butLay.setSizeFull();
		butLay.setSpacing(true);
		Label butLabel = new Label("Is this OK?");
		butLabel.setStyleName("h2");

		CellStyleGenerator myCellColors = new CellStyleGenerator() {
			
			@Override
			public String getStyle(Table source, Object itemId, Object propertyId) {
				if(propertyId!=null){
					Item item = source.getItem(itemId);
					if(item.getItemProperty(propertyId).getValue().getClass()==Integer.class){
						Integer cellValue = (Integer)item.getItemProperty(propertyId).getValue();
						if(cellValue > 15 && cellValue  17){
							return "green";
						}
						if(cellValue < 8){
							return "red";
						}
					}
				}
				return null;
			}
		};
		
		attr = new Table("Attributes");
		attr.addContainerProperty("Attribute", String.class, null);
		attr.addContainerProperty("Value", Integer.class, 0);
		attr.setPageLength(attr.size());
		attr.setSelectable(false);
		attr.setImmediate(true);
		attr.setFooterVisible(false);
		attr.setCellStyleGenerator(myCellColors);

		rnd = new Random();
		createCharacterTable();
		
		savedAttr = new Table("Saved Rolls");
		savedAttr.setSizeFull();
		savedAttr.addContainerProperty("Name", String.class, "");
		savedAttr.addContainerProperty("Strength", Integer.class, 0);
		savedAttr.addContainerProperty("Constitution", Integer.class, 0);
		savedAttr.addContainerProperty("Intelligence", Integer.class, 0);
		savedAttr.addContainerProperty("Agility", Integer.class, 0);
		savedAttr.addContainerProperty("Wisdom", Integer.class, 0);
		savedAttr.setCellStyleGenerator(myCellColors);
		
		Button reroll = new Button("Reroll");
		reroll.setWidth("200px");
		reroll.setIcon(FontAwesome.DIAMOND);
		reroll.addStyleName("friendly");
		reroll.addClickListener(new ClickListener() {
			
			@SuppressWarnings("unchecked")
			@Override
			public void buttonClick(ClickEvent event) {
				str.getItemProperty("Value").setValue(getReroll());
				con.getItemProperty("Value").setValue(getReroll());
				nte.getItemProperty("Value").setValue(getReroll());
				agi.getItemProperty("Value").setValue(getReroll());
				wis.getItemProperty("Value").setValue(getReroll());
				
			}
		});

		TextField name = new TextField("Character Name");
		name.setRequired(true);
		name.setWidth("200px");
		
		Button save = new Button("Save");
		save.addStyleName("primary");
		save.setIcon(FontAwesome.SAVE);
		save.setWidth("200px");
		save.addClickListener(new ClickListener() {
			
			@SuppressWarnings("unchecked")
			@Override
			public void buttonClick(ClickEvent event) {
				int istr = (int) str.getItemProperty("Value").getValue();
				int icon = (int) con.getItemProperty("Value").getValue();
				int inte = (int) nte.getItemProperty("Value").getValue();
				int iagi = (int) agi.getItemProperty("Value").getValue();
				int iwis = (int) wis.getItemProperty("Value").getValue();
				
				if((istr != 0) && (icon != 0) && (inte != 0) && (iagi != 0) && (iwis != 0)){
					if(name.isEmpty()){
						Notification.show("The name is required");
					}else{
						String cName = name.getValue();
						if(findDuplicates(cName)){
							Notification.show("Name is duplicated");
						}else{
							Object savedAttrId = savedAttr.addItem();
							Item nSavAttr = savedAttr.getItem(savedAttrId);
							nSavAttr.getItemProperty("Name").setValue(cName);
							nSavAttr.getItemProperty("Strenght").setValue(istr);
							nSavAttr.getItemProperty("Constitution").setValue(icon);
							nSavAttr.getItemProperty("Intelligence").setValue(inte);
							nSavAttr.getItemProperty("Agility").setValue(iagi);
							nSavAttr.getItemProperty("Wisdom").setValue(iwis);
							name.setValue("");
							Notification.show("Character saved!");
						}
					}
				}else{
					Notification.show("You must generate a character first");
				}
				
			}
		});
		
		butLay.addComponent(butLabel);
		butLay.addComponent(reroll);
		butLay.addComponent(save);
		butLay.addComponent(name);
		
		topHorLay.addComponent(attr);
		topHorLay.addComponent(butLay);
		
		layout.addComponent(topHorLay);
		layout.addComponent(savedAttr);
	}
	
	@SuppressWarnings("unchecked")
	private void createCharacterTable()
	{
		Object strItemId = attr.addItem();
		str = attr.getItem(strItemId);
		str.getItemProperty("Attribute").setValue("STR");
		str.getItemProperty("Value").setValue(0);
		
		Object conItemId = attr.addItem();
		con = attr.getItem(conItemId);
		con.getItemProperty("Attribute").setValue("CON");
		con.getItemProperty("Value").setValue(0);

		Object nteItemId = attr.addItem();
		nte = attr.getItem(nteItemId);
		nte.getItemProperty("Attribute").setValue("INT");
		nte.getItemProperty("Value").setValue(0);
	
		Object agiItemId = attr.addItem();
		agi = attr.getItem(agiItemId);
		agi.getItemProperty("Attribute").setValue("AGI");
		agi.getItemProperty("Value").setValue(0);

		Object wisItemId = attr.addItem();
		wis = attr.getItem(wisItemId);
		wis.getItemProperty("Attribute").setValue("WIS");
		wis.getItemProperty("Value").setValue(0);
	
	}
	
	private int getReroll(){
		return rnd.nextInt(19)+1;
	}
	
	private boolean findDuplicates(String newName){
		for(Iterator i = savedAttr.getItemIds().iterator(); i.hasNext();){
			
			int iid = (Integer) i.next();
			Item item = savedAttr.getItem(iid);
			String curName = (String) item.getItemProperty("Name").getValue();
			
			if(newName.toLowerCase().equals(curName.toLowerCase())){
				return true;
			}
			
		}
		return false;
	}
}

vaadinappexample.scss

@import "../valo/valo.scss";

@mixin vaadinappexample {
  @include valo;

.v-table-cell-content-green {
    background: #33BB00;
    color: #FFFFFF;
}

.v-table-cell-content-orange {
    background: #FCB724;
    color: #FFFFFF;
}

.v-table-cell-content-red {
    background: #FF0000;
    color: #FFFFFF;
}

}

7. Running the example

Right click on the project folder and choose Run as -> Run on server choose Tomcat 8 server and hit finish.

8. Results

3 Vaadin Example Application
3 Vaadin Example Application

9. Download the Source Code

This was an example of: Vaadin Application.

Download
You can download the Eclipse project here: VaadinApplicationExample

Jesus Boadas

I'm a self taught programmer, I began programming back in 1991 using an IBM A10 mainframe with Pascal an Assembler IBM 360/70 emulator and Turbo C on a X86 PC, since that I work for the banking industry with emerging technologies like Fox Pro, Visual Fox Pro, Visual Basic, Visual C++, Borland C++, lately I moved out to the Airline industry, leading designing and programming in-house web applications with Flex, Actionscript, PHP, Python and Rails and in the last 7 years I focused all my work in Java, working on Linux servers using GlassFish, TomCat, Apache and MySql.
Subscribe
Notify of
guest

This site uses Akismet to reduce spam. Learn how your comment data is processed.

0 Comments
Inline Feedbacks
View all comments
Back to top button