Skip to content

Sticky elevation proposal

Tonic Artos edited this page Mar 3, 2015 · 1 revision

Since elevation effects draw ordering, it is necessary to consider how stickied headers interact with elevated views.

The initial discussion on this topic was started in issue #48.

Potential solutions

Two non exclusive options are offered as solutions to the problem.

Sticky header watcher.

The idea here is to provide some method by which the sticky header state can be watched, and the views easily modified. This would allow users to provide their own solutions, but also makes it easy to add new, unique behaviours beyond what is need to solve this problem.

Proposal

Available on all versions.

New methods for LayoutManager

/**
 * Set a listener for state changes to sticky style headers within given distance of the top of the
 * recycler view.
 *
 * @param watchDistance Distance from edge at which to start watching.
 * @param watcher       Watcher.
 */
public void setStickyHeaderWatcher(int watchDistance, StickyHeaderWatcher watcher);

/**
 * Set a listener for state changes to sticky style headers within a default distance of the top of the 
 * recycler view.
 *
 * @param watcher Watcher.
 */
public void setStickyHeaderWatcher(StickyHeaderWatcher watcher);

New interface in LayoutManager

public interface StickyHeaderWatcher {
    /**
     * Called when the view is within a short distance from the top of the recycler view. This distance
     * can be set in {@link LayoutManager#setStickyHeaderWatcher(int watchDistance, StickyHeaderWatcher watcher)}.
     * This method continues to be called until the header is no longer displayed on the screen, and
     * so it may be called twice for two different headers. However, it is only called once for 
     * distance = 0;
     * 
     * @param header   Header view.
     * @param position View position in adapter data set.
     * @param distance Distance of top edge from the top of the recycler view. Values are positive when
     *                 the header is below the edge, and negative when above.
     */
    void onPositionChange(View header, int position, int distance);

    /**
     * Called when the header state changes. The state values are, ABOVE, BELOW, STICKIED, and OUTSIDE.
     * Outside is the final state for when the header was being watched but will no longer be watched.
     *
     * @param header   Header view.
     * @param position View position in adapter data set.
     * @param state    New state of the header.
     */
    void onStickyStateChanged(View header, int position, int state);
}

Configuration options

The idea is that SuperSLiM should be able to handle the situation itself through configuration of the headers layout params. However, the default behaviour should be the existing situation since it is unknown without user input how much elevation should be applied to resolve the problem, or whether a shadow should be applied.

Proposal

XML configuration options

<Truncated
app:slm_header_stickyElevation="dimension|integer"
app:slm_header_stickyElevationAnimDistance="dimension|integer"
app:slm_header_disableShadow="boolean"
/>

New LayoutParams fields

public int stickyElevation = 0;
public int elevationAnimationDistance = DEFAULT_ANIM_DISTANCE;
public boolean disableShadow = false;

The elevation animation distance is the distance from the edge at which the elevation starts being applied. A smoothing function is applied to get a nice animation from the origin elevation.

If true, disable shadow sets the outline provider to null.

Perhaps DEFAULT_ANIM_DISTANCE should be 16dip on smaller devices, and 24dip on tablets and larger. This follows the border padding distances suggested in the material design spec.

Versioned Pages

0.4

[Getting Started](Getting started with version 0.4)
[User's Guide](User's guide for version 0.4)

version5 (WIP)

User documentation
[Basic usage](A simple tutorial)
[Advanced usage](All the cool things)
[SuperSLiM and RxJava](Using SuperSLiM with RxJava)

Developers documentation
Glossary
[The section graph](The section graph)
[Tracking data changes](Tracking data changes)
[Configuration transformations](Configuration transformations)
[Layout helpers](Layout helpers)
[Section configuration](Section configuration)
[Section state](Section state)
[Section layout managers](Section layout managers)
[Header layout managers](Header layout managers)

Clone this wiki locally