自定义HorizontalScrollView实现左右滑动界面

public class TimeLimitPurchaseScrollView extends HorizontalScrollView implements
      OnClickListener
{

   /**
    * 图片滚动时的回调接口
    *
    * @author zhy
    *
    */
   public interface CurrentImageChangeListener
   {
      void onCurrentImgChanged(int position, View viewIndicator);
   }

   /**
    * 条目点击时的回调
    *
    * @author zhy
    *
    */
   public interface OnItemClickListener
   {
      void onClick(View view, int pos);
   }

   private CurrentImageChangeListener mListener;

   private OnItemClickListener mOnClickListener;

   private static final String TAG = "MyHorizontalScrollView";

   /**
    * HorizontalListView中的LinearLayout
    */
   private LinearLayout mContainer;

   /**
    * 子元素的宽度
    */
   private int mChildWidth;
   /**
    * 子元素的高度
    */
   private int mChildHeight;
   /**
    * 当前最后一张图片的index
    */
   private int mCurrentIndex;
   /**
    * 当前第一张图片的下标
    */
   private int mFristIndex;
   /**
    * 当前第一个View
    */
   private View mFirstView;
   /**
    * 数据适配器
    */
   private TimeLimitPurchaseAdapter mAdapter;
   /**
    * 每屏幕最多显示的个数
    */
   private int mCountOneScreen;
   /**
    * 屏幕的宽度
    */
   private int mScreenWitdh;


   /**
    * 保存View与位置的键值对
    */
   private Map<View, Integer> mViewPos = new HashMap<View, Integer>();

   public TimeLimitPurchaseScrollView(Context context, AttributeSet attrs)
   {
      super(context, attrs);
      // 获得屏幕宽度
      WindowManager wm = (WindowManager) context
            .getSystemService(Context.WINDOW_SERVICE);
      DisplayMetrics outMetrics = new DisplayMetrics();
      wm.getDefaultDisplay().getMetrics(outMetrics);
      mScreenWitdh = outMetrics.widthPixels;
   }

   @Override
   protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec)
   {
      super.onMeasure(widthMeasureSpec, heightMeasureSpec);
      mContainer = (LinearLayout) getChildAt(0);
   }

   /**
    * 加载下一张图片
    */
   protected void loadNextImg()
   {
      // 数组边界值计算
      if (mCurrentIndex == mAdapter.getCount() - 1)
      {
         return;
      }
      //移除第一张图片,且将水平滚动位置置0
      scrollTo(0, 0);
      mViewPos.remove(mContainer.getChildAt(0));
      mContainer.removeViewAt(0);
      
      //获取下一张图片,并且设置onclick事件,且加入容器中
      View view = mAdapter.getView(++mCurrentIndex, null, mContainer);
      view.setOnClickListener(this);
      mContainer.addView(view);
      mViewPos.put(view, mCurrentIndex);
      
      //当前第一张图片小标
      mFristIndex++;
      //如果设置了滚动监听则触发
      if (mListener != null)
      {
         notifyCurrentImgChanged();
      }

   }
   /**
    * 加载前一张图片
    */
   protected void loadPreImg()
   {
      //如果当前已经是第一张,则返回
      if (mFristIndex == 0)
         return;
      //获得当前应该显示为第一张图片的下标
      int index = mCurrentIndex - mCountOneScreen;
      if (index >= 0)
      {
//       mContainer = (LinearLayout) getChildAt(0);
         //移除最后一张
         int oldViewPos = mContainer.getChildCount() - 1;
         mViewPos.remove(mContainer.getChildAt(oldViewPos));
         mContainer.removeViewAt(oldViewPos);
         
         //将此View放入第一个位置
         View view = mAdapter.getView(index, null, mContainer);
         mViewPos.put(view, index);
         mContainer.addView(view, 0);
         view.setOnClickListener(this);
         //水平滚动位置向左移动view的宽度个像素
         scrollTo(mChildWidth, 0);
         //当前位置--,当前第一个显示的下标--
         mCurrentIndex--;
         mFristIndex--;
         //回调
         if (mListener != null)
         {
            notifyCurrentImgChanged();

         }
      }
   }

   /**
    * 滑动时的回调
    */
   public void notifyCurrentImgChanged()
   {
      //先清除所有的背景色,点击时会设置为蓝色
      for (int i = 0; i < mContainer.getChildCount(); i++)
      {
         mContainer.getChildAt(i).setBackgroundColor(Color.WHITE);
      }
      
      mListener.onCurrentImgChanged(mFristIndex, mContainer.getChildAt(0));

   }

   /**
    * 初始化数据,设置数据适配器
    * 
    * @param mAdapter
    */
   public void initDatas(TimeLimitPurchaseAdapter mAdapter)
   {
      this.mAdapter = mAdapter;
      mContainer = (LinearLayout) getChildAt(0);
      // 获得适配器中第一个View
      final View view = mAdapter.getView(0, null, mContainer);
      mContainer.addView(view);

      // 强制计算当前View的宽和高
      if (mChildWidth == 0 && mChildHeight == 0)
      {
         int w = MeasureSpec.makeMeasureSpec(0,
               MeasureSpec.UNSPECIFIED);
         int h = MeasureSpec.makeMeasureSpec(0,
               MeasureSpec.UNSPECIFIED);
         view.measure(w, h);
         mChildHeight = view.getMeasuredHeight();
         mChildWidth = view.getMeasuredWidth();
         Log.e(TAG, view.getMeasuredWidth() + "," + view.getMeasuredHeight());
         mChildHeight = view.getMeasuredHeight();
         // 计算每次加载多少个View
         mCountOneScreen = (mScreenWitdh / mChildWidth == 0)?mScreenWitdh / mChildWidth+1:mScreenWitdh / mChildWidth+2;

         Log.e(TAG, "mCountOneScreen = " + mCountOneScreen
               + " ,mChildWidth = " + mChildWidth);
         

      }
      //初始化第一屏幕的元素
      initFirstScreenChildren(mCountOneScreen);
   }

   /**
    * 加载第一屏的View
    * 
    * @param mCountOneScreen
    */
   public void initFirstScreenChildren(int mCountOneScreen)
   {
      mContainer = (LinearLayout) getChildAt(0);
      mContainer.removeAllViews();
      mViewPos.clear();

      for (int i = 0; i < mCountOneScreen; i++)
      {
         View view = mAdapter.getView(i, null, mContainer);
         view.setOnClickListener(this);
         mContainer.addView(view);
         mViewPos.put(view, i);
         mCurrentIndex = i;
      }

      if (mListener != null)
      {
         notifyCurrentImgChanged();
      }

   }

   @Override
   public boolean onTouchEvent(MotionEvent ev)
   {
      switch (ev.getAction())
      {
      case MotionEvent.ACTION_MOVE:
//       Log.e(TAG, getScrollX() + "");

         int scrollX = getScrollX();
         // 如果当前scrollX为view的宽度,加载下一张,移除第一张
         if (scrollX >= mChildWidth)
         {
            loadNextImg();
         }
         // 如果当前scrollX = 0, 往前设置一张,移除最后一张
         if (scrollX == 0)
         {
            loadPreImg();
         }
         break;
      }
      return super.onTouchEvent(ev);
   }

   @Override
   public void onClick(View v)
   {
      if (mOnClickListener != null)
      {
         for (int i = 0; i < mContainer.getChildCount(); i++)
         {
            mContainer.getChildAt(i).setBackgroundColor(Color.WHITE);
         }
         mOnClickListener.onClick(v, mViewPos.get(v));
      }
   }

   public void setOnItemClickListener(OnItemClickListener mOnClickListener)
   {
      this.mOnClickListener = mOnClickListener;
   }

   public void setCurrentImageChangeListener(
         CurrentImageChangeListener mListener)
   {
      this.mListener = mListener;
   }

}
//布局显示
<com.emzk.app.view.TimeLimitPurchaseScrollView
    android:id="@+id/id_timeLimitPurchaseScrollView"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:background="@android:color/white"
    android:scrollbars="none" >

    <LinearLayout
        android:id="@+id/id_gallery"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal" >
    </LinearLayout>
</com.emzk.app.view.TimeLimitPurchaseScrollView>
 mStormAdapter = new TimeLimitPurchaseAdapter(getActivity(),mStormListData);
        timeLimitPurchaseScrollView.initDatas(mStormAdapter);
        timeLimitPurchaseScrollView.setOnItemClickListener(new TimeLimitPurchaseScrollView.OnItemClickListener() {
            @Override
            public void onClick(View view, int pos) {
                Intent intent=new Intent(getActivity(),CommodityDetailsPageActivity.class);
//                intent.putExtra("orderId", list.get(position).getOrderId());
                startActivity(intent);
            }
        });
        mStormAdapter.notifyDataSetChanged();
public class TimeLimitPurchaseAdapter extends BaseAdapter {

    Context context;
    List<TimeLimitPurchase> listData;

    public TimeLimitPurchaseAdapter(Context context,
                                    List<TimeLimitPurchase> listData) {
        this.context = context;
        this.listData = listData;
    }

    @Override
    public int getCount() {
        return listData.size();
    }

    @Override
    public Object getItem(int position) {
        return listData.get(position);
    }

    @Override
    public long getItemId(int position) {
        return position;
    }

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        ViewHolder viewHolder;
        final int pos = position;
        if (convertView == null) {
            LayoutInflater inflater = LayoutInflater.from(context);
            convertView = inflater.inflate(R.layout.time_limit_purchase_item, parent, false);
            viewHolder = new ViewHolder();
//                viewHolder.imageView = (ImageView) convertView
//                        .findViewById(R.id.index_gallery_item_image);
            viewHolder.tv_title = (TextView) convertView.findViewById(R.id.tv_title);
            viewHolder.tv_price = (TextView) convertView.findViewById(R.id.tv_price);
            viewHolder.tv_bonus = (TextView) convertView.findViewById(R.id.tv_bonus);
            viewHolder.tv_count_down = (TextView) convertView.findViewById(R.id.tv_count_down);
            convertView.setTag(viewHolder);
        } else {
            viewHolder = (ViewHolder) convertView.getTag();
            resetViewHolder(viewHolder);
        }

//            ImageLoader.getInstance().displayImage(listData.get(pos).getPigUrl(), viewHolder.imageView);
        viewHolder.tv_title.setText(listData.get(pos).getTitle());
        viewHolder.tv_price.setText("¥" + listData.get(pos).getPrice());
        viewHolder.tv_bonus.setText(listData.get(pos).getBonus() + "元");
        viewHolder.tv_count_down.setText(listData.get(pos).getCount_down());

        return convertView;
    }

    class ViewHolder {
        //            ImageView imageView;
        TextView tv_title;
        TextView tv_price;
        TextView tv_bonus;
        TextView tv_count_down;
    }

    protected void resetViewHolder(ViewHolder viewHolder) {
//            viewHolder.imageView.setImageBitmap(null);
        viewHolder.tv_title.setText("");
        viewHolder.tv_price.setText("");
        viewHolder.tv_bonus.setText("");
    }
}

time_limit_purchase_item布局

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="horizontal" android:layout_width="match_parent"
    android:layout_height="match_parent">
     <LinearLayout
         android:layout_width="300dp"
         android:layout_height="130dp"
         android:layout_marginLeft="5dp"
         android:background="@drawable/circle_rectangle"
         android:orientation="horizontal">
         <LinearLayout
             android:layout_width="0dp"
             android:layout_weight="3"
             android:orientation="vertical"
             android:layout_height="match_parent">
              <TextView
                  android:id="@+id/tv_title"
                  android:layout_width="match_parent"
                  android:layout_height="wrap_content"
                  android:text="@string/summer_love"
                  android:layout_marginLeft="5dp"
                  android:layout_marginTop="10dp"
                  android:textColor="#666666"
                  />
             <LinearLayout
                 android:layout_width="match_parent"
                 android:layout_height="wrap_content"
                 android:layout_marginTop="5dp"
                 android:orientation="horizontal">
             <TextView
                 android:id="@+id/tv_price"
                 android:layout_width="wrap_content"
                 android:layout_height="wrap_content"
                 android:layout_marginLeft="5dp"
                 android:textColor="#383838"
                 android:textSize="16sp"
                 android:text="99.00"/>
              <RelativeLayout
                  android:layout_width="wrap_content"
                  android:layout_marginLeft="10dp"
                  android:layout_height="wrap_content">

                   <Button
                       android:id="@+id/tv_bonus"
                       android:layout_width="80dp"
                       android:layout_height="18dp"
                       android:textColor="#E83033"
                       android:paddingLeft="10dp"
                       android:background="@drawable/bonus_oval_background"
                       android:text="800.5元"
                       />
                  <Button
                      android:layout_width="18dp"
                      android:layout_height="18dp"
                      android:textColor="@color/white"
                      android:gravity="center"
                      android:background="@drawable/bonus_round_background"
                      android:text="@string/bonus"/>
              </RelativeLayout>
             </LinearLayout>
             <View
                 android:layout_width="match_parent"
                 android:background="#F2F2F2"
                 android:layout_marginTop="10dp"
                 android:layout_height="1dp"/>
             <TextView
                 android:id="@+id/tv_count_down"
                 android:layout_width="match_parent"
                 android:layout_height="wrap_content"
                 android:layout_marginTop="10dp"
                 android:layout_marginLeft="5dp"
                 android:textColor="#999999"
                 android:text="剩 3 天 10 时 15 分 43 秒"
                 />
         </LinearLayout>
         <ImageView
             android:layout_width="0dp"
             android:layout_weight="2"
             android:layout_height="match_parent"
             android:layout_margin="5dp"
             android:src="@mipmap/leishi"/>
     </LinearLayout>
</LinearLayout>

猜你喜欢

转载自blog.csdn.net/qq_35572449/article/details/82182724