Android: add loop in slider

This commit is contained in:
王劲鹏 2020-04-10 10:33:15 +08:00 committed by osborn
parent c44c3e5353
commit 4bb9df4dbb
3 changed files with 91 additions and 30 deletions

View File

@ -71,7 +71,11 @@ class SlideAdapter extends RecyclerView.Adapter<SlideAdapter.DoricViewHolder> {
@Override @Override
public int getItemCount() { public int getItemCount() {
return itemCount; if (loop) {
return itemCount + 2;
} else {
return itemCount;
}
} }
@Override @Override
@ -86,11 +90,24 @@ class SlideAdapter extends RecyclerView.Adapter<SlideAdapter.DoricViewHolder> {
} }
private JSValue getItemModel(final int position) { private JSValue getItemModel(final int position) {
String id = itemValues.get(position); int index;
if (loop) {
if (position == 0) {
index = itemCount - 1;
} else if (position == itemCount + 1) {
index = 0;
} else {
index = position - 1;
}
} else {
index = position;
}
String id = itemValues.get(index);
if (TextUtils.isEmpty(id)) { if (TextUtils.isEmpty(id)) {
AsyncResult<JSDecoder> asyncResult = sliderNode.callJSResponse( AsyncResult<JSDecoder> asyncResult = sliderNode.callJSResponse(
"renderBunchedItems", "renderBunchedItems",
position, index,
batchCount); batchCount);
try { try {
JSDecoder jsDecoder = asyncResult.synchronous().get(); JSDecoder jsDecoder = asyncResult.synchronous().get();
@ -100,10 +117,10 @@ class SlideAdapter extends RecyclerView.Adapter<SlideAdapter.DoricViewHolder> {
for (int i = 0; i < jsArray.size(); i++) { for (int i = 0; i < jsArray.size(); i++) {
JSObject itemModel = jsArray.get(i).asObject(); JSObject itemModel = jsArray.get(i).asObject();
String itemId = itemModel.getProperty("id").asString().value(); String itemId = itemModel.getProperty("id").asString().value();
itemValues.put(i + position, itemId); itemValues.put(i + index, itemId);
sliderNode.setSubModel(itemId, itemModel); sliderNode.setSubModel(itemId, itemModel);
} }
return sliderNode.getSubModel(itemValues.get(position)); return sliderNode.getSubModel(itemValues.get(index));
} }
} catch (Exception e) { } catch (Exception e) {
e.printStackTrace(); e.printStackTrace();

View File

@ -65,12 +65,23 @@ public class SliderNode extends SuperNode<RecyclerView> {
public void onScrollStateChanged(@NonNull RecyclerView recyclerView, int newState) { public void onScrollStateChanged(@NonNull RecyclerView recyclerView, int newState) {
if (newState == RecyclerView.SCROLL_STATE_IDLE) { if (newState == RecyclerView.SCROLL_STATE_IDLE) {
View view = snapHelper.findSnapView(layoutManager); View view = snapHelper.findSnapView(layoutManager);
if (view != null && !TextUtils.isEmpty(onPageSlidedFuncId)) { if (view != null) {
int position = layoutManager.getPosition(view); int position = layoutManager.getPosition(view);
if (position != lastPosition) {
callJSResponse(onPageSlidedFuncId, position); if (slideAdapter.loop) {
if (position == 0) {
recyclerView.scrollToPosition(slideAdapter.itemCount);
} else if (position == slideAdapter.itemCount + 1) {
recyclerView.scrollToPosition(1);
}
}
if (!TextUtils.isEmpty(onPageSlidedFuncId)) {
if (position != lastPosition) {
callJSResponse(onPageSlidedFuncId, position);
}
lastPosition = position;
} }
lastPosition = position;
} }
} }
} }
@ -154,6 +165,14 @@ public class SliderNode extends SuperNode<RecyclerView> {
case "loop": case "loop":
boolean loop = prop.asBoolean().value(); boolean loop = prop.asBoolean().value();
slideAdapter.loop = loop; slideAdapter.loop = loop;
if (loop) {
mView.post(new Runnable() {
@Override
public void run() {
mView.scrollToPosition(1);
}
});
}
break; break;
default: default:
super.blend(view, name, prop); super.blend(view, name, prop);

View File

@ -1,4 +1,4 @@
import { Group, Panel, List, text, gravity, Color, Stack, LayoutSpec, list, NativeCall, listItem, log, vlayout, Gravity, hlayout, slider, slideItem, image, layoutConfig, ScaleType } from "doric"; import { Group, Panel, text, gravity, Gravity, Color, LayoutSpec, vlayout, slider, slideItem, image, layoutConfig, ScaleType, switchView, hlayout } from "doric";
import { colors } from "./utils"; import { colors } from "./utils";
const imageUrls = [ const imageUrls = [
@ -15,6 +15,27 @@ const imageUrls = [
@Entry @Entry
class SliderPanel extends Panel { class SliderPanel extends Panel {
build(rootView: Group): void { build(rootView: Group): void {
let pager = slider({
itemCount: imageUrls.length,
renderPage: (idx) => {
return slideItem(image({
imageUrl: imageUrls[idx % imageUrls.length],
scaleType: ScaleType.ScaleAspectFit,
layoutConfig: layoutConfig().configWidth(LayoutSpec.MOST).configHeight(LayoutSpec.MOST).configAlignment(gravity().center()),
})).also(it => {
let start = idx
it.onClick = () => {
it.backgroundColor = (colors[++start % colors.length])
}
})
},
layoutConfig: {
widthSpec: LayoutSpec.MOST,
heightSpec: LayoutSpec.MOST,
weight: 1,
},
})
rootView.addChild(vlayout([ rootView.addChild(vlayout([
text({ text({
text: "Gallery", text: "Gallery",
@ -28,27 +49,31 @@ class SliderPanel extends Panel {
textAlignment: gravity().center(), textAlignment: gravity().center(),
height: 50, height: 50,
}), }),
slider({ hlayout([
itemCount: 100, text({
loop: true, text: "Loop",
renderPage: (idx) => { layoutConfig: {
return slideItem(image({ widthSpec: LayoutSpec.FIT,
imageUrl: imageUrls[idx % imageUrls.length], heightSpec: LayoutSpec.JUST,
scaleType: ScaleType.ScaleAspectFit, },
layoutConfig: layoutConfig().configWidth(LayoutSpec.MOST).configHeight(LayoutSpec.MOST).configAlignment(gravity().center()), textSize: 20,
})).also(it => { textColor: Color.BLACK,
let start = idx textAlignment: gravity().center(),
it.onClick = () => { height: 50,
it.backgroundColor = (colors[++start % colors.length]) }),
} switchView({
}) state: false,
}, onSwitch: (state) => {
layoutConfig: { pager.loop = state
widthSpec: LayoutSpec.MOST, },
heightSpec: LayoutSpec.MOST, }),
weight: 1, ], {
}, layoutConfig: layoutConfig().most().configHeight(LayoutSpec.FIT),
gravity: gravity().center(),
space: 10,
backgroundColor: Color.RED,
}), }),
pager,
]).also(it => { ]).also(it => {
it.layoutConfig = { it.layoutConfig = {
widthSpec: LayoutSpec.MOST, widthSpec: LayoutSpec.MOST,