GithubHelp home page GithubHelp logo

slideback's Introduction

高仿微信视差手势滑动返回库(实验性质,请勿用于商业开发)

实现思路参考自「Slidr」和「and_swipeback

功能

  • 无需设置Activity主题透明
  • 支持动态切换全局或边缘滑动,亦可动态禁止或恢复滑动
  • 支持动态设置边缘响应和滑动关闭距离的阈值
  • 页面边缘附有阴影并随滑动距离而渐变
  • 优化了与RecyclerView、ViewPager等滑动控件手势冲突
  • 支持屏幕旋转

效果图

Demo Demo

使用方法

1. 继承Application实现Activity生命周期的监听,ActivityHelper用于保存Activity栈供侧滑库使用

public class MyApplication extends Application {

    private ActivityHelper mActivityHelper;

    private static MyApplication sMyApplication;

    @Override
    public void onCreate() {
        super.onCreate();

        mActivityHelper = new ActivityHelper();
        registerActivityLifecycleCallbacks(mActivityHelper);

        sMyApplication = this;

    }

    public static ActivityHelper getActivityHelper(){
        return sMyApplication.mActivityHelper;
    }
    
}

2.在需要滑动的Activity使用SlideBackHelper去attach当前Activity

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_second);

    mSlideBackLayout = SlideBackHelper.attach(
            // 当前Activity
            this,
            // Activity栈管理工具
            MyApplication.getActivityHelper(),
            // 参数的配置
            new SlideConfig.Builder()
                    // 屏幕是否旋转
                    .rotateScreen(true)
                    // 是否侧滑
                    .edgeOnly(false)
                    // 是否禁止侧滑
                    .lock(false)
                    // 边缘滑动的响应阈值,0~1,对应屏幕宽度*percent
                    .edgePercent(0.1f)
                    // 关闭页面的阈值,0~1,对应屏幕宽度*percent
                    .slideOutPercent(0.5f).create(),
            // 滑动的监听
            null);
           
    // 其它初始化
}

3.如果开启了屏幕旋转,SlideBackLayout需要监听Activity的结束事件,例如这里的onBackPressed,所以你需要在调用结束事件的地方加上SlideBackLayout.isComingToFinish()

@Override
public void onBackPressed() {
    super.onBackPressed();
    mSlideBackLayout.isCommingToFinish();
    overridePendingTransition(R.anim.anim_none, R.anim.anim_slide_out);
}

4.SlideBackHelper.attach会返回处理侧滑的SlideBackLayout,可在适当时候动态控制侧滑几个参数

  // 是否启用边缘滑动
  mSlideBackLayout.edgeOnly(boolean);
  // 是否禁止滑动
  mSlideBackLayout.lock(boolean);
  // 设置边缘滑动的响应阈值
  mSlideBackLayout.setEdgeRangePercent(float);
  // 设置关闭页面的阈值
  mSlideBackLayout.setSlideOutRangePercent(float);

存在问题

旋转屏幕后上一个Activity的布局也会随之旋转,但是ToolBar比例还是维持旋转之前的比例,无从下手,希望有大神告知>_<
沉浸式状态栏支持有问题
多个滑动页面快速返回有空指针问题,只能等页面取点焦点的时候才能滑动

License

Copyright 2016 oubowu

Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at

   http://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.

slideback's People

Contributors

oubowu avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

slideback's Issues

SlideBackHelper的attach该出偶尔导致crash

SlideBackHelper的attach方法的preActivity偶尔为null
final Activity[] preActivity = {helper.getPreActivity()};
final View[] preContentView = {getContentView(preActivity[0])};

导致该方法报错crash
public static ViewGroup getDecorView(Activity activity) {
return (ViewGroup) activity.getWindow().getDecorView();
}

推测app在后台是很久没打开,上级页面被回收。这应该怎么处理??望解答

我大概知道怎么处理沉浸式状态栏问题了

public class StatusBarUtil {

    public static final int DEFAULT_STATUS_BAR_ALPHA = 112;


    @TargetApi(Build.VERSION_CODES.KITKAT)
    public static boolean setTranslucentStatus(Activity activity, boolean on) {
        Window win = activity.getWindow();
        WindowManager.LayoutParams winParams = win.getAttributes();
        final int bits = WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS;
        if (on) {
            winParams.flags |= bits;
        } else {
            winParams.flags &= ~bits;
        }
        win.setAttributes(winParams);

        return on;
    }

    /**
     * 为滑动返回界面设置状态栏颜色
     *
     */
    public static void setColorForSwipeBack(Activity activity, @ColorInt int color) {
        setColorForSwipeBack(activity, color, 0);
    }

    /**
     * 为滑动返回界面设置状态栏颜色
     *
     * @param activity       需要设置的activity
     * @param color          状态栏颜色值
     * @param statusBarAlpha 状态栏透明度
     */
    public static void setColorForSwipeBack(Activity activity, @ColorInt int color, int statusBarAlpha) {
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {

            ViewGroup contentView = ((ViewGroup) activity.findViewById(android.R.id.content));
            if (contentView == null) return;
            View rootView = contentView.getChildAt(0);
            int statusBarHeight = getStatusBarHeight(activity);
            if (rootView != null && rootView instanceof CoordinatorLayout) {
                final CoordinatorLayout coordinatorLayout = (CoordinatorLayout) rootView;
                if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) {
                    coordinatorLayout.setFitsSystemWindows(false);
                    contentView.setBackgroundColor(calculateStatusColor(color, statusBarAlpha));
                    boolean isNeedRequestLayout = contentView.getPaddingTop() < statusBarHeight;
                    if (isNeedRequestLayout) {
                        contentView.setPadding(0, statusBarHeight, 0, 0);
                        coordinatorLayout.post(new Runnable() {
                            @Override
                            public void run() {
                                coordinatorLayout.requestLayout();
                            }
                        });
                    }
                } else {
                    coordinatorLayout.setStatusBarBackgroundColor(calculateStatusColor(color, statusBarAlpha));
                }
            } else {
                contentView.setPadding(0, statusBarHeight, 0, 0);
                contentView.setBackgroundColor(calculateStatusColor(color, statusBarAlpha));
            }
            setTranslucentStatus(activity, true);
        }
    }


    /**
     * 获取状态栏高度
     *
     * @param context context
     * @return 状态栏高度
     */
    private static int getStatusBarHeight(Context context) {
        // 获得状态栏高度
        int resourceId = context.getResources().getIdentifier("status_bar_height", "dimen", "android");
        return context.getResources().getDimensionPixelSize(resourceId);
    }


    /**
     * 计算状态栏颜色
     *
     * @param color color值
     * @param alpha alpha值
     * @return 最终的状态栏颜色
     */
    private static int calculateStatusColor(@ColorInt int color, int alpha) {
        float a = 1 - alpha / 255f;
        int red = color >> 16 & 0xff;
        int green = color >> 8 & 0xff;
        int blue = color & 0xff;
        red = (int) (red * a + 0.5);
        green = (int) (green * a + 0.5);
        blue = (int) (blue * a + 0.5);
        return 0xff << 24 | red << 16 | green << 8 | blue;
    }

}
public class StatusBarView extends View {
    public StatusBarView(Context context, AttributeSet attrs) {
        super(context, attrs);
    }

    public StatusBarView(Context context) {
        super(context);
    }
}

上面的方法改自StatusBarUtil,修改了setTranslucentStatus(activity, true);
根布局如果是CoordinatorLayout,加上android:fitsSystemWindows="true";如果不是,就不要加android:fitsSystemWindows="true",并且需要在根布局设置背景background,不然背景色和状态栏一样(style设置的背景失效,上面的方法相当重新覆盖了背景色)。如果布局有EditText,请用CoordinatorLayout,不然顶不上去

边缘长按有时会闪回去

在SecondActivity界面的,跳转侧滑页面按钮左下边缘,滑动一下放开,再长按滑动(不行可多操作几次),界面会突然闪回去

与ViewPager的事件冲突

在有ViewPager的页面,ViewPager处于第一页,经常要滑动两三次,才可以触发侧滑返回。

当添加滑动监听时,上级页面列表数据回顶部(5个手机3个存在问题),或者初始化上级页面ui

代码如下::
//滑动关闭activity
public void slideBack(){
mSlideBackLayout = SlideBackHelper.attach(
this,
OkbuyApplication.getActivityHelper(),
new SlideConfig.Builder()
.rotateScreen(true)
.edgeOnly(false)
.lock(false)
.edgePercent(0.1f)
.slideOutPercent(0.5f).create(),
// 滑动的监听
new OnSlideListener() {
@OverRide
public void onSlide(@FloatRange(from = 0.0, to = 1.0) float percent) {
if(percent > 0.0){
cancelCountDown();
}
}
@OverRide
public void onOpen() {
setCountDownForSlideBack();
}
@OverRide
public void onClose() {
setResult(Activity.RESULT_OK);
}
});
}
断点调试没发现问题,莫名其妙,望大神指点一二

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.