Merge branch 'feature/animation' into 'master'
Feature/animation See merge request !42
This commit is contained in:
commit
eaca061573
@ -21,7 +21,7 @@ public class DoricRefreshView extends FrameLayout implements PullingListener {
|
|||||||
private View content;
|
private View content;
|
||||||
private Animation.AnimationListener mListener;
|
private Animation.AnimationListener mListener;
|
||||||
|
|
||||||
private PullingListener mPullingListenr;
|
private PullingListener mPullingListener;
|
||||||
|
|
||||||
public DoricRefreshView(@NonNull Context context) {
|
public DoricRefreshView(@NonNull Context context) {
|
||||||
super(context);
|
super(context);
|
||||||
@ -38,12 +38,15 @@ public class DoricRefreshView extends FrameLayout implements PullingListener {
|
|||||||
public void setContent(View v) {
|
public void setContent(View v) {
|
||||||
removeAllViews();
|
removeAllViews();
|
||||||
content = v;
|
content = v;
|
||||||
if (v.getLayoutParams() instanceof FrameLayout.LayoutParams) {
|
ViewGroup.LayoutParams params = v.getLayoutParams();
|
||||||
((LayoutParams) v.getLayoutParams()).gravity = Gravity.BOTTOM;
|
if (params instanceof LayoutParams) {
|
||||||
|
((LayoutParams) params).gravity = Gravity.BOTTOM;
|
||||||
} else {
|
} else {
|
||||||
LayoutParams params = new LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
|
LayoutParams layoutParams = new LayoutParams(
|
||||||
params.gravity = Gravity.CENTER;
|
params == null ? ViewGroup.LayoutParams.WRAP_CONTENT : params.width,
|
||||||
v.setLayoutParams(params);
|
params == null ? ViewGroup.LayoutParams.WRAP_CONTENT : params.height);
|
||||||
|
layoutParams.gravity = Gravity.CENTER;
|
||||||
|
v.setLayoutParams(layoutParams);
|
||||||
}
|
}
|
||||||
addView(v);
|
addView(v);
|
||||||
}
|
}
|
||||||
@ -53,28 +56,28 @@ public class DoricRefreshView extends FrameLayout implements PullingListener {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public void setPullingListenr(PullingListener listenr) {
|
public void setPullingListener(PullingListener listener) {
|
||||||
this.mPullingListenr = listenr;
|
this.mPullingListener = listener;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void startAnimation() {
|
public void startAnimation() {
|
||||||
if (mPullingListenr != null) {
|
if (mPullingListener != null) {
|
||||||
mPullingListenr.startAnimation();
|
mPullingListener.startAnimation();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void stopAnimation() {
|
public void stopAnimation() {
|
||||||
if (mPullingListenr != null) {
|
if (mPullingListener != null) {
|
||||||
mPullingListenr.stopAnimation();
|
mPullingListener.stopAnimation();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void setProgressRotation(float rotation) {
|
public void setPullingDistance(float distance) {
|
||||||
if (mPullingListenr != null) {
|
if (mPullingListener != null) {
|
||||||
mPullingListenr.setProgressRotation(rotation);
|
mPullingListener.setPullingDistance(distance);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -30,6 +30,8 @@ import androidx.swiperefreshlayout.widget.CircularProgressDrawable;
|
|||||||
|
|
||||||
import android.view.animation.Animation.AnimationListener;
|
import android.view.animation.Animation.AnimationListener;
|
||||||
|
|
||||||
|
import pub.doric.utils.DoricUtils;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @Description: pub.doric.pullable
|
* @Description: pub.doric.pullable
|
||||||
* @Author: pengfei.zhou
|
* @Author: pengfei.zhou
|
||||||
@ -117,11 +119,6 @@ public class DoricSwipeLayout extends ViewGroup implements NestedScrollingParent
|
|||||||
|
|
||||||
int mCustomSlingshotDistance;
|
int mCustomSlingshotDistance;
|
||||||
|
|
||||||
private Animation mScaleAnimation;
|
|
||||||
|
|
||||||
private Animation mScaleDownAnimation;
|
|
||||||
|
|
||||||
private Animation mScaleDownToStartAnimation;
|
|
||||||
|
|
||||||
boolean mNotify;
|
boolean mNotify;
|
||||||
|
|
||||||
@ -131,6 +128,7 @@ public class DoricSwipeLayout extends ViewGroup implements NestedScrollingParent
|
|||||||
private OnChildScrollUpCallback mChildScrollUpCallback;
|
private OnChildScrollUpCallback mChildScrollUpCallback;
|
||||||
|
|
||||||
private DoricRefreshView mRefreshView;
|
private DoricRefreshView mRefreshView;
|
||||||
|
|
||||||
private AnimationListener mRefreshListener = new AnimationListener() {
|
private AnimationListener mRefreshListener = new AnimationListener() {
|
||||||
@Override
|
@Override
|
||||||
public void onAnimationStart(Animation animation) {
|
public void onAnimationStart(Animation animation) {
|
||||||
@ -158,6 +156,20 @@ public class DoricSwipeLayout extends ViewGroup implements NestedScrollingParent
|
|||||||
private int mPullDownHeight = 0;
|
private int mPullDownHeight = 0;
|
||||||
private ValueAnimator headerViewAnimator;
|
private ValueAnimator headerViewAnimator;
|
||||||
|
|
||||||
|
private void onRefreshAnimationEnd() {
|
||||||
|
if (mRefreshing) {
|
||||||
|
mRefreshView.startAnimation();
|
||||||
|
if (mNotify) {
|
||||||
|
if (mListener != null) {
|
||||||
|
mListener.onRefresh();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
mCurrentTargetOffsetTop = mRefreshView.getTop();
|
||||||
|
} else {
|
||||||
|
reset();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void reset() {
|
void reset() {
|
||||||
mRefreshing = false;
|
mRefreshing = false;
|
||||||
if (headerViewAnimator != null && headerViewAnimator.isRunning()) {
|
if (headerViewAnimator != null && headerViewAnimator.isRunning()) {
|
||||||
@ -169,6 +181,9 @@ public class DoricSwipeLayout extends ViewGroup implements NestedScrollingParent
|
|||||||
public void onAnimationUpdate(ValueAnimator animation) {
|
public void onAnimationUpdate(ValueAnimator animation) {
|
||||||
mCurrentTargetOffsetTop = (int) animation.getAnimatedValue()
|
mCurrentTargetOffsetTop = (int) animation.getAnimatedValue()
|
||||||
- mRefreshView.getMeasuredHeight();
|
- mRefreshView.getMeasuredHeight();
|
||||||
|
if (mRefreshView.getMeasuredHeight() > 0) {
|
||||||
|
mRefreshView.setPullingDistance(DoricUtils.px2dp(mRefreshView.getBottom()));
|
||||||
|
}
|
||||||
mRefreshView.requestLayout();
|
mRefreshView.requestLayout();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@ -320,36 +335,13 @@ public class DoricSwipeLayout extends ViewGroup implements NestedScrollingParent
|
|||||||
}
|
}
|
||||||
setTargetOffsetTopAndBottom(endTarget - mCurrentTargetOffsetTop);
|
setTargetOffsetTopAndBottom(endTarget - mCurrentTargetOffsetTop);
|
||||||
mNotify = false;
|
mNotify = false;
|
||||||
startScaleUpAnimation(mRefreshListener);
|
mRefreshView.setVisibility(View.VISIBLE);
|
||||||
|
onRefreshAnimationEnd();
|
||||||
} else {
|
} else {
|
||||||
setRefreshing(refreshing, false /* notify */);
|
setRefreshing(refreshing, false /* notify */);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void startScaleUpAnimation(AnimationListener listener) {
|
|
||||||
mRefreshView.setVisibility(View.VISIBLE);
|
|
||||||
mScaleAnimation = new Animation() {
|
|
||||||
@Override
|
|
||||||
public void applyTransformation(float interpolatedTime, Transformation t) {
|
|
||||||
setAnimationProgress(interpolatedTime);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
mScaleAnimation.setDuration(mMediumAnimationDuration);
|
|
||||||
if (listener != null) {
|
|
||||||
mRefreshView.setAnimationListener(listener);
|
|
||||||
}
|
|
||||||
mRefreshView.clearAnimation();
|
|
||||||
mRefreshView.startAnimation(mScaleAnimation);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Pre API 11, this does an alpha animation.
|
|
||||||
*
|
|
||||||
* @param progress
|
|
||||||
*/
|
|
||||||
void setAnimationProgress(float progress) {
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
private void setRefreshing(boolean refreshing, final boolean notify) {
|
private void setRefreshing(boolean refreshing, final boolean notify) {
|
||||||
if (mRefreshing != refreshing) {
|
if (mRefreshing != refreshing) {
|
||||||
@ -359,24 +351,11 @@ public class DoricSwipeLayout extends ViewGroup implements NestedScrollingParent
|
|||||||
if (mRefreshing) {
|
if (mRefreshing) {
|
||||||
animateOffsetToCorrectPosition(mCurrentTargetOffsetTop, mRefreshListener);
|
animateOffsetToCorrectPosition(mCurrentTargetOffsetTop, mRefreshListener);
|
||||||
} else {
|
} else {
|
||||||
startScaleDownAnimation(mRefreshListener);
|
onRefreshAnimationEnd();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void startScaleDownAnimation(Animation.AnimationListener listener) {
|
|
||||||
mScaleDownAnimation = new Animation() {
|
|
||||||
@Override
|
|
||||||
public void applyTransformation(float interpolatedTime, Transformation t) {
|
|
||||||
setAnimationProgress(1 - interpolatedTime);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
mScaleDownAnimation.setDuration(SCALE_DOWN_DURATION);
|
|
||||||
mRefreshView.setAnimationListener(listener);
|
|
||||||
mRefreshView.clearAnimation();
|
|
||||||
mRefreshView.startAnimation(mScaleDownAnimation);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return Whether the SwipeRefreshWidget is actively showing refresh
|
* @return Whether the SwipeRefreshWidget is actively showing refresh
|
||||||
* progress.
|
* progress.
|
||||||
@ -744,24 +723,7 @@ public class DoricSwipeLayout extends ViewGroup implements NestedScrollingParent
|
|||||||
} else {
|
} else {
|
||||||
// cancel refresh
|
// cancel refresh
|
||||||
mRefreshing = false;
|
mRefreshing = false;
|
||||||
Animation.AnimationListener listener = null;
|
animateOffsetToStartPosition(mCurrentTargetOffsetTop, null);
|
||||||
listener = new Animation.AnimationListener() {
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onAnimationStart(Animation animation) {
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onAnimationEnd(Animation animation) {
|
|
||||||
startScaleDownAnimation(null);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onAnimationRepeat(Animation animation) {
|
|
||||||
}
|
|
||||||
|
|
||||||
};
|
|
||||||
animateOffsetToStartPosition(mCurrentTargetOffsetTop, listener);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -912,7 +874,7 @@ public class DoricSwipeLayout extends ViewGroup implements NestedScrollingParent
|
|||||||
ViewCompat.offsetTopAndBottom(mRefreshView, offset);
|
ViewCompat.offsetTopAndBottom(mRefreshView, offset);
|
||||||
mCurrentTargetOffsetTop = mRefreshView.getTop();
|
mCurrentTargetOffsetTop = mRefreshView.getTop();
|
||||||
if (mRefreshView.getMeasuredHeight() > 0) {
|
if (mRefreshView.getMeasuredHeight() > 0) {
|
||||||
mRefreshView.setProgressRotation((float) mRefreshView.getBottom() / (float) mRefreshView.getMeasuredHeight() * 2);
|
mRefreshView.setPullingDistance(DoricUtils.px2dp(mRefreshView.getBottom()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -16,5 +16,5 @@ public interface PullingListener {
|
|||||||
*
|
*
|
||||||
* @param rotation Rotation is from [0..2]
|
* @param rotation Rotation is from [0..2]
|
||||||
*/
|
*/
|
||||||
void setProgressRotation(float rotation);
|
void setPullingDistance(float rotation);
|
||||||
}
|
}
|
||||||
|
@ -33,7 +33,7 @@ public class RefreshableNode extends SuperNode<DoricSwipeLayout> implements Pull
|
|||||||
@Override
|
@Override
|
||||||
protected DoricSwipeLayout build() {
|
protected DoricSwipeLayout build() {
|
||||||
DoricSwipeLayout doricSwipeLayout = new DoricSwipeLayout(getContext());
|
DoricSwipeLayout doricSwipeLayout = new DoricSwipeLayout(getContext());
|
||||||
doricSwipeLayout.getRefreshView().setPullingListenr(this);
|
doricSwipeLayout.getRefreshView().setPullingListener(this);
|
||||||
return doricSwipeLayout;
|
return doricSwipeLayout;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -188,9 +188,9 @@ public class RefreshableNode extends SuperNode<DoricSwipeLayout> implements Pull
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void setProgressRotation(float rotation) {
|
public void setPullingDistance(float rotation) {
|
||||||
if (mHeaderNode != null) {
|
if (mHeaderNode != null) {
|
||||||
mHeaderNode.callJSResponse("setProgressRotation", rotation);
|
mHeaderNode.callJSResponse("setPullingDistance", rotation);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -17,4 +17,5 @@ export default [
|
|||||||
'src/PopoverDemo',
|
'src/PopoverDemo',
|
||||||
'src/AnimatorDemo',
|
'src/AnimatorDemo',
|
||||||
'src/ComplicatedAnimations',
|
'src/ComplicatedAnimations',
|
||||||
|
'src/ComplicatedDemo',
|
||||||
]
|
]
|
@ -17,11 +17,12 @@ function thisLabel(str: string) {
|
|||||||
class AnimationDemo extends Panel {
|
class AnimationDemo extends Panel {
|
||||||
build(rootView: Group): void {
|
build(rootView: Group): void {
|
||||||
const view = box(2)
|
const view = box(2)
|
||||||
|
const view2 = box(3)
|
||||||
view.onClick = () => {
|
view.onClick = () => {
|
||||||
modal(context).toast('Clicked')
|
modal(context).toast('Clicked')
|
||||||
}
|
}
|
||||||
vlayout([
|
vlayout([
|
||||||
title("Complicated Animation"),
|
title("Complicated Animation"),
|
||||||
vlayout(
|
vlayout(
|
||||||
[
|
[
|
||||||
hlayout([
|
hlayout([
|
||||||
@ -177,7 +178,17 @@ class AnimationDemo extends Panel {
|
|||||||
]
|
]
|
||||||
).apply({ space: 10 } as IVLayout),
|
).apply({ space: 10 } as IVLayout),
|
||||||
stack([
|
stack([
|
||||||
view,
|
view.also(v => {
|
||||||
|
v.x = 20
|
||||||
|
v.y = 0
|
||||||
|
v.width = 30
|
||||||
|
v.left = 15
|
||||||
|
}),
|
||||||
|
view2.also(v => {
|
||||||
|
v.x = v.y = 20
|
||||||
|
v.y = 40
|
||||||
|
v.scaleX = 1.5
|
||||||
|
})
|
||||||
]).apply({
|
]).apply({
|
||||||
layoutConfig: layoutConfig().atmost(),
|
layoutConfig: layoutConfig().atmost(),
|
||||||
backgroundColor: colors[1].alpha(0.3 * 255),
|
backgroundColor: colors[1].alpha(0.3 * 255),
|
||||||
|
49
demo/src/ComplicatedDemo.ts
Normal file
49
demo/src/ComplicatedDemo.ts
Normal file
@ -0,0 +1,49 @@
|
|||||||
|
import { Panel, Group, vlayout, image, layoutConfig, ScaleType, refreshable, Color, pullable, stack, Image, Refreshable, TranslationAnimation, loge, log } from "doric";
|
||||||
|
import { title, icon_refresh } from "./utils";
|
||||||
|
|
||||||
|
@Entry
|
||||||
|
class MyDemo extends Panel {
|
||||||
|
build(root: Group) {
|
||||||
|
let refreshed: Refreshable
|
||||||
|
let headerImage: Image
|
||||||
|
stack([
|
||||||
|
refreshed = refreshable({
|
||||||
|
onRefresh: () => {
|
||||||
|
refreshed.setRefreshing(context, false)
|
||||||
|
},
|
||||||
|
header: pullable(context,
|
||||||
|
stack([]).apply({
|
||||||
|
backgroundColor: Color.RED,
|
||||||
|
layoutConfig: layoutConfig().exactly(),
|
||||||
|
width: 100,
|
||||||
|
height: 30,
|
||||||
|
}),
|
||||||
|
{
|
||||||
|
startAnimation: () => {
|
||||||
|
},
|
||||||
|
stopAnimation: () => {
|
||||||
|
},
|
||||||
|
setPullingDistance: (distance: number) => {
|
||||||
|
headerImage.scaleX = headerImage.scaleY = (headerImage.height + distance * 2) / headerImage.height
|
||||||
|
log(`Header Image scaleY:${headerImage.scaleY},height:${headerImage.height},distance:${distance}`)
|
||||||
|
},
|
||||||
|
}),
|
||||||
|
content: vlayout([]).apply({
|
||||||
|
backgroundColor: Color.YELLOW,
|
||||||
|
}),
|
||||||
|
}).apply({
|
||||||
|
layoutConfig: layoutConfig().atmost(),
|
||||||
|
}).also(v => {
|
||||||
|
v.top = 200
|
||||||
|
}),
|
||||||
|
|
||||||
|
headerImage = image({
|
||||||
|
imageUrl: "https://img.zcool.cn/community/01e75b5da933daa801209e1ffa4649.jpg@1280w_1l_2o_100sh.jpg",
|
||||||
|
layoutConfig: layoutConfig().exactly(),
|
||||||
|
width: root.width,
|
||||||
|
height: 200,
|
||||||
|
scaleType: ScaleType.ScaleAspectFill,
|
||||||
|
}),
|
||||||
|
]).in(root)
|
||||||
|
}
|
||||||
|
}
|
@ -31,8 +31,8 @@ class RefreshableDemo extends Panel {
|
|||||||
stopAnimation: () => {
|
stopAnimation: () => {
|
||||||
log('stopAnimation')
|
log('stopAnimation')
|
||||||
},
|
},
|
||||||
setProgressRotation: (rotation: number) => {
|
setPullingDistance: (distance: number) => {
|
||||||
refreshImage.rotation = rotation
|
refreshImage.rotation = distance / 30
|
||||||
},
|
},
|
||||||
}),
|
}),
|
||||||
content: (vlayout([
|
content: (vlayout([
|
||||||
@ -83,18 +83,6 @@ class RefreshableDemo extends Panel {
|
|||||||
refreshView.setRefreshable(context, false)
|
refreshView.setRefreshable(context, false)
|
||||||
}
|
}
|
||||||
} as IText),
|
} as IText),
|
||||||
label('Rotate self').apply({
|
|
||||||
width: 300,
|
|
||||||
height: 50,
|
|
||||||
backgroundColor: colors[0],
|
|
||||||
textSize: 30,
|
|
||||||
textColor: Color.WHITE,
|
|
||||||
layoutConfig: layoutConfig().exactly(),
|
|
||||||
} as IText).also(v => {
|
|
||||||
v.onClick = () => {
|
|
||||||
v.nativeChannel(context, "setRotation")(0.25)
|
|
||||||
}
|
|
||||||
}),
|
|
||||||
]).apply({
|
]).apply({
|
||||||
layoutConfig: layoutConfig().atmost().h(LayoutSpec.WRAP_CONTENT),
|
layoutConfig: layoutConfig().atmost().h(LayoutSpec.WRAP_CONTENT),
|
||||||
gravity: gravity().centerX(),
|
gravity: gravity().centerX(),
|
||||||
|
@ -65,8 +65,8 @@ export function rotatedArrow(context: BridgeContext) {
|
|||||||
stopAnimation: () => {
|
stopAnimation: () => {
|
||||||
log('stopAnimation')
|
log('stopAnimation')
|
||||||
},
|
},
|
||||||
setProgressRotation: (rotation: number) => {
|
setPullingDistance: (distance: number) => {
|
||||||
refreshImage.rotation = rotation
|
refreshImage.rotation = distance / 30
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
}
|
}
|
@ -152,13 +152,13 @@ - (void)stopAnimation {
|
|||||||
[self.headerNode callJSResponse:@"stopAnimation", nil];
|
[self.headerNode callJSResponse:@"stopAnimation", nil];
|
||||||
}
|
}
|
||||||
|
|
||||||
- (void)setProgressRotation:(CGFloat)rotation {
|
- (void)setPullingDistance:(CGFloat)distance {
|
||||||
[self.headerNode callJSResponse:@"setProgressRotation", @(rotation), nil];
|
[self.headerNode callJSResponse:@"setPullingDistance", @(distance), nil];
|
||||||
}
|
}
|
||||||
|
|
||||||
- (void)setRefreshing:(NSNumber *)refreshable withPromise:(DoricPromise *)promise {
|
- (void)setRefreshing:(NSNumber *)refreshable withPromise:(DoricPromise *)promise {
|
||||||
self.view.refreshing = [refreshable boolValue];
|
self.view.refreshing = [refreshable boolValue];
|
||||||
[promise resolve:nil];
|
[promise resolve:nil];
|
||||||
}
|
}
|
||||||
|
|
||||||
- (void)setRefreshable:(NSNumber *)refreshing withPromise:(DoricPromise *)promise {
|
- (void)setRefreshable:(NSNumber *)refreshing withPromise:(DoricPromise *)promise {
|
||||||
|
@ -1,18 +1,3 @@
|
|||||||
/*
|
|
||||||
* Copyright [2019] [Doric.Pub]
|
|
||||||
*
|
|
||||||
* 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.
|
|
||||||
*/
|
|
||||||
//
|
//
|
||||||
// Created by pengfei.zhou on 2019/11/26.
|
// Created by pengfei.zhou on 2019/11/26.
|
||||||
//
|
//
|
||||||
@ -24,7 +9,7 @@
|
|||||||
|
|
||||||
- (void)stopAnimation;
|
- (void)stopAnimation;
|
||||||
|
|
||||||
- (void)setProgressRotation:(CGFloat)rotation;
|
- (void)setPullingDistance:(CGFloat)rotation;
|
||||||
@end
|
@end
|
||||||
|
|
||||||
@interface DoricSwipeRefreshLayout : UIScrollView
|
@interface DoricSwipeRefreshLayout : UIScrollView
|
||||||
|
@ -68,7 +68,14 @@ - (BOOL)requestFromSubview:(UIView *)subview {
|
|||||||
return [super requestFromSubview:subview];
|
return [super requestFromSubview:subview];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
- (void)layoutSubviews {
|
||||||
|
[super layoutSubviews];
|
||||||
|
}
|
||||||
|
|
||||||
- (void)layoutSelf:(CGSize)targetSize {
|
- (void)layoutSelf:(CGSize)targetSize {
|
||||||
|
if (self.contentOffset.y != 0) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
self.width = targetSize.width;
|
self.width = targetSize.width;
|
||||||
self.height = targetSize.height;
|
self.height = targetSize.height;
|
||||||
[self.headerView also:^(UIView *it) {
|
[self.headerView also:^(UIView *it) {
|
||||||
@ -109,7 +116,7 @@ - (void)scrollViewDidEndDragging:(UIScrollView *)scrollView willDecelerate:(BOOL
|
|||||||
|
|
||||||
- (void)scrollViewDidScroll:(UIScrollView *)scrollView {
|
- (void)scrollViewDidScroll:(UIScrollView *)scrollView {
|
||||||
if (scrollView.contentOffset.y <= 0) {
|
if (scrollView.contentOffset.y <= 0) {
|
||||||
[self.swipePullingDelegate setProgressRotation:-scrollView.contentOffset.y / self.headerView.height * 2];
|
[self.swipePullingDelegate setPullingDistance:-scrollView.contentOffset.y];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -122,31 +129,14 @@ - (void)setRefreshing:(BOOL)refreshing {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (refreshing) {
|
if (refreshing) {
|
||||||
|
[self setContentOffset:CGPointMake(0, -self.headerView.height) animated:YES];
|
||||||
|
self.scrollEnabled = NO;
|
||||||
if (self.onRefreshBlock) {
|
if (self.onRefreshBlock) {
|
||||||
self.onRefreshBlock();
|
self.onRefreshBlock();
|
||||||
}
|
}
|
||||||
[UIView animateWithDuration:.3f
|
|
||||||
animations:^{
|
|
||||||
self.contentOffset = (CGPoint) {0, -self.headerView.height};
|
|
||||||
self.contentInset = UIEdgeInsetsMake(self.headerView.height, 0, 0, 0);
|
|
||||||
}
|
|
||||||
completion:^(BOOL finished) {
|
|
||||||
[self.swipePullingDelegate startAnimation];
|
|
||||||
self.scrollEnabled = NO;
|
|
||||||
}
|
|
||||||
];
|
|
||||||
} else {
|
} else {
|
||||||
self.bounces = YES;
|
[self setContentOffset:(CGPoint) {0, 0} animated:YES];
|
||||||
[UIView animateWithDuration:.3f
|
self.scrollEnabled = YES;
|
||||||
animations:^{
|
|
||||||
self.contentOffset = (CGPoint) {0, 0};
|
|
||||||
self.contentInset = UIEdgeInsetsMake(0, 0, 0, 0);
|
|
||||||
}
|
|
||||||
completion:^(BOOL finished) {
|
|
||||||
[self.swipePullingDelegate stopAnimation];
|
|
||||||
self.scrollEnabled = YES;
|
|
||||||
}
|
|
||||||
];
|
|
||||||
}
|
}
|
||||||
_refreshing = refreshing;
|
_refreshing = refreshing;
|
||||||
}
|
}
|
||||||
|
@ -62,13 +62,13 @@ export function refreshable(config: IRefreshable) {
|
|||||||
export interface IPullable {
|
export interface IPullable {
|
||||||
startAnimation(): void
|
startAnimation(): void
|
||||||
stopAnimation(): void
|
stopAnimation(): void
|
||||||
setProgressRotation(rotation: number): void
|
setPullingDistance(distance: number): void
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
export function pullable(context: BridgeContext, v: View, config: IPullable) {
|
export function pullable(context: BridgeContext, v: View, config: IPullable) {
|
||||||
Reflect.set(v, 'startAnimation', config.startAnimation)
|
Reflect.set(v, 'startAnimation', config.startAnimation)
|
||||||
Reflect.set(v, 'stopAnimation', config.stopAnimation)
|
Reflect.set(v, 'stopAnimation', config.stopAnimation)
|
||||||
Reflect.set(v, 'setProgressRotation', config.setProgressRotation)
|
Reflect.set(v, 'setPullingDistance', config.setPullingDistance)
|
||||||
return v
|
return v
|
||||||
}
|
}
|
Reference in New Issue
Block a user