ScrollView巢狀Viewpager巢狀ListView時遇到的問題
問題彙總:
1.介面顯示不全,並且需要將TabLayout跟隨ListView往上移動
2.當滑動Viewpager時ListView會突然跳到螢幕的頂部
3.當內容往上滑動,使TabLayout懸浮在頂部
問題一
問題描述:.介面顯示不全,需要將TabLayout跟隨ListView往上移動
解決問題的思路,首先獲取ListView的整個控制元件的高度Height,設定外層Viewpager的高度為Height.這樣Scrollview就能完全顯示介面.
解決方案:
第一步:計算listview高度
使用工具類測量public class ViewUtil { public static void使用EventBus把測量的高度回傳給Viewpager所在的activity(fragment)setListViewHeightBasedOnChildren(ListView listView) { ListAdapter listAdapter = listView.getAdapter(); if (listAdapter == null) { return; } int totalHeight = 0; for (int i = 0; i < listAdapter.getCount(); i++) { View listItem = listAdapter.getView(i, null,listView); listItem.measure(0, 0); totalHeight += listItem.getMeasuredHeight(); } ViewGroup.LayoutParams params = listView.getLayoutParams(); params.height = totalHeight + (listView.getDividerHeight() * (listAdapter.getCount() - 1)); listView.setLayoutParams(params); } /** * 獲取Listview的高度,然後設定ViewPager的高度 * @param listView * @return */ public static int setListViewHeightBasedOnChildren1(ListView listView) { //獲取ListView對應的Adapter ListAdapter listAdapter = listView.getAdapter(); if (listAdapter == null) { // pre-condition return 0; } int totalHeight = 0; for (int i = 0, len = listAdapter.getCount(); i < len; i++) { //listAdapter.getCount()返回資料項的數目 View listItem = listAdapter.getView(i, null, listView); listItem.measure(0, 0); //計運算元項View 的寬高 totalHeight += listItem.getMeasuredHeight(); //統計所有子項的總高度 } ViewGroup.LayoutParams params = listView.getLayoutParams(); params.height = totalHeight + (listView.getDividerHeight() * (listAdapter.getCount() - 1)); //listView.getDividerHeight()獲取子項間分隔符佔用的高度 //params.height最後得到整個ListView完整顯示需要的高度 listView.setLayoutParams(params); return params.height; } }
listViewHomeVPAdapter = new ListViewHomeVPAdapter(getContext(),data); mListView.setAdapter(listViewHomeVPAdapter); int listViewHeight = ViewUtil.setListViewHeightBasedOnChildren1(mListView); EventBus.getDefault().post(new ListViewHeight(listViewHeight));給Viewpager設定Height
@Subscribe(threadMode = ThreadMode.MAIN) public void onEventMainThread(ListViewHeight listViewHeight) { int height = listViewHeight.getListViewHeight(); ViewGroup.LayoutParams layoutParams = mViewPager.getLayoutParams(); layoutParams.height = height;mViewPager.setLayoutParams(layoutParams); }現在解決了介面顯示不全的問題.
第二步:自定義ScrollView
public class MyScrollView extends ScrollView { private float xDistance, yDistance, xLast, yLast; private OnScrollListener onScrollListener; /** * 主要是用在使用者手指離開MyScrollView,MyScrollView還在繼續滑動,我們用來儲存Y的距離,然後做比較 */ private int lastScrollY; public MyScrollView(Context context) { this(context, null); } public MyScrollView(Context context, AttributeSet attrs) { this(context, attrs, 0); } public MyScrollView(Context context, AttributeSet attrs, int defStyle) { super(context, attrs, defStyle); } /** * 設定滾動介面 * @param onScrollListener */ public void setOnScrollListener(OnScrollListener onScrollListener) { this.onScrollListener = onScrollListener; } /** * 用於使用者手指離開MyScrollView的時候獲取MyScrollView滾動的Y距離,然後回撥給onScroll方法中 */ private Handler handler = new Handler() { public void handleMessage(android.os.Message msg) { int scrollY = MyScrollView.this.getScrollY(); //此時的距離和記錄下的距離不相等,在隔5毫秒給handler傳送訊息 if(lastScrollY != scrollY){ lastScrollY = scrollY; handler.sendMessageDelayed(handler.obtainMessage(), 5); } if(onScrollListener != null){ onScrollListener.onScroll(scrollY); } } }; /** * 重寫onTouchEvent, 當用戶的手在MyScrollView上面的時候, * 直接將MyScrollView滑動的Y方向距離回撥給onScroll方法中,當用戶擡起手的時候, * MyScrollView可能還在滑動,所以當用戶擡起手我們隔5毫秒給handler傳送訊息,在handler處理 * MyScrollView滑動的距離 */ @Override public boolean onTouchEvent(MotionEvent ev) { if(onScrollListener != null){ onScrollListener.onScroll(lastScrollY = this.getScrollY()); } switch(ev.getAction()){ case MotionEvent.ACTION_UP: handler.sendMessageDelayed(handler.obtainMessage(), 5); break; } Log.d("print", "getScrollY: "+this.getScrollY()); return super.onTouchEvent(ev); } /** * * 滾動的回撥介面 * */ public interface OnScrollListener{ /** * 回撥方法, 返回MyScrollView滑動的Y方向距離 */ public void onScroll(int scrollY); } /** *解決ViewPager與ScrollView手勢衝突的問題 */ @Override public boolean onInterceptTouchEvent(MotionEvent ev) { switch (ev.getAction()) { case MotionEvent.ACTION_DOWN: xDistance = yDistance = 0f; xLast = ev.getX(); yLast = ev.getY(); break; case MotionEvent.ACTION_MOVE: final float curX = ev.getX(); final float curY = ev.getY(); xDistance += Math.abs(curX - xLast); yDistance += Math.abs(curY - yLast); xLast = curX; yLast = curY; if(xDistance > yDistance){ return false; } } return super.onInterceptTouchEvent(ev); } }最外層的ScrollView改成使用自定義的MyScrollView
問題二:
問題描述:
在專案中用到了ScrollView巢狀ViewPager巢狀ListView情況,當滑動Viewpager時ListView會突然跳到螢幕的頂部
解決方案:
在Fragment之外的控制元件中新增3個屬性
在ScrollView的根佈局中新增屬性設定
<RelativeLayout android:layout_width="match_parent" android:layout_height="match_parent" android:focusable="true" android:focusableInTouchMode="true" android:descendantFocusability="beforeDescendants">關鍵程式碼:
android:focusable="true" android:focusableInTouchMode="true" android:descendantFocusability="beforeDescendants"
屬性是當一個為View獲取焦點時,定義ViewGroup和其子控制元件兩者之間的關係.
descendantFocousability屬性的值有三種: beforeDescendants , afterDescendants , blocksDescendants.
beforeDescendants: ViewGroup會優先其子控制元件獲取焦點. afterDescendants: ViewGroup只有當他的子控制元件不需要獲取焦點時才獲取焦點. blocksDescendants: ViewGroup會覆蓋子類控制元件而直接獲得焦點.
問題三:
問題描述:.當內容往上滑動,使TabLayout懸浮在頂部 需要實現的效果:解決思路:在XML檔案中放置兩個RelativeLayout, 一個保持在原位置,一個在頂部佔位(當需要的時候把TabLayout新增進去)
解決方案:
ViewPager所在的Activity(Fragment)中
MyScrollViewHomeFragment.setOnScrollListener(this);
@Override public void onScroll(int scrollY) { if (scrollY >= 600) { if (mTabFragmentHome.getParent() != relativeLayoutTop) { relativeLayoutCenter.removeView(mTabFragmentHome); relativeLayoutTop.addView(mTabFragmentHome); } } else { if (mTabFragmentHome.getParent() != relativeLayoutCenter) { relativeLayoutTop.removeView(mTabFragmentHome); relativeLayoutCenter.addView(mTabFragmentHome); } } }
佈局檔案(此處有修改,請按照思路模仿)
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" android:layout_width="match_parent" android:layout_height="match_parent"> <com.xxx.widget.MyScrollView android:id="@+id/MyScrollView_home_fragment" android:layout_width="match_parent" android:layout_height="match_parent"> <RelativeLayout android:layout_width="match_parent" android:layout_height="match_parent" android:descendantFocusability="beforeDescendants" android:focusable="true" android:focusableInTouchMode="true"> <android.support.v4.view.ViewPager android:id="@+id/vp_fragment_home" android:layout_width="match_parent" android:layout_height="match_parent" android:layout_below="@+id/relativeLayout_center" /> <RelativeLayout android:id="@+id/relativeLayout_center" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_below="@+id/GongNeng"> <android.support.design.widget.TabLayout android:id="@+id/tab_fragment_home" android:layout_width="match_parent" android:layout_height="20dp" android:background="#fff" app:tabIndicatorColor="@color/primary" app:tabMode="scrollable" app:tabSelectedTextColor="@color/color_text_selected" app:tabTextColor="@color/color_text_normal" /> </RelativeLayout> </RelativeLayout> </com.xxx.widget.MyScrollView> <RelativeLayout android:id="@+id/relativeLayout_top" android:layout_width="match_parent" android:layout_height="wrap_content"/> </RelativeLayout>
相關推薦
ScrollView巢狀Viewpager巢狀ListView時遇到的問題
問題彙總: 1.介面顯示不全,並且需要將TabLayout跟隨ListView往上移動 2.當滑動Viewpager時ListView會突然跳到螢幕的頂部 3.當內容往上滑動,使TabLayout懸浮在頂部 問題一 問題描述:.介面顯示不全,需要將TabLayout跟隨
fragment中 ScrollView 同時巢狀viewpager banner和 listview, scrollview 滑動異常·
fragment中 ScrollView 同時巢狀viewpager banner和 &nbs
RecyclerView裡巢狀ViewPager,滾動RecyclerView時,記住之前ViewPager滑動後的位置
如果是ListView裡巢狀ViewPager的話,首先要考慮的是豎向滑動和橫向衝突的問題,RecyclerView的話,不用考慮此問題 方法: 準備一個map來儲存你滑動過的ViewPager所在的RcyclerView中的位置和你滑動Vie
Android 仿京東,淘寶RecyclerView巢狀ViewPager巢狀RecyclerView商品展示
最近看到京東,淘寶都有RecyclerView巢狀ViewPager巢狀RecyclerView商品展示的效果,效果挺好,廢話不多說先看效果圖: GIF.gif 技能點: 1.Android事件分發機制等 需求點: 1.列表巢狀,內層的列表可以左右切換 2.V
ListView顯示不全,ViewPager顯示不全,ScrollVIew巢狀ViewPager顯示問題
自定義listView,重寫他的onMeasure方法:解決listView顯示不全 @Overrideprotected void onMeasure(int widthMeasureSpec,
ScrollView內巢狀ListView時禁止ListView的滾動
ScrollView內巢狀ListView時不知道為什麼ListView高度很小隻能顯示一行資料,網上有說是因為ScrollView和ListView之間衝突導致的 禁止ListView的滾動事件時可以解決該問題,只讓
解決ScrollView或者listview巢狀ViewPager 時候 Pager左右滑動不流暢
pager.setOnTouchListener(new View.OnTouchListener() { @Override public boolean onTouch(View v, MotionEvent event) {
在ScrollView中巢狀ListView時,需要根據內容來設定listView的高度
動態設定ListView的高度 public void setListViewHeightBasedOnChildren(ListView mListView) { ListAdapter listAdapter = mListView.getAdapter();
解決ScrollView巢狀viewPager中巢狀listView滑動事件衝突問題(水平方向)
我們在開發中經常會碰到view滑動衝突的情況。滑動衝突的解決辦法就兩種:1.外部攔截法:是指在點選事件先經過父容器的攔截處理,如果父容器需要處理此事件就進行攔截,如果不需要此事件就不攔截,這樣就可以解決滑動衝突的問題,外部攔截法需要重寫父容器的onInterceptTouch
Android學習 之 問題&解答 ScrollView中巢狀ListView時顯示不全的簡便解決方案
利用下面這個Utility 類的靜態方法setListViewHeightBasedOnChildren()即可實現: 在listview.setAdapter()之後呼叫Utility.setListViewHeightBasedOnChilren(listview)就
安卓在ScrollView中巢狀ViewPager時,設定ViewPager的單個頁面高度隨內容變化
在開發過程中,有時候頁面佈局比較複雜,會使用到ScrollView和ViewPager,如果不進行處理,會出現不顯示ViewPager的子頁面,或者子頁面高度一樣,內容顯示不全,或者是留白太多。我的需求是需要在頁面下面加一個可以左右滑動的分欄,而且兩個分類的頁面高度不一致且不
解決Android中ScrollView裡巢狀listview時,listview不能不能滾動的問題
我們在Android的佈局中有時會使用到ScrollView,然後在ScrollView中再巢狀listview,但是這樣就會導致listview獲取焦點失敗不能滾動(具體原理可自行搜尋Android的觸控事件的分發機制),在搜尋解決方案時發現需要重寫Scrol
ScrollView巢狀ListView時Bug解決以及ExpandableListView設定全部展開
1.ExpandableListView設定預設展 mExpandListview.setAdapter(adapter); //設定ExpandableListView全部展開 for (int i = 0;i < adapter.getGroupCount();
scrollview巢狀viewpager(fragment裡有listview)
專案地址: 經常用到scrollview巢狀listview, 效果是:listview自己不滾動,隨著scrollview的滾動而滾動。 但是有個需求是scrollview巢狀viewpager,viewpager有三個fragment,fragme
Android:ScrollView中巢狀ViewPager和ListView示例
引言: 我們在實際開發一個款Android App時,經常會遇到Scrollview和ViewPager和ListView同時使用的場景,如下圖所示的需求: 下面我們通過程式碼來模擬一下這種場景: 佈局檔案: <?xml version="
解決ScrollView巢狀RecyclerView(橫向)或ListView(橫向)時,橫向滑動不順暢的問題。
程式碼簡單,容易理解,裡面有點註釋,夠看了,特別少的改動。 package com.laka.live.ui.widget; import android.content.Context; im
從原始碼角度解析 - ScrollView巢狀ViewPager不顯示的問題
<ScrollView android:id="@+id/scroll_view" android:layout_width="match_parent" android:layout_height="match_parent">
Android---SwipeRefreshLayout巢狀ViewPager時的滑動衝突
SwipeRefreshLayout巢狀ViewPager 最近在專案中用到了SwipeRefreshLayout控制元件,以實現下拉重新整理,在我的SwipeRefreshLayout佈局中存在一個ViewPager。那麼問題就出現了,當我對ViewPager
scrollview中巢狀viewpager不顯示
activityScdetailsBottomVp.setOnPageChangeListener(new ViewPager.OnPageChangeListener() { @Override publicvoid onPageS
Android 混排效果之 ScrollView 巢狀 RecyclerView 巢狀gridview 實現listview 巢狀gridview 效果
RecyclerView 出現以後 很受大家歡迎 漂亮流暢的列表 簡單的操作 可以幫我們完成很多的列表 但是有一種listview 巢狀gridview 的效果 目前還是需要巢狀才能完成 現在就簡單說一下我的思路 本人的需求是例如手機淘寶頁 本人使用老套的實現模