SmoothScrollViewer

April 9, 2026 · View on GitHub

A ScrollViewer replacement with inertia-based smooth scrolling. Supports configurable easing and duration, horizontal/vertical scroll bar visibility, scroll chaining, and programmatic scroll methods.

Basic usage

<SmoothScrollViewer>
    <StackPanel>
        <!-- long content -->
    </StackPanel>
</SmoothScrollViewer>

Properties

PropertyTypeDefaultDescription
HorizontalScrollBarVisibilityScrollBarVisibilityDisabledDisabled, Auto, Hidden, Visible
VerticalScrollBarVisibilityScrollBarVisibilityAutoDisabled, Auto, Hidden, Visible
SmoothScrollEasingEasing?Easing function for the smooth scroll animation
SmoothScrollDurationTimeSpanDuration of the smooth scroll animation
AllowAutoHideboolinheritedWhether scroll bars auto-hide when not in use
IsScrollChainingEnabledbooltrueWhether scrolling propagates to a parent scrollable when the limit is reached
OffsetVectorCurrent scroll offset (get/set)
ExtentSizeTotal size of the scrollable content (read-only)
ViewportSizeSize of the visible viewport (read-only)

Events

EventDescription
ScrollChangedFired when scroll position, extent, or viewport size changes

Smooth scroll animation

<SmoothScrollViewer SmoothScrollDuration="0:0:0.3"
                    SmoothScrollEasing="{x:Static Easings.CubicEaseOut}">
    <ItemsControl ItemsSource="{Binding Items}" />
</SmoothScrollViewer>

Horizontal scroll

<SmoothScrollViewer HorizontalScrollBarVisibility="Auto"
                    VerticalScrollBarVisibility="Disabled">
    <StackPanel Orientation="Horizontal">
        <!-- wide content -->
    </StackPanel>
</SmoothScrollViewer>

Programmatic scrolling

// Line scroll
viewer.LineUp();
viewer.LineDown();
viewer.LineLeft();
viewer.LineRight();

// Page scroll
viewer.PageUp();
viewer.PageDown();

// Jump to start / end
viewer.ScrollToHome();
viewer.ScrollToEnd();

// Set offset directly
viewer.Offset = new Vector(0, 500);

Attached properties

HorizontalScrollBarVisibility and VerticalScrollBarVisibility can be set as attached properties on child controls:

<SmoothScrollViewer>
    <TextBox SmoothScrollViewer.HorizontalScrollBarVisibility="Auto"
             AcceptsReturn="True" />
</SmoothScrollViewer>

Disable scroll chaining

Prevent scroll events from bubbling to a parent scrollable:

<SmoothScrollViewer IsScrollChainingEnabled="False">
    <!-- nested scrollable content -->
</SmoothScrollViewer>