Theme:
Description & Source Code
  • Description
  • XML & Java Source
    spreadsheet_functionalities
    SpreadsheetComposer.java
    Year.java
    Quarter.java
    Month.java
    SpreadsheetDataModel.java

The ZK grid component is enriched with spreadsheet functionalities such as frozen columns, in place editing, and merging the cells in grid. In this demo, the first three columns are frozen and cells are merged to layout the grid data.

To freeze columns, simply declare the number of frozen columns needed starting from the left hand side; in the case of this demo: <frozen columns="3">.

To merge cells in grid, declare a cell component and specify the rowspan and colspan with respect to the number of cells you wish to merge vertically, or horizontally.

Since ZK 6, all input components (intbox, combobox, etc.) support in-place editing. To enable this feature, simply set inplace="true" in the input component tags.

<?taglib uri="http://www.zkoss.org/dsp/web/core" prefix="c" ?>
<zk>
	<style src="/widgets/grid/spreadsheet_functionalities/Style.css" />
	<div apply="demo.grid.spreadsheet_functionalities.SpreadsheetComposer">
		<grid sclass="grid-spreadsheet" height="350px" width="817px"
			model="${$composer.months}">
			<frozen style="background: #DFDED8" columns="3">
				<div style="padding: 0 10px;" />
			</frozen>
			<columns>
				<column sclass="header" label="Year" width="80px" />
				<column sclass="header" label="Season" width="80px" />
				<column sclass="header last" label="Month" width="80px" />
				<column style="text-align:right;"
					forEach="${$composer.days}" width="80px"
					label="${forEachStatus.index + 1}" />
			</columns>
			<template name="model">
				<row>
					<cell sclass="years" rowspan="12"
						if="${each.firstMonthOfTheYear}">
						<label value="${each.quarter.year.name}" />
					</cell>

					<cell sclass="season" rowspan="3"
						if="${each.firstMonthOfTheQuarter}">
						<label value="${each.quarter.name}" />
					</cell>

					<cell sclass="month last">
						<label value="${each.name}" />
					</cell>

					<intbox forEach="${$composer.days}"
						format="#,###"
						constraint="no empty"
						inplace="true"
						width="55px"
						value="${each.days[forEachStatus.index] }"
						style="${each.days[forEachStatus.index] lt 0 ? 'color:red;text-align:right' : 'color:#373842;text-align:right'}"
						if="${each.numberOfDays gt forEachStatus.index}" />
				</row>
			</template>

		</grid>
	</div>
</zk>
package demo.grid.spreadsheet_functionalities;

import org.zkoss.zk.ui.Component;
import org.zkoss.zk.ui.select.SelectorComposer;
import org.zkoss.zul.ListModel;
import org.zkoss.zul.ListModelList;

public class SpreadsheetComposer extends SelectorComposer<Component> {
	/**
	 * 
	 */
	private static final long serialVersionUID = -625303546085696587L;
	
	private final SpreadsheetDataModel sdm = new SpreadsheetDataModel();
	
	public ListModel<Month> getMonths() {
		return new ListModelList<Month>(sdm.getMonths(), true);
	}
	
	public String[] getDays() {
		return new String[31];
	}
}
package demo.grid.spreadsheet_functionalities;

import java.util.ArrayList;
import java.util.List;

public class Year {
	
	private final List<Quarter> quarters = new ArrayList<Quarter>() {
		/**
		 * 
		 */
		private static final long serialVersionUID = -2265572068539812010L;

		{
			add(new Quarter(Year.this, 1));
			add(new Quarter(Year.this, 2));
			add(new Quarter(Year.this, 3));
			add(new Quarter(Year.this, 4));
		}
	};
	
	private final int year;
	
	public Year(int year) {
		this.year = year;
	}
	
	public List<Quarter> getQuarters() {
		return quarters;
	}
	
	public int getName() {
		return year;
	}
}
package demo.grid.spreadsheet_functionalities;

import java.util.ArrayList;
import java.util.List;

public class Quarter {
	
	private final String name;
	private final List<Month> months = new ArrayList<Month>();
	private final Year year;
	
	public Quarter(Year year, int quarter) {
		int start = (quarter - 1) * 3;
		
		for(int i=start; i< start+3; i++) {
			months.add(new Month(this, i));
		}
		
		this.name = String.format("Q%d", quarter);
		this.year = year;
	}
	
	public String getName() {
		return name;
	}
	
	public Year getYear() {
		return year;
	}
	
	public List<Month> getMonths() {
		return months;
	}
	
}
package demo.grid.spreadsheet_functionalities;

import java.text.SimpleDateFormat;
import java.util.Calendar;

public class Month {
	
	public static final int MAXIMUMDAYS = 31;
	
	private final Calendar calendar = Calendar.getInstance();
	private final SimpleDateFormat sdf = new SimpleDateFormat("MMM");
	private final String monthlyData[] = new String[MAXIMUMDAYS];
	private final Quarter quarter;
	
	
	public Month(Quarter quarter, int month) {
		calendar.set(Calendar.MONTH, month);
		
		int totalDays = getNumberOfDays();
		final java.util.Random random = new java.util.Random();
		
		for(int i=0; i<totalDays; i++) {
			int data = random.nextInt(10) == 5 ? 0 - random.nextInt(65536) : random.nextInt(65536);
			monthlyData[i] = Integer.toString(data);
		}
		
		this.quarter = quarter;
	}
	
	public int getNumberOfDays() {
		return calendar.getActualMaximum(Calendar.DAY_OF_MONTH);
	}
	
	public String getName() {
		return sdf.format(calendar.getTime());
	}
	
	public String[] getDays() {
		return monthlyData;
	}
	
	public Quarter getQuarter() {
		return this.quarter;
	}
	
	public boolean isFirstMonthOfTheQuarter() {
		return (calendar.get(Calendar.MONTH) % 3) == 0;
	}
	
	public boolean isFirstMonthOfTheYear() {
		return calendar.get(Calendar.MONTH) == Calendar.JANUARY;
	}
}
package demo.grid.spreadsheet_functionalities;

import java.util.ArrayList;
import java.util.List;

public class SpreadsheetDataModel {
	
	private final List<Year> years = new ArrayList<Year>() {
		/**
		 * 
		 */
		private static final long serialVersionUID = -2265572068539812010L;

		{
			add(new Year(2011));

		}
	};
	
	public List<Year> getYears() {
		return years;
	}
	
	public List<Month> getMonths() {
		List<Month> allMonths = new ArrayList<Month>();
		
		for(Year yr : getYears()) {
			for(Quarter q : yr.getQuarters()) {
				allMonths.addAll(q.getMonths());
			}
		}
		
		return allMonths;
	}
}