属性动画
ValueAnimator:
ObjectAnimator:继承自ValueAnimator,
AnimatorSet:
属性动画的示例
AnimatorListener:属性动画监听器;
- 定义如下:
public static interface AnimatorListener { void onAnimationStart(Animator animation); void onAnimationEnd(Animator animation); void onAnimationCancel(Animator animation); void onAnimationRepeat(Animator animation); }
可以定义动画的开始、结束、取消和重复。
AnimatorListenerAdapter:该监听器的适配器,这样可以有选择的实现以上四个方法
AnimatorUpdateListener:用于监听整个动画。
- 定义如下:
public static interface AnimatorUpdateListener { void onAnimatorUpdate(ValueAnimator animation); }
若要在动画过程中作其他事情。例如:在显示输入框的时候,让顶部面板逐渐隐藏;在输入框消失时,让顶部面板渐显。可以使用该监听器。
动画每播放一帧,
onAnimatorUpdate()
就会被调用一次。实例:
@Override protected void startInputAnimator(boolean inputShow) { if (mInputShow == inputShow) { return; } mInputShow = inputShow; ValueAnimator valueAnimator = deRef(mInputAnimatorRef); if (valueAnimator != null) { if (!valueAnimator.isStarted() && !valueAnimator.isRunning()) { valueAnimator.start(); } return; } valueAnimator = ValueAnimator.ofFloat(0.0f, 1.0f); valueAnimator.setDuration(300); valueAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() { @Override public void onAnimationUpdate(ValueAnimator animation) { float value = (float) animation.getAnimatedValue(); if (mInputShow) { value = 1.0f - value; } setAlpha(mTopInfoView, value); } }); valueAnimator.addListener(new AnimatorListenerAdapter() { @Override public void onAnimationStart(Animator animation) { if (mInputShow) { if (mIsLandscape) { setVisibility(mLiveCommentView, View.GONE); } } else { setVisibility(mTopInfoView, View.VISIBLE); } } @Override public void onAnimationEnd(Animator animation) { if (mInputShow) { setVisibility(mTopInfoView, View.GONE); } else { setAlpha(mTopInfoView, 1.0f); if (mIsLandscape) { setVisibility(mLiveCommentView, View.VISIBLE); } } } }); valueAnimator.start(); mInputAnimatorRef = new WeakReference<>(valueAnimator); }
MVP的View和Presenter
View和Presenter的绑定,为了让 view 和 presenter 能够相互通信,双方都要持有对方的引用。
常用做法:
- 定义一个IPresenter接口,接口中定义view需要通知presenter做的事情的方法,让Presenter实现该接口。
- 在View中new一个Presenter对象,这样在view中就可以调用IPresenter定义的方法。这样就实现了view到presenter的通信。
- 在view中定义一个IView接口,接口中定义presenter需要通知view做的事情的方法。
- 为IPresenter添加setView方法,然后在view中调用presenter.setView(new IView(){…})
- presenter实现setView方法,这样就会持有view的引用,可以调用IView中定义的方法。
- 在4中的new IView(){…}实现IView定义的方法。这样就实现了presenter到view的通知。
Git常用操作
push出错时:
gitdir=(git rev-parse --git-dir); scp -p -P 29418 wangmengjie@git.xiaomi.com:hooks/commit-msg {gitdir}/hooks/
#拷贝这次commit的前一次commitID
git log
#reset到前一个commit
git commit commitId
#查看当前状态
git status
#保持和远端的同步
git pull
git add .
git commit -s -m "完成的功能
N/A
"
git push origin 分支:refs/for/分支
提交到远端之后,需要做一些修改
git status
git add .
git status
#git使用amend选项提供了最后一次commit的反悔
git commit --amend
git status
git commit -s -m "完成的功能
N/A
"
git push origin 分支:refs/for/分支
- git使用amend选项提供了最后一次commit的反悔。但是对于历史提交呢,就需要使用rebase了。