diff --git a/examples/spreadsheet/src/dlangui/widgets/spreadsheet.d b/examples/spreadsheet/src/dlangui/widgets/spreadsheet.d
index 53e38f95..d348e6c1 100644
--- a/examples/spreadsheet/src/dlangui/widgets/spreadsheet.d
+++ b/examples/spreadsheet/src/dlangui/widgets/spreadsheet.d
@@ -47,10 +47,20 @@ class SpreadSheetView : StringGridWidget {
         layoutWidth = FILL_PARENT;
         layoutHeight = FILL_PARENT;
         resize(50, 50);
+        _colWidths[0] = 50;
+        for (int i = 0; i < 26; i++) {
+            dchar[1] t;
+            t[0] = cast(dchar)('A' + i);
+            setColTitle(i, t.dup);
+        }
+        for (int i = 0; i < 50; i++) {
+            dstring label = to!dstring(i + 1);
+            setRowTitle(i, label);
+        }
     }
 }
 
-class SpreadSheetWidget : WidgetGroupDefaultDrawing {
+class SpreadSheetWidget : WidgetGroupDefaultDrawing, OnScrollHandler {
 
     SheetEditControl _editControl;
     SheetTabs _tabs;
@@ -119,6 +129,9 @@ class SpreadSheetWidget : WidgetGroupDefaultDrawing {
             _viewTopLeft, _viewTopRight, _viewBottomLeft, _viewBottomRight,
             _editControl, _tabs
         ]);
+
+        foreach(sb; _scrollbars)
+            sb.onScrollEventListener = this;
     }
 
 	/// Measure widget according to desired width and height constraints. (Step 1 of two phase layout).
@@ -167,4 +180,22 @@ class SpreadSheetWidget : WidgetGroupDefaultDrawing {
         _vScroll1.layout(Rect(rc.right - vscrollWidth, rc.top, rc.right, rc.top + splity));
         _vScroll2.layout(Rect(rc.right - vscrollWidth, rc.top + splity + splitHeight, rc.right, rc.bottom - bottomSize));
     }
+
+    /// handle scroll event
+    override bool onScrollEvent(AbstractSlider source, ScrollEvent event) {
+        if (source == _hScroll1) {
+            _viewBottomLeft.onHScroll(event);
+            return _viewTopLeft.onHScroll(event);
+        } else if (source == _hScroll2) {
+            _viewBottomRight.onHScroll(event);
+            return _viewTopRight.onHScroll(event);
+        } else if (source == _vScroll1) {
+            _viewTopRight.onVScroll(event);
+            return _viewTopLeft.onVScroll(event);
+        } else if (source == _vScroll2) {
+            _viewBottomRight.onVScroll(event);
+            return _viewBottomLeft.onVScroll(event);
+        }
+        return true;
+    }
 }
diff --git a/src/dlangui/widgets/controls.d b/src/dlangui/widgets/controls.d
index 629c8869..6200e178 100644
--- a/src/dlangui/widgets/controls.d
+++ b/src/dlangui/widgets/controls.d
@@ -578,6 +578,19 @@ class AbstractSlider : WidgetGroup {
         }
         return true;
     }
+
+    protected Orientation _orientation = Orientation.Vertical;
+    /// returns scrollbar orientation (Vertical, Horizontal)
+    @property Orientation orientation() { return _orientation; }
+    /// sets scrollbar orientation
+    @property AbstractSlider orientation(Orientation value) { 
+        if (_orientation != value) {
+            _orientation = value; 
+            requestLayout(); 
+        }
+        return this; 
+    }
+
 }
 
 /// scroll bar - either vertical or horizontal
@@ -748,11 +761,10 @@ class ScrollBar : AbstractSlider, OnClickHandler {
         return true;
     }
 
-    protected Orientation _orientation = Orientation.Vertical;
     /// returns scrollbar orientation (Vertical, Horizontal)
-    @property Orientation orientation() { return _orientation; }
+    override @property Orientation orientation() { return _orientation; }
     /// sets scrollbar orientation
-    @property ScrollBar orientation(Orientation value) { 
+    override @property AbstractSlider orientation(Orientation value) { 
         if (_orientation != value) {
             _orientation = value; 
             _btnBack.drawableId = style.customDrawableId(_orientation == Orientation.Vertical ? ATTR_SCROLLBAR_BUTTON_UP : ATTR_SCROLLBAR_BUTTON_LEFT);
diff --git a/src/dlangui/widgets/scroll.d b/src/dlangui/widgets/scroll.d
index ac227e29..6cd3c1ac 100644
--- a/src/dlangui/widgets/scroll.d
+++ b/src/dlangui/widgets/scroll.d
@@ -133,12 +133,11 @@ class ScrollWidgetBase :  WidgetGroup, OnScrollHandler {
 
     /// handle scroll event
     override bool onScrollEvent(AbstractSlider source, ScrollEvent event) {
-        if (source.compareId("hscrollbar")) {
+        if (source.orientation == Orientation.Horizontal) {
             return onHScroll(event);
-        } else if (source.compareId("vscrollbar")) {
+        } else {
             return onVScroll(event);
         }
-        return true;
     }
 
     /// update scrollbar positions
@@ -161,7 +160,7 @@ class ScrollWidgetBase :  WidgetGroup, OnScrollHandler {
             _hscrollbar = null;
             _hscrollbarMode = ScrollBarMode.Invisible;
         }
-        if (_hscrollbar) {
+        if (hscroll) {
             _hscrollbar = hscroll;
             _hscrollbarMode = ScrollBarMode.External;
         }
@@ -174,7 +173,7 @@ class ScrollWidgetBase :  WidgetGroup, OnScrollHandler {
             _vscrollbar = null;
             _vscrollbarMode = ScrollBarMode.Invisible;
         }
-        if (_vscrollbar) {
+        if (vscroll) {
             _vscrollbar = vscroll;
             _vscrollbarMode = ScrollBarMode.External;
         }
@@ -306,11 +305,11 @@ class ScrollWidgetBase :  WidgetGroup, OnScrollHandler {
 		Rect hsbrc = rc;
 		hsbrc.right = hsbrc.right - (needVscroll ? _vscrollbar.measuredWidth : 0);
 		hsbrc.top = hsbrc.bottom - (needHscroll ? _hscrollbar.measuredHeight : 0);
-        if (_vscrollbar) {
+        if (_vscrollbar && _vscrollbarMode != ScrollBarMode.External) {
             _vscrollbar.visibility = needVscroll ? Visibility.Visible : Visibility.Gone;
 		    _vscrollbar.layout(vsbrc);
         }
-        if (_hscrollbar) {
+        if (_hscrollbar && _hscrollbarMode != ScrollBarMode.External) {
             _hscrollbar.visibility = needHscroll ? Visibility.Visible : Visibility.Gone;
             _hscrollbar.layout(hsbrc);
         }