我正在使用带有Endless Scroll的StaggeredGridLayoutManager的Recyclerview。当列表的最后一项对用户可见时,我想进行网络呼叫。所以这是我的代码:
<html>
<head>
<script type='text/javascript' src='js/jquery-1.4.2.min.js'></script>
<script>
$('#menu-button').click(function(){
$('#hide-menu').toggleClass('show-menu');
});
</script>
<style>
body
{
overflow:hidden;
}
.menu-button
{
border:1px solid #000;
color:fff;
display:inline-block;
cursor:pointer;
}
.hide-menu
{
background-color:#336ca6;
position: absolute;
top:0;
right:0;
z-index: 1;
width: 300px;
height: 100%;
-webkit-transform: translate3d(300px,0,0);
-moz-transform: translate3d(300px,0,0);
-o-transform: translate3d(300px,0,0);
-ms-transform: translate3d(300px,0,0);
transform: translate3d(300px,0,0);
-webkit-transition: all 0.3s linear;
-moz-transition: all 0.3s linear;
-ms-transition: all 0.3s linear;
-o-transition: all 0.3s linear;
transition: all 0.3s linear;
}
.show-menu
{
-webkit-transform: translate3d(0,0,0);
-moz-transform: translate3d(0,0,0);
-o-transform: translate3d(0,0,0);
-ms-transform: translate3d(0,0,0);
transform: translate3d(0,0,0);
}
</style>
</head>
<body>
<center>
<br>
<div style='display:none;'>
<img src="images/loader.gif" />
</div>
<form action="" name = "form">
<input type="text" name="name" id="fn" Placeholder="Search Something..." style="width:300px; padding:8px;"/>
<input type="submit" value="Search" id="menu-button"style="padding:8px;"/>
</form>
<br>
<div id = "s-results">
<!-- Search results here! -->
</div>
<nav id="hide-menu" class="hide-menu">
<script type = "text/javascript">
$(document).ready(function(){
$('#s-results').load('search.php').show();
$('#search-btn').click(function(){
showValues();
});
$(function() {
$('form').bind('submit',function(){
showValues();
return false;
});
});
function showValues() {
$('#s-results').html('<img src="images/loader.gif" />');
$.post('search.php', { name: form.name.value },
function(result){
$('#s-results').html(result).show();
});
}
});
</script>
</center>
</nav>
</body>
</html>
我在第一次通话时从服务器获得9个值。因此,当我移动到最后一个索引[8]时,lastVisibleItem将为8并且visibleThreshold为1,totalItemCount为9,因此下一次网络调用应该发生。现在实际发生的是,当屏幕第一次加载时,lastVisibleItem应该是1或2,但是它返回8,结果,loadMore()被调用。
logcat的:
public RecyclerViewAdapter(Context context) {
Log.d(Const.DEBUG, "RecyclerViewAdapter Constructor()");
this.context = context;
final StaggeredGridLayoutManager staggeredGridLayoutManager = (StaggeredGridLayoutManager) recyclerView.getLayoutManager();
recyclerView.addOnScrollListener(new RecyclerView.OnScrollListener() {
@Override
public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
super.onScrolled(recyclerView, dx, dy);
totalItemCount = staggeredGridLayoutManager.getItemCount();
lastVisibleItems = staggeredGridLayoutManager.findLastVisibleItemPositions(new int[mStaggeredLayoutManager.getSpanCount()]);
Log.d(Const.DEBUG, "LastVisibleItems: " + Arrays.toString(lastVisibleItems));
Log.d(Const.DEBUG, "LastVisibleItems Count: " + lastVisibleItems.length);
if (staggeredGridLayoutManager.getSpanCount() == 1) {
lastVisibleItem = lastVisibleItems[0];
} else if (staggeredGridLayoutManager.getSpanCount() == 2) {
lastVisibleItem = Math.max(lastVisibleItems[0], lastVisibleItems[1]);
} else if (staggeredGridLayoutManager.getSpanCount() == 3) {
lastVisibleItem = Math.max(Math.max(lastVisibleItems[0], lastVisibleItems[1]), lastVisibleItems[2]);
}
if (!isRefreshing && (totalItemCount <= lastVisibleItem + visibleThreshold)) {
Log.d(Const.DEBUG, "isRefreshing: " + isRefreshing);
Log.d(Const.DEBUG, "totalItemCount: " + totalItemCount);
Log.d(Const.DEBUG, "lastVisibileItem: " + lastVisibleItem);
Log.d(Const.DEBUG, "visibileThreshold: " + visibleThreshold);
Log.d(Const.DEBUG, "calling LoadMore()");
if (mIOnLoadMoreListener != null) {
mIOnLoadMoreListener.onLoadMore();
}
isRefreshing = true;
}
}
});
}
上面的代码有什么问题?需要帮助请叫我。相同的代码之前运作良好。
答案 0 :(得分:2)
试试这个。
private int pastVisiblesItems, visibleItemCount, totalItemCount;
private boolean loading = true;
private StaggeredGridLayoutManager layoutManager;
private RecyclerView recyclerView ;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
layoutManager=new StaggeredGridLayoutManager(2,1);
recyclerView = (RecyclerView) findViewById(R.id.recycler_view);
recyclerView.setLayoutManager(layoutManager);
recycleView.addOnScrollListener(new RecyclerView.OnScrollListener() {
@Override
public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
if (dy > 0) //for vertical scrolling
{
} else if (dy < 0) {
}
if (dx > 0)//for horizontal scrolling
{
visibleItemCount = layoutManager.getChildCount();
totalItemCount = layoutManager.getItemCount();
pastVisiblesItems = layoutManager.findFirstVisibleItemPosition();
if (loading) {
if ((visibleItemCount + pastVisiblesItems) >= totalItemCount) {
loading = false;
loadMore(); //desired function call
}
}
}
}
});
}
API调用成功后请不要忘记 loading = true 。
希望它有所帮助......
答案 1 :(得分:0)
private void recyclerViewOnScroll(RecyclerView recyclerView, final StaggeredGridLayoutManager staggeredGridLayoutManager) {
recyclerView.addOnScrollListener(new RecyclerView.OnScrollListener() {
@Override
public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
super.onScrolled(recyclerView, dx, dy);
if (dy > 0) {
totalItemCount = staggeredGridLayoutManager.getItemCount();
if (lastPositions == null)
lastPositions = new int[staggeredGridLayoutManager.getSpanCount()];
lastPositions = staggeredGridLayoutManager.findLastCompletelyVisibleItemPositions(lastPositions);
lastVisibleItem = Math.max(lastPositions[0], lastPositions[1]);//findMax(lastPositions);
if (!loading && totalItemCount >= 20 && totalItemCount <= (lastVisibleItem + visibleThreshold)) {
// End has been reached
if (onLoadMoreListener != null) {
onLoadMoreListener.onLoadMore();
}
loading = true;
}
}
}
});
}
答案 2 :(得分:0)
以下代码对我有用:
//return true if it's last item visited
private boolean isLastItemDisplaying(RecyclerView recyclerView) {
if (recyclerView.getAdapter().getItemCount() != 0) {
//int lastVisibleItemPosition = ((StaggeredGridLayoutManager)recyclerView.getLayoutManager()).findLastVisibleItemPositions();
int[] lastVisibleItemPositions = ((StaggeredGridLayoutManager) Objects.requireNonNull(recyclerView.getLayoutManager())).findLastVisibleItemPositions(null);
// get maximum element within the list
int lastVisibleItemPosition = getLastVisibleItem(lastVisibleItemPositions);
return lastVisibleItemPosition != RecyclerView.NO_POSITION && lastVisibleItemPosition == recyclerView.getAdapter().getItemCount() - 1;
}
return false;
}
//get last item
public int getLastVisibleItem(int[] lastVisibleItemPositions) {
int maxSize = 0;
for (int i = 0; i < lastVisibleItemPositions.length; i++) {
if (i == 0) {
maxSize = lastVisibleItemPositions[i];
} else if (lastVisibleItemPositions[i] > maxSize) {
maxSize = lastVisibleItemPositions[i];
}
}
return maxSize;
}