di-friendly (no-arg constructors); ui binding stuff
diff --git a/NatTable/bnd.bnd b/NatTable/bnd.bnd
index 472b24b..2578a9f 100644
--- a/NatTable/bnd.bnd
+++ b/NatTable/bnd.bnd
@@ -23,6 +23,7 @@
 	org.eclipse.core.commands.source,\
 	com.google.guava,\
 	com.springsource.org.junit,\
-	osgi.core
+	osgi.core,\
+	javax.inject
 
 -sub: *.bnd
diff --git a/NatTable/renderer.swt.bnd b/NatTable/renderer.swt.bnd
index 19aaa80..45325d2 100644
--- a/NatTable/renderer.swt.bnd
+++ b/NatTable/renderer.swt.bnd
@@ -1,4 +1,7 @@
 Export-Package: org.eclipse.nebula.widgets.nattable.renderer.swt,\
+	org.eclipse.nebula.widgets.nattable.renderer.swt.event,\
+	org.eclipse.nebula.widgets.nattable.renderer.swt.event.action,\
+	org.eclipse.nebula.widgets.nattable.renderer.swt.event.mode,\
 	org.eclipse.nebula.widgets.nattable.renderer.swt.layer,\
 	org.eclipse.nebula.widgets.nattable.renderer.swt.layer.cell,\
 	org.eclipse.nebula.widgets.nattable.renderer.swt.layer.cell.impl,\
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/InjectorExtensions.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/InjectorExtensions.xtend
new file mode 100644
index 0000000..73b06e5
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/InjectorExtensions.xtend
@@ -0,0 +1,14 @@
+package org.eclipse.nebula.widgets.nattable.core
+
+import com.google.inject.Injector
+import javax.inject.Inject
+
+class InjectorExtensions {
+	
+	@Inject Injector injector
+	
+	def <T> create(Class<T> clazz) {
+		injector.getInstance(clazz)
+	}
+	
+}
\ No newline at end of file
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/LayerInvariants.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/LayerInvariants.xtend
index b6bed44..7acba78 100644
--- a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/LayerInvariants.xtend
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/LayerInvariants.xtend
@@ -55,7 +55,7 @@
 		layer.verticalAxis.pixelSize
 	}
 	
-	def static getRowPostionOfYPixel(Layer layer, int yPixel) {
+	def static getRowPositionOfYPixel(Layer layer, int yPixel) {
 		layer.verticalAxis.getSegmentPositionOfPixelLocation(yPixel)
 	}
 	
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/axis/impl/AxisImpl.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/axis/impl/AxisImpl.xtend
index 0f8b958..2592a4c 100644
--- a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/axis/impl/AxisImpl.xtend
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/axis/impl/AxisImpl.xtend
@@ -15,8 +15,18 @@
 	int defaultSegmentSize
 	val segmentSizeMap = new TreeMap<Integer, Integer>  // segment Position -> pixel size
 	
+	new() {}
+	
 	new(int segmentCount, int defaultSegmentSize) {
+		setSegmentCount(segmentCount)
+		setDefaultSegmentSize(defaultSegmentSize)
+	}
+	
+	def void setSegmentCount(int segmentCount) {
 		this.segmentCount = segmentCount
+	}
+	
+	def void setDefaultSegmentSize(int defaultSegmentSize) {
 		this.defaultSegmentSize = defaultSegmentSize
 	}
 	
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/axis/impl/hideshow/HideShowAxis.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/axis/impl/hideshow/HideShowAxis.xtend
index ffb73d8..53d760b 100644
--- a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/axis/impl/hideshow/HideShowAxis.xtend
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/axis/impl/hideshow/HideShowAxis.xtend
@@ -10,11 +10,18 @@
 
 class HideShowAxis implements Axis {
 	
-	val Axis underlyingAxis
 	val SortedMap<Integer, Serializable> hiddenSegmentPositionToIdMap = new TreeMap
 	val Map<Integer, Integer> segmentPositionToStartPixelMap = newHashMap
 	
+	Axis underlyingAxis
+	
+	new() {}
+	
 	new(Axis underlyingAxis) {
+		setUnderlyingAxis(underlyingAxis)
+	}
+	
+	def void setUnderlyingAxis(Axis underlyingAxis) {
 		this.underlyingAxis = underlyingAxis
 	}
 	
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/axis/impl/reorder/ReorderAxis.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/axis/impl/reorder/ReorderAxis.xtend
index dcb1bb0..6eab87d 100644
--- a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/axis/impl/reorder/ReorderAxis.xtend
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/axis/impl/reorder/ReorderAxis.xtend
@@ -9,11 +9,18 @@
 
 class ReorderAxis implements Axis {
 	
-	val Axis underlyingAxis
 	val List<Serializable> reorderedSegmentIds = newArrayList
 	val Map<Integer, Integer> segmentPositionToStartPixelMap = newHashMap
 	
+	Axis underlyingAxis
+	
+	new() {}
+	
 	new(Axis underlyingAxis) {
+		setUnderlyingAxis(underlyingAxis)
+	}
+	
+	def void setUnderlyingAxis(Axis underlyingAxis) {
 		this.underlyingAxis = underlyingAxis
 		
 		for (segmentPosition : 0 ..< underlyingAxis.segmentCount)
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/DimensionallyDependentLayer.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/DimensionallyDependentLayer.xtend
index b2c47df..56a8769 100644
--- a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/DimensionallyDependentLayer.xtend
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/DimensionallyDependentLayer.xtend
@@ -6,13 +6,27 @@
 
 class DimensionallyDependentLayer extends AbstractLayer {
 	
-	val Axis horizontalAxis
-	val Axis verticalAxis
-	val LayerDataAccessor layerDataAccessor
+	Axis horizontalAxis
+	Axis verticalAxis
+	LayerDataAccessor layerDataAccessor
+	
+	new() {}
 	
 	new(Axis horizontalAxis, Axis verticalAxis, LayerDataAccessor layerDataAccessor) {
+		setHorizontalAxis(horizontalAxis)
+		setVerticalAxis(verticalAxis)
+		setLayerDataAccessor(layerDataAccessor)
+	}
+	
+	def void setHorizontalAxis(Axis horizontalAxis) {
 		this.horizontalAxis = horizontalAxis
+	}
+	
+	def void setVerticalAxis(Axis verticalAxis) {
 		this.verticalAxis = verticalAxis
+	}
+	
+	def void setLayerDataAccessor(LayerDataAccessor layerDataAccessor) {
 		this.layerDataAccessor = layerDataAccessor
 	}
 	
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/DummyLayer.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/DummyLayer.xtend
index 8bfb4a0..eff6162 100644
--- a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/DummyLayer.xtend
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/DummyLayer.xtend
@@ -8,11 +8,21 @@
  */
 class DummyLayer extends AbstractLayer {
 
-	val Axis horizontalAxis
-	val Axis verticalAxis
+	Axis horizontalAxis
+	Axis verticalAxis
+
+	new() {}
 
 	new(Axis horizontalAxis, Axis verticalAxis) {
+		setHorizontalAxis(horizontalAxis)
+		setVerticalAxis(verticalAxis)
+	}
+
+	def void setHorizontalAxis(Axis horizontalAxis) {
 		this.horizontalAxis = horizontalAxis
+	}
+	
+	def void setVerticalAxis(Axis verticalAxis) {
 		this.verticalAxis = verticalAxis
 	}
 	
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/LayerDataAccessorImpl.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/LayerDataAccessorImpl.xtend
index 7e4ec35..c3920a8 100644
--- a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/LayerDataAccessorImpl.xtend
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/LayerDataAccessorImpl.xtend
@@ -8,15 +8,25 @@
 
 class LayerDataAccessorImpl implements LayerDataAccessor {
 	
-	val LayerDataReadAccessor layerDataReadAccessor
-	val LayerDataWriteAccessor layerDataWriteAccessor
+	LayerDataReadAccessor layerDataReadAccessor
+	LayerDataWriteAccessor layerDataWriteAccessor
 	
-	new(LayerDataReadAccessor readDataAccessor) {
-		this(readDataAccessor, null)
+	new() {}
+	
+	new(LayerDataReadAccessor layerDataReadAccessor) {
+		this(layerDataReadAccessor, null)
 	}
 	
 	new(LayerDataReadAccessor layerDataReadAccessor, LayerDataWriteAccessor layerDataWriteAccessor) {
+		setLayerDataReadAccessor(layerDataReadAccessor)
+		setLayerDataWriteAccessor(layerDataWriteAccessor)
+	}
+	
+	def void setLayerDataReadAccessor(LayerDataReadAccessor layerDataReadAccessor) {
 		this.layerDataReadAccessor = layerDataReadAccessor
+	}
+	
+	def void setLayerDataWriteAccessor(LayerDataWriteAccessor layerDataWriteAccessor) {
 		this.layerDataWriteAccessor = layerDataWriteAccessor
 	}
 	
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/ListRowDataLayer.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/ListRowDataLayer.xtend
index 0215096..7885145 100644
--- a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/ListRowDataLayer.xtend
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/ListRowDataLayer.xtend
@@ -1,6 +1,5 @@
 package org.eclipse.nebula.widgets.nattable.core.layer.impl
 
-import com.google.inject.Inject
 import java.util.List
 import org.eclipse.nebula.widgets.nattable.core.data.ObjectPropertyAccessor
 import org.eclipse.nebula.widgets.nattable.core.layer.axis.Axis
@@ -12,19 +11,34 @@
  */
 class ListRowDataLayer extends AbstractLayer {
 	
-	val List<?> list
+	List<?> list
 	
-	val Axis horizontalAxis
-	val Axis verticalAxis
+	Axis horizontalAxis
+	Axis verticalAxis
 	
-	@Inject extension ObjectPropertyAccessor
+	extension ObjectPropertyAccessor
 	
-	new(List<?> list, Axis horizontalAxis) {
+	new() {}
+	
+	new(List<?> list, Axis horizontalAxis, ObjectPropertyAccessor objectPropertyAccessor) {
+		setList(list)
+		setHorizontalAxis(horizontalAxis)
+		setObjectPropertyAccessor(objectPropertyAccessor)
+	}
+	
+	def void setList(List<?> list) {
 		this.list = list
-		this.horizontalAxis = horizontalAxis
 		this.verticalAxis = new AxisImpl(list.size, 20)
 	}
 	
+	def void setHorizontalAxis(Axis horizontalAxis) {
+		this.horizontalAxis = horizontalAxis
+	}
+	
+	def void setObjectPropertyAccessor(ObjectPropertyAccessor objectPropertyAccessor) {
+		this._objectPropertyAccessor = objectPropertyAccessor
+	}
+	
 	// Layer interface
 	
 	override getHorizontalAxis() { horizontalAxis }
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/header/ColumnHeaderLayer.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/header/ColumnHeaderLayer.xtend
index e51a4c1..32a0042 100644
--- a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/header/ColumnHeaderLayer.xtend
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/header/ColumnHeaderLayer.xtend
@@ -11,13 +11,25 @@
  */
 class ColumnHeaderLayer extends AbstractLayer {
 	
-	val Axis horizontalAxis
+	Axis horizontalAxis
 	val Axis verticalAxis
-	val LayerDataAccessor layerDataAccessor
+	LayerDataAccessor layerDataAccessor
+	
+	new() {
+		verticalAxis = new AxisImpl(1, 20)
+	}
 	
 	new(Axis horizontalAxis, LayerDataAccessor layerDataAccessor) {
+		this()
+		setHorizontalAxis(horizontalAxis)
+		setLayerDataAccessor(layerDataAccessor)
+	}
+	
+	def void setHorizontalAxis(Axis horizontalAxis) {
 		this.horizontalAxis = horizontalAxis
-		this.verticalAxis = new AxisImpl(1, 20)
+	}
+	
+	def void setLayerDataAccessor(LayerDataAccessor layerDataAccessor) {
 		this.layerDataAccessor = layerDataAccessor
 	}
 	
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/header/RowHeaderLayer.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/header/RowHeaderLayer.xtend
index ae9ee5c..abb60cf 100644
--- a/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/header/RowHeaderLayer.xtend
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/core/layer/impl/header/RowHeaderLayer.xtend
@@ -12,12 +12,24 @@
 class RowHeaderLayer extends AbstractLayer {
 	
 	val Axis horizontalAxis
-	val Axis verticalAxis
-	val LayerDataAccessor layerDataAccessor
+	Axis verticalAxis
+	LayerDataAccessor layerDataAccessor
+	
+	new() {
+		this.horizontalAxis = new AxisImpl(1, 20)
+	}
 	
 	new(Axis verticalAxis, LayerDataAccessor layerDataAccessor) {
-		this.horizontalAxis = new AxisImpl(1, 20)
+		this()
+		setVerticalAxis(verticalAxis)
+		setLayerDataAccessor(layerDataAccessor)
+	}
+	
+	def void setVerticalAxis(Axis verticalAxis) {
 		this.verticalAxis = verticalAxis
+	}
+	
+	def void setLayerDataAccessor(LayerDataAccessor layerDataAccessor) {
 		this.layerDataAccessor = layerDataAccessor
 	}
 	
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/SWTNatTable.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/SWTNatTable.xtend
index 141a61e..536c3ac 100644
--- a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/SWTNatTable.xtend
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/SWTNatTable.xtend
@@ -1,18 +1,27 @@
 package org.eclipse.nebula.widgets.nattable.renderer.swt
 
+import javax.inject.Inject
+import org.eclipse.nebula.widgets.nattable.core.InjectorExtensions
 import org.eclipse.nebula.widgets.nattable.core.layer.Layer
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.mode.Mode
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.mode.ModeSwitcher
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.mode.NormalMode
 import org.eclipse.nebula.widgets.nattable.renderer.swt.layer.impl.GridLineCellLayerRenderer
 import org.eclipse.swt.SWT
 import org.eclipse.swt.events.DisposeEvent
+import org.eclipse.swt.events.KeyEvent
+import org.eclipse.swt.events.KeyListener
 import org.eclipse.swt.events.PaintEvent
 import org.eclipse.swt.graphics.GC
 import org.eclipse.swt.widgets.Canvas
 import org.eclipse.swt.widgets.Composite
 
-class SWTNatTable extends Canvas {
+class SWTNatTable extends Canvas implements KeyListener {
 
 	static val int DEFAULT_STYLE_OPTIONS = SWT::NO_BACKGROUND.bitwiseOr(SWT::NO_REDRAW_RESIZE).bitwiseOr(SWT::DOUBLE_BUFFERED).bitwiseOr(SWT::V_SCROLL).bitwiseOr(SWT::H_SCROLL)
 	static val defaultLayerRenderer = new GridLineCellLayerRenderer
+	
+	@Inject extension InjectorExtensions
 
 	Layer layer
 
@@ -30,15 +39,29 @@
 		this.layer = layer
 		
 		addPaintListener([ PaintEvent event | renderLayer(event.gc) ])
-		addDisposeListener([ DisposeEvent event | layer.layerRenderer.dispose ])
+		addDisposeListener([ DisposeEvent event | layer?.layerRenderer?.dispose ])
+		
+		val modeSwitcher = new ModeSwitcher(this)
+		modeSwitcher.registerMode(Mode::NORMAL, create(typeof(NormalMode)))
+		modeSwitcher.switchToMode(Mode::NORMAL)
 	}
 	
 	private def renderLayer(GC gc) {
-		layer.layerRenderer.renderLayer(layer, gc)
+		layer?.layerRenderer?.renderLayer(layer, gc)
 	}
 	
 	private def getLayerRenderer(Layer layer) {
 		defaultLayerRenderer
 	}
 	
+	// KeyListener interface
+	
+	override keyPressed(KeyEvent event) {
+		println('''keyPressed «event»''')
+	}
+	
+	override keyReleased(KeyEvent event) {
+		println('''keyReleased «event»''')
+	}
+	
 }
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/action/DragAction.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/action/DragAction.xtend
new file mode 100644
index 0000000..d8f584e
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/action/DragAction.xtend
@@ -0,0 +1,11 @@
+package org.eclipse.nebula.widgets.nattable.renderer.swt.event.action
+
+import org.eclipse.swt.events.MouseEvent
+
+interface DragAction {
+	
+	def void mouseDown(MouseEvent event)
+	def void mouseMove(MouseEvent event)
+	def void mouseUp(MouseEvent event)
+	
+}
\ No newline at end of file
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/action/KeyAction.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/action/KeyAction.xtend
new file mode 100644
index 0000000..dee02b6
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/action/KeyAction.xtend
@@ -0,0 +1,9 @@
+package org.eclipse.nebula.widgets.nattable.renderer.swt.event.action
+
+import org.eclipse.swt.events.KeyEvent
+
+interface KeyAction {
+	
+	def void run(KeyEvent event)
+	
+}
\ No newline at end of file
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/action/MouseAction.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/action/MouseAction.xtend
new file mode 100644
index 0000000..9bf3f42
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/action/MouseAction.xtend
@@ -0,0 +1,9 @@
+package org.eclipse.nebula.widgets.nattable.renderer.swt.event.action
+
+import org.eclipse.swt.events.MouseEvent
+
+interface MouseAction {
+	
+	def void run(MouseEvent event)
+
+}
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/action/packageinfo b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/action/packageinfo
new file mode 100644
index 0000000..a4f1546
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/action/packageinfo
@@ -0,0 +1 @@
+version 1.0
\ No newline at end of file
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/binding/DragBinding.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/binding/DragBinding.xtend
new file mode 100644
index 0000000..162a75d
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/binding/DragBinding.xtend
@@ -0,0 +1,12 @@
+package org.eclipse.nebula.widgets.nattable.renderer.swt.event.binding
+
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.action.DragAction
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.matcher.MouseEventMatcher
+
+@Data
+class DragBinding {
+	
+	MouseEventMatcher matcher
+	DragAction action
+	
+}
\ No newline at end of file
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/binding/KeyBinding.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/binding/KeyBinding.xtend
new file mode 100644
index 0000000..7ad2e40
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/binding/KeyBinding.xtend
@@ -0,0 +1,12 @@
+package org.eclipse.nebula.widgets.nattable.renderer.swt.event.binding
+
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.action.KeyAction
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.matcher.KeyEventMatcher
+
+@Data
+class KeyBinding {
+
+	KeyEventMatcher matcher
+	KeyAction action
+	
+}
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/binding/MouseBinding.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/binding/MouseBinding.xtend
new file mode 100644
index 0000000..ce92536
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/binding/MouseBinding.xtend
@@ -0,0 +1,12 @@
+package org.eclipse.nebula.widgets.nattable.renderer.swt.event.binding
+
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.action.MouseAction
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.matcher.MouseEventMatcher
+
+@Data
+class MouseBinding {
+
+	MouseEventMatcher matcher
+	MouseAction action
+	
+}
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/binding/UiBindings.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/binding/UiBindings.xtend
new file mode 100644
index 0000000..a4de09c
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/binding/UiBindings.xtend
@@ -0,0 +1,20 @@
+package org.eclipse.nebula.widgets.nattable.renderer.swt.event.binding
+
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.action.DragAction
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.action.KeyAction
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.action.MouseAction
+import org.eclipse.swt.events.KeyEvent
+import org.eclipse.swt.events.MouseEvent
+
+interface UiBindings {
+	
+	def KeyAction getKeyEventAction(KeyEvent event)
+	
+	def MouseAction getMouseDownAction(MouseEvent event)
+	def MouseAction getMouseMoveAction(MouseEvent event)
+	def DragAction getDragAction(MouseEvent event)
+	
+	def MouseAction getSingleClickAction(MouseEvent event)
+	def MouseAction getDoubleClickAction(MouseEvent event)
+	
+}
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/binding/UiBindingsImpl.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/binding/UiBindingsImpl.xtend
new file mode 100644
index 0000000..5881606
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/binding/UiBindingsImpl.xtend
@@ -0,0 +1,48 @@
+package org.eclipse.nebula.widgets.nattable.renderer.swt.event.binding
+
+import java.util.LinkedList
+import org.eclipse.swt.events.KeyEvent
+import org.eclipse.swt.events.MouseEvent
+
+class UiBindingsImpl implements UiBindings {
+	
+	val keyBindings = new LinkedList<KeyBinding>
+	val mouseMoveBindings = new LinkedList<MouseBinding>
+	val mouseDownBindings = new LinkedList<MouseBinding>
+	val singleClickBindings = new LinkedList<MouseBinding>
+	val doubleClickBindings = new LinkedList<MouseBinding>
+	val dragBindings = new LinkedList<DragBinding>
+	
+	def getKeyBindings() { keyBindings }
+	def getMouseMoveBindings() { mouseMoveBindings }
+	def getMouseDownBindings() { mouseDownBindings }
+	def getSingleClickBindings() { singleClickBindings }
+	def getDoubleClickBindings() { doubleClickBindings }
+	
+	// Lookup /////////////////////////////////////////////////////////////////
+	
+	override getKeyEventAction(KeyEvent event) {
+		keyBindings.findFirst([ matcher.matches(event) ])?.action
+	}
+	
+	override getMouseMoveAction(MouseEvent event) {
+		mouseMoveBindings.findFirst([ matcher.matches(event) ])?.action
+	}
+	
+	override getMouseDownAction(MouseEvent event) {
+		mouseDownBindings.findFirst([ matcher.matches(event) ])?.action
+	}
+	
+	override getSingleClickAction(MouseEvent event) {
+		singleClickBindings.findFirst([ matcher.matches(event) ])?.action
+	}
+	
+	override getDoubleClickAction(MouseEvent event) {
+		doubleClickBindings.findFirst([ matcher.matches(event) ])?.action
+	}
+	
+	override getDragAction(MouseEvent event) {
+		dragBindings.findFirst([ matcher.matches(event) ])?.action
+	}
+	
+}
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/matcher/KeyEventMatcher.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/matcher/KeyEventMatcher.xtend
new file mode 100644
index 0000000..e4ae9f4
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/matcher/KeyEventMatcher.xtend
@@ -0,0 +1,9 @@
+package org.eclipse.nebula.widgets.nattable.renderer.swt.event.matcher
+
+import org.eclipse.swt.events.KeyEvent
+
+interface KeyEventMatcher {
+	
+	def boolean matches(KeyEvent event)
+	
+}
\ No newline at end of file
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/matcher/MouseEventMatcher.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/matcher/MouseEventMatcher.xtend
new file mode 100644
index 0000000..32610e9
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/matcher/MouseEventMatcher.xtend
@@ -0,0 +1,9 @@
+package org.eclipse.nebula.widgets.nattable.renderer.swt.event.matcher
+
+import org.eclipse.swt.events.MouseEvent
+
+interface MouseEventMatcher {
+	
+	def boolean matches(MouseEvent event)
+	
+}
\ No newline at end of file
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/AbstractMode.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/AbstractMode.xtend
new file mode 100644
index 0000000..d343fb0
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/AbstractMode.xtend
@@ -0,0 +1,31 @@
+package org.eclipse.nebula.widgets.nattable.renderer.swt.event.mode
+
+import org.eclipse.swt.events.FocusEvent
+import org.eclipse.swt.events.KeyEvent
+import org.eclipse.swt.events.MouseEvent
+
+class AbstractMode implements Mode {
+
+	private ModeSwitcher modeSwitcher
+	
+	override setModeSwitcher(ModeSwitcher modeSwitcher) {
+		this.modeSwitcher = modeSwitcher
+	}
+	
+	protected def switchToMode(String modeName) { modeSwitcher.switchToMode(modeName) }
+	protected def void switchToMode(Mode mode) { modeSwitcher.switchToMode(mode) }
+	
+	// ModalEventHandler interface
+	
+	override keyPressed(KeyEvent event) {}
+	override keyReleased(KeyEvent event) {}
+	override mouseDoubleClick(MouseEvent event) {}
+	override mouseDown(MouseEvent event) {}
+	override mouseUp(MouseEvent event) {}
+	override mouseMove(MouseEvent event) {}
+	override focusGained(FocusEvent event) {}
+	override focusLost(FocusEvent event) {
+		switchToMode(Mode::NORMAL)
+	}
+
+}
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/DragMode.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/DragMode.xtend
new file mode 100644
index 0000000..19b9408
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/DragMode.xtend
@@ -0,0 +1,23 @@
+package org.eclipse.nebula.widgets.nattable.renderer.swt.event.mode
+
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.action.DragAction
+import org.eclipse.swt.events.MouseEvent
+
+class DragMode extends AbstractMode {
+
+	val DragAction dragAction
+	
+	new(DragAction dragMode) {
+		this.dragAction = dragMode
+	}
+	
+	override mouseMove(MouseEvent event) {
+		dragAction.mouseMove(event)
+	}
+	
+	override mouseUp(MouseEvent event) {
+		dragAction.mouseUp(event)
+		switchToMode(Mode::NORMAL)
+	}
+	
+}
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/Mode.java b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/Mode.java
new file mode 100644
index 0000000..cc2b87f
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/Mode.java
@@ -0,0 +1,14 @@
+package org.eclipse.nebula.widgets.nattable.renderer.swt.event.mode;
+
+import org.eclipse.swt.events.FocusListener;
+import org.eclipse.swt.events.KeyListener;
+import org.eclipse.swt.events.MouseListener;
+import org.eclipse.swt.events.MouseMoveListener;
+
+public interface Mode extends KeyListener, MouseListener, MouseMoveListener, FocusListener {
+	
+	static final String NORMAL = "NORMAL_MODE";
+	
+	void setModeSwitcher(ModeSwitcher modeSwitcher);
+	
+}
\ No newline at end of file
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/ModeSwitcher.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/ModeSwitcher.xtend
new file mode 100644
index 0000000..13ba737
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/ModeSwitcher.xtend
@@ -0,0 +1,83 @@
+package org.eclipse.nebula.widgets.nattable.renderer.swt.event.mode
+
+import java.util.Map
+import org.eclipse.swt.events.FocusEvent
+import org.eclipse.swt.events.FocusListener
+import org.eclipse.swt.events.KeyEvent
+import org.eclipse.swt.events.KeyListener
+import org.eclipse.swt.events.MouseEvent
+import org.eclipse.swt.events.MouseListener
+import org.eclipse.swt.events.MouseMoveListener
+import org.eclipse.swt.widgets.Control
+
+/**
+ * Modal event handler for NatTable. This class acts as a proxy event listener.
+ * It manages a set of IModeEventHandler instances which control the actual
+ * event handling for a given mode. This allows the event handling behavior for
+ * different modes to be grouped together and isolated from each other.
+ */
+class ModeSwitcher implements KeyListener, MouseListener, MouseMoveListener, FocusListener {
+
+	val Map<String, Mode> modalEventHandlerMap = newHashMap
+
+	Mode currentMode
+
+	new(Control control) {
+		control.addKeyListener(this)
+		control.addMouseListener(this)
+		control.addMouseMoveListener(this)
+		control.addFocusListener(this)
+	}
+
+	/**
+	 * Register an event handler to handle events for a given mode.
+	 * 
+	 * @param mode
+	 *            The mode.
+	 * @param modeEventHandler
+	 *            An IModeEventHandler instance that will handle events in the
+	 *            given mode.
+	 * 
+	 * @see IModeEventHandler
+	 */
+	def void registerMode(String modeName, Mode mode) {
+		modalEventHandlerMap.put(modeName, mode)
+	}
+
+	/**
+	 * Switch to the given mode.
+	 * 
+	 * @param mode
+	 *            The target mode to switch to.
+	 */
+	def void switchToMode(String modeName) {
+		currentMode = modalEventHandlerMap.get(modeName)
+		currentMode.modeSwitcher = this
+	}
+	
+	def void switchToMode(Mode mode) {
+		currentMode = mode
+		currentMode.modeSwitcher = this
+	}
+
+	// KeyListner interface
+
+	override keyPressed(KeyEvent event) { currentMode.keyPressed(event) }
+	override keyReleased(KeyEvent event) { currentMode.keyReleased(event) }
+
+	// MouseListener interface
+
+	override mouseDoubleClick(MouseEvent event) { currentMode.mouseDoubleClick(event) }
+	override mouseDown(MouseEvent event) { currentMode.mouseDown(event) }
+	override mouseUp(MouseEvent event) { currentMode.mouseUp(event) }
+	
+	// MouseMotionListener interface
+	
+	override mouseMove(MouseEvent event) { currentMode.mouseMove(event) }
+
+	// FocusListener interface
+
+	override focusGained(FocusEvent event) { currentMode.focusGained(event) }
+	override focusLost(FocusEvent event) { currentMode.focusLost(event) }
+
+}
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/MouseMode.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/MouseMode.xtend
new file mode 100644
index 0000000..07066e7
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/MouseMode.xtend
@@ -0,0 +1,91 @@
+package org.eclipse.nebula.widgets.nattable.renderer.swt.event.mode
+
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.action.DragAction
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.action.MouseAction
+import org.eclipse.swt.events.MouseEvent
+
+class MouseMode extends AbstractMode {
+	
+	MouseEvent initialMouseDownEvent
+	MouseAction singleClickAction
+	MouseAction doubleClickAction
+	boolean mouseDown
+	DragAction dragMode
+	Runnable singleClickRunnable
+	boolean doubleClick
+	
+	new(MouseEvent initialMouseDownEvent, MouseAction singleClickAction, MouseAction doubleClickAction, DragAction dragMode) {
+		mouseDown = true
+		
+		this.initialMouseDownEvent = initialMouseDownEvent
+		
+		this.singleClickAction = singleClickAction
+		this.doubleClickAction = doubleClickAction
+		this.dragMode = dragMode
+	}
+	
+	override mouseUp(MouseEvent event) {
+		mouseDown = false
+		doubleClick = false
+		
+		if (singleClickAction != null) {
+			//convert/validate/commit/close possible open editor
+			//needed in case of conversion/validation errors to cancel any action
+//			if (EditUtils.commitAndCloseActiveEditor()) {
+				if (doubleClickAction != null) {
+					// If a doubleClick action is registered, wait to see if this mouseUp is part of a doubleClick or not.
+					singleClickRunnable = [| if (!doubleClick) executeSingleClickAction(singleClickAction, event) ]
+					event.display.timerExec(event.display.getDoubleClickTime(), singleClickRunnable)
+				} else {
+					executeSingleClickAction(singleClickAction, event)
+				}
+//			}
+		} else {
+			// No single or double click action registered when mouseUp detected. Switch back to normal mode.
+			switchToMode(Mode::NORMAL)
+		}
+	}
+	
+	override mouseDoubleClick(MouseEvent event) {
+		//double click event is fired after second mouse up event, so it needs to be set to true here
+		//this way the SingleClickRunnable knows that it should not execute as a double click was performed
+		doubleClick = true
+		
+		//convert/validate/commit/close possible open editor
+		//needed in case of conversion/validation errors to cancel any action
+//		if (EditUtils.commitAndCloseActiveEditor()) {
+			if (doubleClickAction != null) {
+				doubleClickAction.run(event)
+				// Double click action complete. Switch back to normal mode.
+				switchToMode(Mode::NORMAL)
+			}
+//		}
+	}
+	
+	// synchronized
+	override void mouseMove(MouseEvent event) {
+		if (mouseDown && dragMode != null) {
+//			if (EditUtils.commitAndCloseActiveEditor()) {
+				dragMode.mouseDown(initialMouseDownEvent)
+				switchToMode(new DragMode(dragMode))
+//			}
+//			else {
+//				switchMode(ModeEnum::NORMAL)
+//			}
+		} else {
+			// No drag mode registered when mouseMove detected. Switch back to normal mode.
+			switchToMode(Mode::NORMAL)
+		}
+	}
+	
+	private def void executeSingleClickAction(MouseAction action, MouseEvent event) {
+		//convert/validate/commit/close possible open editor
+		//needed in case of conversion/validation errors to cancel any action
+//		if (EditUtils.commitAndCloseActiveEditor()) {
+			action.run(event)
+			// Single click action complete. Switch back to normal mode.
+			switchToMode(Mode::NORMAL)
+//		}
+	}
+	
+}
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/NormalMode.xtend b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/NormalMode.xtend
new file mode 100644
index 0000000..4108669
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/NormalMode.xtend
@@ -0,0 +1,52 @@
+package org.eclipse.nebula.widgets.nattable.renderer.swt.event.mode
+
+import com.google.inject.Inject
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.binding.UiBindings
+import org.eclipse.swt.events.KeyEvent
+import org.eclipse.swt.events.MouseEvent
+import org.eclipse.swt.widgets.Control
+
+class NormalMode extends AbstractMode {
+
+	@Inject UiBindings uiBindings
+
+	// Event handling /////////////////////////////////////////////////////////
+	
+	override keyPressed(KeyEvent event) {
+		val keyAction = uiBindings.getKeyEventAction(event)
+		if (keyAction != null) {
+			(event.widget as Control).forceFocus
+			keyAction.run(event)
+		}
+	}
+	
+	override mouseDown(MouseEvent event) {
+//		if (EditUtils.commitAndCloseActiveEditor()) {
+			val mouseDownAction = uiBindings.getMouseDownAction(event)
+			if (mouseDownAction != null) {
+				mouseDownAction.run(event)
+			}
+			
+			val singleClickAction = uiBindings.getSingleClickAction(event)
+			val doubleClickAction = uiBindings.getDoubleClickAction(event)
+			val dragMode = uiBindings.getDragAction(event)
+			
+			if (singleClickAction != null || doubleClickAction != null || dragMode != null) {
+				switchToMode(new MouseMode(event, singleClickAction, doubleClickAction, dragMode))
+			}
+//		}
+	}
+
+	// syncrhonized
+	override mouseMove(MouseEvent event) {
+		if (event.x >= 0 && event.y >= 0) {
+			val mouseMoveAction = uiBindings.getMouseMoveAction(event)
+			if (mouseMoveAction != null) {
+				mouseMoveAction.run(event)
+			} else {
+				(event.widget as Control).setCursor(null)
+			}
+		}
+	}
+	
+}
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/packageinfo b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/packageinfo
new file mode 100644
index 0000000..a4f1546
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/mode/packageinfo
@@ -0,0 +1 @@
+version 1.0
\ No newline at end of file
diff --git a/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/packageinfo b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/packageinfo
new file mode 100644
index 0000000..a4f1546
--- /dev/null
+++ b/NatTable/src/org/eclipse/nebula/widgets/nattable/renderer/swt/event/packageinfo
@@ -0,0 +1 @@
+version 1.0
\ No newline at end of file
diff --git a/NatTable/test/org/eclipse/nebula/widgets/nattable/renderer/swt/SWTExample.xtend b/NatTable/test/org/eclipse/nebula/widgets/nattable/renderer/swt/SWTExample.xtend
index dc1263e..8958d21 100644
--- a/NatTable/test/org/eclipse/nebula/widgets/nattable/renderer/swt/SWTExample.xtend
+++ b/NatTable/test/org/eclipse/nebula/widgets/nattable/renderer/swt/SWTExample.xtend
@@ -1,5 +1,8 @@
 package org.eclipse.nebula.widgets.nattable.renderer.swt
 
+import com.google.inject.Guice
+import com.google.inject.Injector
+import org.eclipse.nebula.widgets.nattable.core.InjectorExtensions
 import org.eclipse.nebula.widgets.nattable.core.layer.axis.impl.AxisImpl
 import org.eclipse.nebula.widgets.nattable.core.layer.axis.impl.hideshow.HideShowAxis
 import org.eclipse.nebula.widgets.nattable.core.layer.axis.impl.reorder.ReorderAxis
@@ -9,6 +12,9 @@
 import org.eclipse.nebula.widgets.nattable.core.layer.impl.composite.CompositeLayer
 import org.eclipse.nebula.widgets.nattable.core.layer.impl.header.ColumnHeaderLayer
 import org.eclipse.nebula.widgets.nattable.core.layer.impl.header.RowHeaderLayer
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.binding.KeyBinding
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.binding.UiBindings
+import org.eclipse.nebula.widgets.nattable.renderer.swt.event.binding.UiBindingsImpl
 import org.eclipse.swt.SWT
 import org.eclipse.swt.layout.FillLayout
 import org.eclipse.swt.widgets.Display
@@ -17,10 +23,18 @@
 class SWTExample {
 	
 	def static void main(String[] args) {
-		run(400, 300)
+		new SWTExample().run(400, 300)
 	}
 	
-	static def void run(int shellWidth, int shellHeight) {
+	Injector injector
+	extension InjectorExtensions
+	
+	new() {
+		injector = createInjector
+		_injectorExtensions = injector.getInstance(typeof(InjectorExtensions))
+	}
+	
+	def void run(int shellWidth, int shellHeight) {
 		val display = Display::getDefault
 		val shell = new Shell(display, SWT::SHELL_TRIM)
 		shell.setLayout(new FillLayout)
@@ -28,7 +42,7 @@
 		shell.setText("NatTable -> SWT")
 		
 		// Create example control
-		val natTable = shell.SWTNatTable
+		val natTable = createNatTable(shell)
 
 		// Start
 		shell.open
@@ -46,14 +60,12 @@
 		display.dispose
 	}
 	
-	static def getSWTNatTable(Shell shell) {
-		val natTable = new SWTNatTable(shell)
-		
+	def createNatTable(Shell shell) {
 		val bodyLayer = new DummyLayer(
 			// Horizontal axis
 			new ReorderAxis(
 				new AxisImpl(4, 200) => [ setPixelSizeOfSegmentPosition(100, 0) ]
-			) => [ reorderSegmentPosition(1, 2) ],
+			) => [ reorderSegmentPosition(0, 2) ],
 			
 			// Vertical axis
 			new HideShowAxis(
@@ -69,16 +81,28 @@
 //		])
 
 		val String[] columnHeaders = #[ "A", "B", "C", "D" ]
-		val columnHeaderLayer = new ColumnHeaderLayer(bodyLayer.horizontalAxis, new LayerDataAccessorImpl [ layer, columnId, rowId | columnHeaders.get(columnId as Integer) ])
-		val rowHeaderLayer = new RowHeaderLayer(bodyLayer.verticalAxis, new LayerDataAccessorImpl [ layer, columnId, rowId | rowId ])
-		val cornerLayer = new DimensionallyDependentLayer(rowHeaderLayer.horizontalAxis, columnHeaderLayer.verticalAxis, new LayerDataAccessorImpl [ layer, columnId, rowId | "" ])
+		val columnHeaderLayer = new ColumnHeaderLayer(bodyLayer.horizontalAxis, new LayerDataAccessorImpl([ layer, columnId, rowId | columnHeaders.get(columnId as Integer) ]))
+		val rowHeaderLayer = new RowHeaderLayer(bodyLayer.verticalAxis, new LayerDataAccessorImpl([ layer, columnId, rowId | rowId ]))
+		val cornerLayer = new DimensionallyDependentLayer(rowHeaderLayer.horizontalAxis, columnHeaderLayer.verticalAxis, new LayerDataAccessorImpl([ layer, columnId, rowId | "" ]))
 		
-		natTable.layer = new CompositeLayer => [
-			addRow(cornerLayer, columnHeaderLayer)
-			addRow(rowHeaderLayer, bodyLayer)
+		new SWTNatTable(shell) => [
+			injector.injectMembers(it)
+			layer = new CompositeLayer => [
+				addRow(cornerLayer, columnHeaderLayer)
+				addRow(rowHeaderLayer, bodyLayer)
+			]
 		]
+	}
+	
+	def Injector createInjector() {
+		// UI bindings
+		val uiBindings = new UiBindingsImpl
+		uiBindings.keyBindings += new KeyBinding([ event | event.keyCode == Character::valueOf('a') ], [ event | println((event.widget as SWTNatTable).layer) ])
 		
-		natTable
+		// Create injector
+		Guice::createInjector([ binder |
+			binder.bind(typeof(UiBindings)).toInstance(uiBindings)
+		])
 	}
 	
 }
\ No newline at end of file