仿新闻类实现滑动选择标签(一)
2017-06-06 10:30
459 查看
文章界面,可以上拉下拉刷新数据,并且可以加载标签布局,通过viewpager实现滑动,改造PagerSlidingTabStrip实现修改字体颜色,底部横线宽度与字体宽度一致
直接附代码
实现文章页面:
文章页面:HealthEducationActivity.java
public class HealthEducationActivity extends BaseCompatActivity { @BindView(R.id.iv_back) ImageView ivBack; @BindView(R.id.tabs) PagerSlidingTabStrip tabs; @BindView(R.id.iv_addView) LinearLayout ivAddView; @BindView(R.id.pager) ViewPager pager; private DisplayMetrics dm; // 获取当前屏幕密度 private ArrayList<ArticleBean> articleBeanArrayList = new ArrayList<>(); private MyPagerAdapter myPagerAdapter; private static final int CHANGE_COLUMN = 0x0009; private int selectPosition=0; public static void start(Context context) { Intent intent = new Intent(); intent.setClass(context, HealthEducationActivity.class); intent.addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP); context.startActivity(intent); } @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_health_education); ButterKnife.bind(this); myPagerAdapter = new MyPagerAdapter(getSupportFragmentManager()); dm = getResources().getDisplayMetrics(); ivAddView.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { ColumnCustomizationActivity.startForResult(HealthEducationActivity.this, selectPosition,articleBeanArrayList,CHANGE_COLUMN); } }); ivBack.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { finish(); } }); getListArticleMainClassByCitizenId(); pager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() { @Override public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) { } @Override public void onPageSelected(int position) { selectPosition=position; } @Override public void onPageScrollStateChanged(int state) { } }); } private void setPagerSlidingTabStrip() { tabs.setIndicatorColor(R.color.color_green_34cb80); // 设置Tab是自动填充满屏幕的 tabs.setShouldExpand(true); // 设置Tab的分割线是透明的 tabs.setDividerColor(Color.TRANSPARENT); // 设置Tab底部线的高度 tabs.setUnderlineHeight((int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 1, dm)); // 设置Tab Indicator的高度 tabs.setIndicatorHeight((int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 2, dm)); tabs.setDividerPadding((int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 20, dm)); // 设置Tab标题文字的大小 tabs.setTextSize((int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_SP, 15, dm)); // 设置Tab标题默认的颜色 tabs.setTextColor(getResources().getColor(R.color.get_record_text_unselected_color)); // 设置选中Tab标题的颜色 tabs.setSelectedTextColor(getResources().getColor(R.color.get_record_text_selected_color)); // 设置Tab底部线的颜色 tabs.setUnderlineColor(Color.TRANSPARENT); // 设置Tab Indicator的颜色 tabs.setIndicatorColor(getResources().getColor(R.color.get_record_line_selected_color)); } class MyPagerAdapter extends FragmentPagerAdapter { public MyPagerAdapter(FragmentManager fm) { super(fm); } @Override public Fragment getItem(int position) { return HealthEducationFragment.newInstance(articleBeanArrayList.get(position).getId()); } @Override public int getCount() { return articleBeanArrayList.size(); } @Override public int getItemPosition(Object object) { return PagerAdapter.POSITION_NONE; } @Override public CharSequence getPageTitle(int position) { SpannableStringBuilder ssb = new SpannableStringBuilder(" " + articleBeanArrayList.get(position).getName()); // space added before text for ForegroundColorSpan fcs = new ForegroundColorSpan(Color.parseColor("#34cb80"));//字体颜色设置为绿色 ssb.setSpan(fcs, 1, ssb.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);//设置字体颜色 ssb.setSpan(new RelativeSizeSpan(1.2f), 1, ssb.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE); return ssb; } } @Override protected void onResume() { super.onResume(); } public void getListArticleMainClassByCitizenId() { showProgressDialog("加载中", null, null); String url = Contants.APIURL.GET_LISTARTICLEMAINCLASSBYCITIZENID.getUrl(); RequestEntity<String> entity = new RequestEntity<>(); OkHttpUtils.get().url(url).headers(entity.getHeader()).build().execute(new JsonCallBack<ResponseEntity<ArrayList<ArticleBean>>>() { @Override public void onError(Call call, Exception e, RequestCall requestCall) { dismissProgressDialog(); ToastUtil.showLongToast("网络异常,请稍后尝试"); } @Override public void onResponse(ResponseEntity<ArrayList<ArticleBean>> data, RequestCall requestCall) { dismissProgressDialog(); if (data.isOK()) { articleBeanArrayList.clear(); articleBeanArrayList.addAll(data.getRstData()); pager.setAdapter(myPagerAdapter); tabs.setViewPager(pager); setPagerSlidingTabStrip(); } else { ToastUtil.showLongToast(data.getErrorMsg()); } } }); } /** * 回调方法,从第二个页面回来的时候会执行这个方法 */ @Override protected void onActivityResult(int requestCode, int resultCode, Intent data) { super.onActivityResult(requestCode, resultCode, data); if (resultCode != RESULT_OK) return; // 根据上面发送过去的请求码来区别 switch (requestCode) { case CHANGE_COLUMN://修改定制栏目 ArrayList<ArticleBean> chooseList = (ArrayList<ArticleBean>) data.getSerializableExtra(ColumnCustomizationActivity.SELECT_COLUMN); selectPosition = data.getIntExtra(ColumnCustomizationActivity.SELECT_COLUMN_INDEX,0); articleBeanArrayList.clear(); articleBeanArrayList.addAll(chooseList); myPagerAdapter.notifyDataSetChanged(); tabs.notifyDataSetChanged(); pager.setCurrentItem(selectPosition); default: break; } } }
activity_health_education.xml
<?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:infiniteCard="http://schemas.android.com/apk/res-auto" android:layout_width="match_parent" android:layout_height="match_parent" android:background="@color/white" android:orientation="vertical"> <com.mandala.healthserviceresident.widget.PagerSlidingTabStrip android:id="@+id/tabs" android:layout_width="wrap_content" android:layout_height="48dip" android:layout_centerHorizontal="true" android:layout_marginRight="40dp" android:layout_marginLeft="40dp" /> <LinearLayout android:layout_width="30dp" android:layout_height="30dp" android:gravity="center" android:layout_alignLeft="@id/tabs" android:layout_alignParentLeft="true" android:layout_margin="10dp"> <ImageView android:id="@+id/iv_back" android:layout_width="wrap_content" android:layout_height="wrap_content" android:src="@mipmap/ic_navigation" android:gravity="center" /> </LinearLayout> <LinearLayout android:id="@+id/iv_addView" android:layout_width="30dp" android:layout_height="30dp" android:gravity="center" android:layout_margin="10dp" android:layout_alignRight="@id/tabs" android:layout_alignParentRight="true"> <ImageView android:layout_width="wrap_content" android:layout_height="wrap_content" android:src="@drawable/add_language_new" /> </LinearLayout> <android.support.v4.view.ViewPager android:id="@+id/pager" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_below="@id/tabs" /> </RelativeLayout>
对应的fragment
HealthEducationFragment.java
public class HealthEducationFragment extends LazyFragment { private static final String MAIN_ID = "mainID"; @BindView(R.id.listView) ListView listView; @BindView(R.id.pull_refresh_scrollview) PullToRefreshScrollView mPullRefreshScrollView; private String mainId; @BindView(R.id.id_flow_layout) FlowLayout idFlowLayout; private ArrayList<ArticleBean> childBeanList = new ArrayList<>(); private ArrayList<ListArticleBean> listArticleBeanArrayList = new ArrayList<>(); private View mFragmentView; private ArticleAdapter articleAdapter; private int num = 10;//加载文章列表,每次加载十条 private int page = 1;//加载文章的页数 public static HealthEducationFragment newInstance(String mainId) { HealthEducationFragment fragment = new HealthEducationFragment(); Bundle args = new Bundle(); args.putString(MAIN_ID, mainId); fragment.setArguments(args); return fragment; } @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); if (getArguments() != null) { mainId = getArguments().getString(MAIN_ID); } } @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { // Inflate the layout for this fragment if (mFragmentView == null) { mFragmentView = inflater.inflate(R.layout.fragment_health_education, container, false); ButterKnife.bind(this, mFragmentView); } articleAdapter = new ArticleAdapter(getActivity(), listArticleBeanArrayList); listView.setAdapter(articleAdapter); articleAdapter.registerDataSetObserver(new MyDataSetObserver(listView)); // 刷新label的设置 // mPullRefreshScrollView.getLoadingLayoutProxy().setLastUpdatedLabel("上次刷新时间"); mPullRefreshScrollView.getLoadingLayoutProxy().setPullLabel("下拉刷新"); mPullRefreshScrollView.getLoadingLayoutProxy().setReleaseLabel("松开即可刷新"); //上拉监听函数 mPullRefreshScrollView.setOnRefreshListener(new PullToRefreshBase.OnRefreshListener2<ScrollView>() { @Override public void onPullDownToRefresh(PullToRefreshBase<ScrollView> refreshView) { Log.e("TAG", "onPullDownToRefresh"); listArticleBeanArrayList.clear(); //这里写下拉刷新的任务 page = 1; getListArticleBYMainId(); } @Override public void onPullUpToRefresh(PullToRefreshBase<ScrollView> refreshView) { Log.e("TAG", "onPullUpToRefresh"); //这里写上拉加载更多的任务 page++; getListArticleBYMainId(); } }); return mFragmentView; } @Override public void initData() { getListArticleChildClass(); getListArticleBYMainId(); } public void getListArticleChildClass() { String url = Contants.APIURL.GET_LISTARTICLECHILDCLASS.getUrl().replace("{id}", mainId); RequestEntity<String> entity = new RequestEntity<>(); OkHttpUtils.get().url(url).headers(entity.getHeader()).build().execute(new JsonCallBack<ResponseEntity<ArrayList<ArticleBean>>>() { @Override public void onError(Call call, Exception e, RequestCall requestCall) { ToastUtil.showLongToast("网络异常,请稍后尝试"); } @Override public void onResponse(ResponseEntity<ArrayList<ArticleBean>> data, RequestCall requestCall) { if (data.isOK()) { childBeanList.clear(); childBeanList.addAll(data.getRstData()); idFlowLayout.removeAllViews(); for (final ArticleBean s : childBeanList) { FlowLayoutItem flowLayoutItem = new FlowLayoutItem(getActivity()); LinearLayout.LayoutParams params = new LinearLayout.LayoutParams(LinearLayout.LayoutParams.WRAP_CONTENT, LinearLayout.LayoutParams.WRAP_CONTENT); flowLayoutItem.setmViewInterface(new FlowLayoutItem.viewInterface() { @Override public void viewOnClick() { HealthArticleListActivity.start(getActivity(), s.getName(), s.getId()); } }); idFlowLayout.addView(flowLayoutItem.getItemView(s.getName()), 0, params); } //防止listview加载完数据,只显示listview,将listview顶部控件顶入上方,不可见 mPullRefreshScrollView.post(new Runnable() { @Override public void run() { mPullRefreshScrollView.getRefreshableView().fullScroll(ScrollView.FOCUS_UP); } }); } else { ToastUtil.showLongToast(data.getErrorMsg()); } } }); } //返回主目录下所有的文章列表 public void getListArticleBYMainId() { String url = Contants.APIURL.GET_LISTARTICLEBYMAINID.getUrl().replace("{MainId}", mainId).replace("{page}", page + "").replace("{num}", num + ""); RequestEntity<String> entity = new RequestEntity<>(); OkHttpUtils.get().url(url).headers(entity.getHeader()).build().execute(new JsonCallBack<ResponseEntity<ArrayList<ListArticleBean>>>() { @Override public void onError(Call call, Exception e, RequestCall requestCall) { ToastUtil.showLongToast("网络异常,请稍后尝试"); } @Override public void onResponse(ResponseEntity<ArrayList<ListArticleBean>> data, RequestCall requestCall) { if (data.isOK()) { listArticleBeanArrayList.addAll(data.getRstData()); if (data.getRstData().size() < num) {//如果加载的文章条数小于num,说明数据已加载完 mPullRefreshScrollView.setMode(PullToRefreshBase.Mode.PULL_FROM_START); ToastUtil.showShortToast("没有更多数据了"); } else { mPullRefreshScrollView.setMode(PullToRefreshBase.Mode.BOTH); } articleAdapter.notifyDataSetChanged(); mPullRefreshScrollView.onRefreshComplete(); //防止listview加载完数据,只显示listview,将listview顶部控件顶入上方,不可见 if (page == 1) { mPullRefreshScrollView.post(new Runnable() { @Override public void run() { mPullRefreshScrollView.getRefreshableView().fullScroll(ScrollView.FOCUS_UP); } }); } } else { ToastUtil.showLongToast(data.getErrorMsg()); } } }); } @Override public void onDestroyView() { super.onDestroyView(); if (null != mFragmentView) { ((ViewGroup) mFragmentView.getParent()).removeView(mFragmentView); } } /** * 解决PullToRefreshScrollView嵌套Listview问题 */ public class MyDataSetObserver extends DataSetObserver { private ListView listview; public MyDataSetObserver(ListView listview) { super(); this.listview = listview; } @Override public void onChanged() { super.onChanged(); setListViewHeightBasedOnChildren(listview); } /** * 计算listview高度并重设 * * @param listView */ public void 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); } } }
LazyFragment.java
/** * Fragment 懒加载 */ public abstract class LazyFragment extends Fragment { public Context mContext; protected boolean isVisible; private boolean isPrepared; private boolean isFirst = true; public LazyFragment() { } @Override public void onCreate(@Nullable Bundle savedInstanceState) { super.onCreate(savedInstanceState); mContext = getActivity(); setHasOptionsMenu(true); } @Override public void onActivityCreated(@Nullable Bundle savedInstanceState) { super.onActivityCreated(savedInstanceState); isPrepared = true; lazyLoad(); } @Override public void setUserVisibleHint(boolean isVisibleToUser) { super.setUserVisibleHint(isVisibleToUser); if (getUserVisibleHint()) { isVisible = true; lazyLoad(); } else { isVisible = false; onInvisible(); } } protected void lazyLoad() { if (!isPrepared || !isVisible || !isFirst) { return; } initData(); isFirst = false; } //do something protected void onInvisible() { } public abstract void initData(); }
fragment_health_education.xml
<?xml version="1.0" encoding="utf-8"?> <com.handmark.pulltorefresh.library.PullToRefreshScrollView xmlns:tools="http://schemas.android.com/tools" xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" xmlns:ptr="http://schemas.android.com/apk/res-auto" android:background="@color/white" ptr:ptrAnimationStyle="flip" ptr:ptrMode="both" android:id="@+id/pull_refresh_scrollview"> <LinearLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="vertical" android:background="@color/white" tools:context="com.mandala.healthserviceresident.fragment.HealthEducationFragment"> <ImageView android:layout_width="match_parent" android:layout_height="wrap_content" android:src="@drawable/search_layout" android:focusable="true" android:focusableInTouchMode="true" /> <com.mandala.healthserviceresident.widget.FlowLayout android:id="@+id/id_flow_layout" android:layout_width="match_parent" android:layout_height="wrap_content" /> <ListView android:id="@+id/listView" android:layout_width="fill_parent" android:layout_height="fill_parent" android:dividerHeight="0.2dp" /> </LinearLayout> </com.handmark.pulltorefresh.library.PullToRefreshScrollView>
FlowLayout.java
public class FlowLayout extends ViewGroup
{
private static final String TAG = "FlowLayout"; public FlowLayout(Context context, AttributeSet attrs) { super(context, attrs); } @Override protected LayoutParams generateLayoutParams( LayoutParams p) { return new MarginLayoutParams(p); } @Override public LayoutParams generateLayoutParams(AttributeSet attrs) { return new MarginLayoutParams(getContext(), attrs); } @Override protected LayoutParams generateDefaultLayoutParams() { return new MarginLayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT); } /** * 负责设置子控件的测量模式和大小 根据所有子控件设置自己的宽和高 */ @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { super.onMeasure(widthMeasureSpec, heightMeasureSpec); // 获得它的父容器为它设置的测量模式和大小 int sizeWidth = MeasureSpec.getSize(widthMeasureSpec); int sizeHeight = MeasureSpec.getSize(heightMeasureSpec); int modeWidth = MeasureSpec.getMode(widthMeasureSpec); int modeHeight = MeasureSpec.getMode(heightMeasureSpec); Log.e(TAG, sizeWidth + "," + sizeHeight); // 如果是warp_content情况下,记录宽和高 int width = 0; int height = 0; /** * 记录每一行的宽度,width不断取最大宽度 */ int lineWidth = 0; /** * 每一行的高度,累加至height */ int lineHeight = 0; int cCount = getChildCount(); // 遍历每个子元素 for (int i = 0; i < cCount; i++) { View child = getChildAt(i); // 测量每一个child的宽和高 measureChild(child, widthMeasureSpec, heightMeasureSpec); // 得到child的lp MarginLayoutParams lp = (MarginLayoutParams) child .getLayoutParams(); // 当前子空间实际占据的宽度 int childWidth = child.getMeasuredWidth() + lp.leftMargin + lp.rightMargin; // 当前子空间实际占据的高度 int childHeight = child.getMeasuredHeight() + lp.topMargin + lp.bottomMargin; /** * 如果加入当前child,则超出最大宽度,则的到目前最大宽度给width,类加height 然后开启新行 */ if (lineWidth + childWidth > sizeWidth) { width = Math.max(lineWidth, childWidth);// 取最大的 lineWidth = childWidth; // 重新开启新行,开始记录 // 叠加当前高度, height += lineHeight; // 开启记录下一行的高度 lineHeight = childHeight; } else // 否则累加值lineWidth,lineHeight取最大高度 { lineWidth += childWidth; lineHeight = Math.max(lineHeight, childHeight); } // 如果是最后一个,则将当前记录的最大宽度和当前lineWidth做比较 if (i == cCount - 1) { width = Math.max(width, lineWidth); height += lineHeight; } } setMeasuredDimension((modeWidth == MeasureSpec.EXACTLY) ? sizeWidth : width, (modeHeight == MeasureSpec.EXACTLY) ? sizeHeight : height); } /** * 存储所有的View,按行记录 */ private List<List<View>> mAllViews = new ArrayList<List<View>>(); /** * 记录每一行的最大高度 */ private List<Integer> mLineHeight = new ArrayList<Integer>(); @Override protected void onLayout(boolean changed, int l, int t, int r, int b) { mAllViews.clear(); mLineHeight.clear(); int width = getWidth(); int lineWidth = 0; int lineHeight = 0; // 存储每一行所有的childView List<View> lineViews = new ArrayList<View>(); int cCount = getChildCount(); // 遍历所有的孩子 for (int i = 0; i < cCount; i++) { View child = getChildAt(i); MarginLayoutParams lp = (MarginLayoutParams) child .getLayoutParams(); int childWidth = child.getMeasuredWidth(); int childHeight = child.getMeasuredHeight(); // 如果已经需要换行 if (childWidth + lp.leftMargin + lp.rightMargin + lineWidth > width) { // 记录这一行所有的View以及最大高度 mLineHeight.add(lineHeight); // 将当前行的childView保存,然后开启新的ArrayList保存下一行的childView mAllViews.add(lineViews); lineWidth = 0;// 重置行宽 lineViews = new ArrayList<View>(); } /** * 如果不需要换行,则累加 */ lineWidth += childWidth + lp.leftMargin + lp.rightMargin; lineHeight = Math.max(lineHeight, childHeight + lp.topMargin + lp.bottomMargin); lineViews.add(child); } // 记录最后一行 mLineHeight.add(lineHeight); mAllViews.add(lineViews); int left = 0; int top = 0; // 得到总行数 int lineNums = mAllViews.size(); for (int i = 0; i < lineNums; i++) { // 每一行的所有的views lineViews = mAllViews.get(i); // 当前行的最大高度 lineHeight = mLineHeight.get(i); Log.e(TAG, "第" + i + "行 :" + lineViews.size() + " , " + lineViews); Log.e(TAG, "第" + i + "行, :" + lineHeight); // 遍历当前行所有的View for (int j = 0; j < lineViews.size(); j++) { View child = lineViews.get(j); if (child.getVisibility() == View.GONE) { continue; } MarginLayoutParams lp = (MarginLayoutParams) child .getLayoutParams(); //计算childView的left,top,right,bottom int lc = left + lp.leftMargin; int tc = top + lp.topMargin; int rc =lc + child.getMeasuredWidth(); int bc = tc + child.getMeasuredHeight(); Log.e(TAG, child + " , l = " + lc + " , t = " + t + " , r =" + rc + " , b = " + bc); child.layout(lc, tc, rc, bc); left += child.getMeasuredWidth() + lp.rightMargin + lp.leftMargin; } left = 0; top += lineHeight; } }
}
ArticleAdapter
/** * 健康教育,文章列表adapter * */ public class ArticleAdapter extends BaseAdapter { private Context mContext; private List<ListArticleBean> arrayList ; private DisplayImageOptions options = null; public ArticleAdapter(Context context,List<ListArticleBean> mArrayList) { mContext=context; arrayList = mArrayList; options = new DisplayImageOptions.Builder().showImageOnLoading(R.drawable.health_teach_loading).showImageForEmptyUri(R.drawable.health_teach_error).showImageOnFail(R.drawable.health_teach_error).build(); } @Override public int getCount() { return arrayList.size(); } @Override public Object getItem(int position) { return position; } @Override public long getItemId(int position) { return position; } @Override public View getView(final int position, View convertView, ViewGroup parent) { ViewHolder viewHolder; if (convertView == null) { convertView = LayoutInflater.from(mContext).inflate(R.layout.item_article, null); viewHolder = new ViewHolder(); viewHolder.tvNewsTitle = (TextView) convertView.findViewById(com.mandala.healthserviceresident.R.id.tv_newsTitle); viewHolder.ivNewsContent = (ImageView) convertView.findViewById(R.id.iv_newsContent); convertView.setTag(viewHolder); } else { viewHolder = (ViewHolder) convertView.getTag(); } Resources resources =mContext.getResources(); DisplayMetrics dm = resources.getDisplayMetrics(); //获取手机宽度 int scrennWidth = dm.widthPixels; /** * (int) (x * scrennWidth / 640.0 + 0.5) * x 标注图显示的标注 * 640.0 标注图宽度 * 0.5 用来四舍五入 */ int height = (int) (130 * scrennWidth / 640.0 + 0.5); ViewGroup.LayoutParams parmas = viewHolder.ivNewsContent.getLayoutParams(); parmas.height = height; parmas.width = 2*height; viewHolder.ivNewsContent.setLayoutParams(parmas); viewHolder.tvNewsTitle.setText(arrayList.get(position).getTitle()); ImageLoader.getInstance().displayImage(arrayList.get(position).getImageUrl(), viewHolder.ivNewsContent, options); convertView.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { if (TextUtils.isEmpty(arrayList.get(position).getUrl())) { ToastUtil.showLongToast("服务器数据异常,请稍后尝试"); } else { WebViewActivity.start(mContext, "", arrayList.get(position).getUrl() + "?t=" + System.currentTimeMillis()); } } }); return convertView; } public static class ViewHolder { TextView tvNewsTitle; ImageView ivNewsContent; } }
PagerSlidingTabStrip.java
public class PagerSlidingTabStrip extends HorizontalScrollView { public interface IconTabProvider { public int getPageIconResId(int position); } // @formatter:off private static final int[] ATTRS = new int[] { android.R.attr.textSize, android.R.attr.textColor }; // @formatter:on private LinearLayout.LayoutParams defaultTabLayoutParams; private LinearLayout.LayoutParams expandedTabLayoutParams; private final PageListener pageListener = new PageListener(); public ViewPager.OnPageChangeListener delegatePageListener; private LinearLayout tabsContainer; private ViewPager pager; private int tabCount; private int currentPosition = 0; private int selectedPosition = 0; private float currentPositionOffset = 0f; private Paint rectPaint; private Paint dividerPaint; private int indicatorColor = 0xFF666666; private int underlineColor = 0x1A000000; private int dividerColor = 0x1A000000; private boolean shouldExpand = false; private boolean textAllCaps = true; private int scrollOffset = 52; private int indicatorHeight = 8; private int underlineHeight = 2; private int dividerPadding = 12; private int tabPadding = 24; private int dividerWidth = 1; private int tabTextSize = 12; private int tabTextColor = 0xFF666666; private int selectedTabTextColor = 0xFF666666; private Typeface tabTypeface = null; private int tabTypefaceStyle = Typeface.NORMAL; private int lastScrollX = 0; private int tabBackgroundResId = R.drawable.background_tab; private Locale locale; public PagerSlidingTabStrip(Context context) { this(context, null); } public PagerSlidingTabStrip(Context context, AttributeSet attrs) { this(context, attrs, 0); } public PagerSlidingTabStrip(Context context, AttributeSet attrs, int defStyle) { super(context, attrs, defStyle); setFillViewport(true); setWillNotDraw(false); tabsContainer = new LinearLayout(context); tabsContainer.setOrientation(LinearLayout.HORIZONTAL); tabsContainer.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT)); addView(tabsContainer); DisplayMetrics dm = getResources().getDisplayMetrics(); scrollOffset = (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, scrollOffset, dm); indicatorHeight = (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, indicatorHeight, dm); underlineHeight = (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, underlineHeight, dm); dividerPadding = (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, dividerPadding, dm); tabPadding = (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, tabPadding, dm); dividerWidth = (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, dividerWidth, dm); tabTextSize = (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_SP, tabTextSize, dm); // get system attrs (android:textSize and android:textColor) TypedArray a = context.obtainStyledAttributes(attrs, ATTRS); tabTextSize = a.getDimensionPixelSize(0, tabTextSize); tabTextColor = a.getColor(1, tabTextColor); a.recycle(); // get custom attrs a = context.obtainStyledAttributes(attrs, R.styleable.PagerSlidingTabStrip); indicatorColor = a.getColor(R.styleable.PagerSlidingTabStrip_pstsIndicatorColor, indicatorColor); underlineColor = a.getColor(R.styleable.PagerSlidingTabStrip_pstsUnderlineColor, underlineColor); dividerColor = a.getColor(R.styleable.PagerSlidingTabStrip_pstsDividerColor, dividerColor); indicatorHeight = a.getDimensionPixelSize(R.styleable.PagerSlidingTabStrip_pstsIndicatorHeight, indicatorHeight); underlineHeight = a.getDimensionPixelSize(R.styleable.PagerSlidingTabStrip_pstsUnderlineHeight, underlineHeight); dividerPadding = a.getDimensionPixelSize(R.styleable.PagerSlidingTabStrip_pstsDividerPadding, dividerPadding); tabPadding = a.getDimensionPixelSize(R.styleable.PagerSlidingTabStrip_pstsTabPaddingLeftRight, tabPadding); tabBackgroundResId = a.getResourceId(R.styleable.PagerSlidingTabStrip_pstsTabBackground, tabBackgroundResId); shouldExpand = a.getBoolean(R.styleable.PagerSlidingTabStrip_pstsShouldExpand, shouldExpand); scrollOffset = a.getDimensionPixelSize(R.styleable.PagerSlidingTabStrip_pstsScrollOffset, scrollOffset); textAllCaps = a.getBoolean(R.styleable.PagerSlidingTabStrip_pstsTextAllCaps, textAllCaps); a.recycle(); rectPaint = new Paint(); rectPaint.setAntiAlias(true); rectPaint.setStyle(Paint.Style.FILL); dividerPaint = new Paint(); dividerPaint.setAntiAlias(true); dividerPaint.setStrokeWidth(dividerWidth); defaultTabLayoutParams = new LinearLayout.LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.MATCH_PARENT); expandedTabLayoutParams = new LinearLayout.LayoutParams(0, LayoutParams.MATCH_PARENT, 1.0f); if (locale == null) { locale = getResources().getConfiguration().locale; } } public void setViewPager(ViewPager pager) { this.pager = pager; if (pager.getAdapter() == null) { throw new IllegalStateException("ViewPager does not have adapter instance."); } pager.setOnPageChangeListener(pageListener); notifyDataSetChanged(); } public void setOnPageChangeListener(ViewPager.OnPageChangeListener listener) { this.delegatePageListener = listener; } public void notifyDataSetChanged() { tabsContainer.removeAllViews(); tabCount = pager.getAdapter().getCount(); for (int i = 0; i < tabCount; i++) { if (pager.getAdapter() instanceof IconTabProvider) { addIconTab(i, ((IconTabProvider) pager.getAdapter()).getPageIconResId(i)); } else { addTextTab(i, pager.getAdapter().getPageTitle(i).toString()); } } updateTabStyles(); getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() { @Override public void onGlobalLayout() { getViewTreeObserver().removeGlobalOnLayoutListener(this); currentPosition = pager.getCurrentItem(); scrollToChild(currentPosition, 0); } }); } private void addTextTab(final int position, String title) { TextView tab = new TextView(getContext()); tab.setText(title); tab.setGravity(Gravity.CENTER); tab.setSingleLine(); addTab(position, tab); } private void addIconTab(final int position, int resId) { ImageButton tab = new ImageButton(getContext()); tab.setImageResource(resId); addTab(position, tab); } private void addTab(final int position, View tab) { tab.setFocusable(true); tab.setOnClickListener(new OnClickListener() { @Override public void onClick(View v) { pager.setCurrentItem(position); } }); tab.setPadding(tabPadding, 0, tabPadding, 0); tabsContainer.addView(tab, position, shouldExpand ? expandedTabLayoutParams : defaultTabLayoutParams); } private void updateTabStyles() { for (int i = 0; i < tabCount; i++) { View v = tabsContainer.getChildAt(i); v.setBackgroundResource(tabBackgroundResId); if (v instanceof TextView) { TextView tab = (TextView) v; tab.setTextSize(TypedValue.COMPLEX_UNIT_PX, tabTextSize); tab.setTypeface(tabTypeface, tabTypefaceStyle); tab.setTextColor(tabTextColor); // setAllCaps() is only available from API 14, so the upper case is made manually if we are on a // pre-ICS-build if (textAllCaps) { if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.ICE_CREAM_SANDWICH) { tab.setAllCaps(true); } else { tab.setText(tab.getText().toString().toUpperCase(locale)); } } if (i == selectedPosition) { tab.setTextColor(selectedTabTextColor); } } } } private void scrollToChild(int position, int offset) { if (tabCount == 0) { return; } int newScrollX = tabsContainer.getChildAt(position).getLeft() + offset; if (position > 0 || offset > 0) { newScrollX -= scrollOffset; } if (newScrollX != lastScrollX) { lastScrollX = newScrollX; scrollTo(newScrollX, 0); } } @Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); if (isInEditMode() || tabCount == 0) { return; } final int height = getHeight(); // draw underline rectPaint.setColor(underlineColor); canvas.drawRect(0, height - underlineHeight, tabsContainer.getWidth(), height, rectPaint); // draw indicator line rectPaint.setColor(indicatorColor); // default: line below current tab View currentTab = tabsContainer.getChildAt(currentPosition); float lineLeft = currentTab.getLeft(); float lineRight = currentTab.getRight(); // if there is an offset, start interpolating left and right coordinates between current and next tab if (currentPositionOffset > 0f && currentPosition < tabCount - 1) { View nextTab = tabsContainer.getChildAt(currentPosition + 1); final float nextTabLeft = nextTab.getLeft(); final float nextTabRight = nextTab.getRight(); lineLeft = (currentPositionOffset * nextTabLeft + (1f - currentPositionOffset) * lineLeft); lineRight = (currentPositionOffset * nextTabRight + (1f - currentPositionOffset) * lineRight); } //通过处理tabPadding,设置底部横线与文字宽度一致, canvas.drawRect(lineLeft+tabPadding, height - indicatorHeight, lineRight-tabPadding, height, rectPaint); //默认设置,底部横线填满宽度 // canvas.drawRect(lineLeft, height - indicatorHeight, lineRight, height, rectPaint); // draw divider dividerPaint.setColor(dividerColor); for (int i = 0; i < tabCount - 1; i++) { View tab = tabsContainer.getChildAt(i); canvas.drawLine(tab.getRight(), dividerPadding, tab.getRight(), height - dividerPadding, dividerPaint); } } private class PageListener implements ViewPager.OnPageChangeListener { @Override public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) { currentPosition = position; currentPositionOffset = positionOffset; scrollToChild(position, (int) (positionOffset * tabsContainer.getChildAt(position).getWidth())); invalidate(); if (delegatePageListener != null) { delegatePageListener.onPageScrolled(position, positionOffset, positionOffsetPixels); } } @Override public void onPageScrollStateChanged(int state) { if (state == ViewPager.SCROLL_STATE_IDLE) { scrollToChild(pager.getCurrentItem(), 0); } if (delegatePageListener != null) { delegatePageListener.onPageScrollStateChanged(state); } } @Override public void onPageSelected(int position) { selectedPosition = position; updateTabStyles(); if (delegatePageListener != null) { delegatePageListener.onPageSelected(position); } } } public void setIndicatorColor(int indicatorColor) { this.indicatorColor = indicatorColor; invalidate(); } public void setIndicatorColorResource(int resId) { this.indicatorColor = getResources().getColor(resId); invalidate(); } public int getIndicatorColor() { return this.indicatorColor; } public void setIndicatorHeight(int indicatorLineHeightPx) { this.indicatorHeight = indicatorLineHeightPx; invalidate(); } public int getIndicatorHeight() { return indicatorHeight; } public void setUnderlineColor(int underlineColor) { this.underlineColor = underlineColor; invalidate(); } public void setUnderlineColorResource(int resId) { this.underlineColor = getResources().getColor(resId); invalidate(); } public int getUnderlineColor() { return underlineColor; } public void setDividerColor(int dividerColor) { this.dividerColor = dividerColor; invalidate(); } public void setDividerColorResource(int resId) { this.dividerColor = getResources().getColor(resId); invalidate(); } public int getDividerColor() { return dividerColor; } public void setUnderlineHeight(int underlineHeightPx) { this.underlineHeight = underlineHeightPx; invalidate(); } public int getUnderlineHeight() { return underlineHeight; } public void setDividerPadding(int dividerPaddingPx) { this.dividerPadding = dividerPaddingPx; invalidate(); } public int getDividerPadding() { return dividerPadding; } public void setScrollOffset(int scrollOffsetPx) { this.scrollOffset = scrollOffsetPx; invalidate(); } public int getScrollOffset() { return scrollOffset; } public void setShouldExpand(boolean shouldExpand) { this.shouldExpand = shouldExpand; notifyDataSetChanged(); } public boolean getShouldExpand() { return shouldExpand; } public boolean isTextAllCaps() { return textAllCaps; } public void setAllCaps(boolean textAllCaps) { this.textAllCaps = textAllCaps; } public void setTextSize(int textSizePx) { this.tabTextSize = textSizePx; updateTabStyles(); } public int getTextSize() { return tabTextSize; } public void setTextColor(int textColor) { this.tabTextColor = textColor; updateTabStyles(); } public void setTextColorResource(int resId) { this.tabTextColor = getResources().getColor(resId); updateTabStyles(); } public int getTextColor() { return tabTextColor; } public void setSelectedTextColor(int textColor) { this.selectedTabTextColor = textColor; updateTabStyles(); } public void setSelectedTextColorResource(int resId) { this.selectedTabTextColor = getResources().getColor(resId); updateTabStyles(); } public int getSelectedTextColor() { return selectedTabTextColor; } public void setTypeface(Typeface typeface, int style) { this.tabTypeface = typeface; this.tabTypefaceStyle = style; updateTabStyles(); } public void setTabBackground(int resId) { this.tabBackgroundResId = resId; updateTabStyles(); } public int getTabBackground() { return tabBackgroundResId; } public void setTabPaddingLeftRight(int paddingPx) { this.tabPadding = paddingPx; updateTabStyles(); } public int getTabPaddingLeftRight() { return tabPadding; } @Override public void onRestoreInstanceState(Parcelable state) { SavedState savedState = (SavedState) state; super.onRestoreInstanceState(savedState.getSuperState()); currentPosition = savedState.currentPosition; requestLayout(); } @Override public Parcelable onSaveInstanceState() { Parcelable superState = super.onSaveInstanceState(); SavedState savedState = new SavedState(superState); savedState.currentPosition = currentPosition; return savedState; } static class SavedState extends BaseSavedState { int currentPosition; public SavedState(Parcelable superState) { super(superState); } private SavedState(Parcel in) { super(in); currentPosition = in.readInt(); } @Override public void writeToParcel(Parcel dest, int flags) { super.writeToParcel(dest, flags); dest.writeInt(currentPosition); } public static final Parcelable.Creator<SavedState> CREATOR = new Parcelable.Creator<SavedState>() { @Override public SavedState createFromParcel(Parcel in) { return new SavedState(in); } @Override public SavedState[] newArray(int size) { return new SavedState[size]; } }; } }
以上是文章类对应的文件,使用了一个第三方类库,PullToRefreshScrollView,实现上拉下拉功能。
相关文章推荐
- 仿新闻类实现滑动选择标签(二)
- php jquery 实现新闻标签分类与无刷新分页
- JQuery 绑定select标签的onchange事件,弹出选择的值,并实现跳转、传参(selected的值和页面其它元素的值)
- android FragmentTabhost+ViewPager实现可滑动的标签页
- 用Jquery实现修改页面selecte标签的默认选择
- ActionBarSherlock与Viewpager及Fragment结合实现仿新闻客户端顶部滑动切换效果
- php + jquery ui插件 + jquery pager插件 实现新闻的 标签分类 + 无刷新分页
- Android之Tab分页标签的实现方法一-----可滑动的Tab的3种方式
- 在窗体上放置一个标签、一个按钮、一个fontDialog控件。标签内容改为“烟台大学”。实现功能:1)程序运行时,单击打开字体对话框按钮,可选择字体,并以所选字体作为标签字体。
- 。窗体上有一个文本框(多行、且带有垂直滚动条)、一个标签(字体颜色红色、字号16)、一个按钮(该按钮被单击时,实现将文本框中选择文本复制至标签。
- 用Jquery实现修改页面selecte标签的默认选择
- JQuery 绑定select标签的onchange事件,弹出选择的值,并实现跳转、传参
- JQuery 绑定select标签的onchange事件,弹出选择的值,并实现跳转、传参
- 游戏引擎Andengine总结(六):滑动关卡选择的实现
- Struts2标签实现for循环 分页 选择第几页
- 基于jquery的选择标签至文本域效果,可多选/可过滤重复/可限制个数的实现代码
- 使用 TabActivity 实现滑动翻页(带动画)和标签置底
- 关于JSP中单击任意标签弹出文件选择框(<input type="file"/>)的实现方法
- 滑动菜单方案之二: Activity实现从底部弹出或滑出选择菜单或窗口
- Android 实现用户列表信息滑动删除功能和选择删除功能