[lottery] 05_购彩大厅(四)——标题的滚动效果

Android 4.0

购彩大厅(四)——标题的滚动效果

技术点:1、获取屏幕的宽度高度
 DisplayMetrics 
WindowManager manager = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE);
Display display = manager.getDefaultDisplay();
DisplayMetrics outMetrics = new DisplayMetrics();
display.getMetrics(outMetrics);
float width = outMetrics.widthPixels;
 低版本:getWidth()
width = display.getWidth();  
 高版本:getSize()
Point outSize = new Point();
display.getSize(outSize);
width = outSize.x;
④总结:(获取屏幕宽度)
public float getWindowWidth() {
    
    WindowManager manager = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE);
    Display display = manager.getDefaultDisplay();
    
    DisplayMetrics outMetrics = new DisplayMetrics();
    display.getMetrics(outMetrics);
    float width = outMetrics.widthPixels;
    // int width = 0;
    // android2.3
    //获取版本
    int sdkVersion = Build.VERSION.SDK_INT;
    if (sdkVersion < 13) {// 低版本
        LogUtil.i(TAG"低版本系统:" + sdkVersion);
        width = display.getWidth();
    } else {
        LogUtil.i(TAG"高版本系统:" + sdkVersion);
        Point outSize = new Point();
        display.getSize(outSize);
        width = outSize.x;
    }
    return width;
}
2、设置ViewPager的滑动切换页面的监听
vpViewPager.setOnPageChangeListener(new OnPageChangeListener(){})
存在问题:标题的效果
需要自己实现标题效果
注意ImageView的scaleType =“matrix”,利用矩阵绘图,由于ImageView的宽度为填充父窗体,下划线需要在ImageView中来回的移动

下划线初始位置确定:(GloableParams.winWidth / 3 - mapWidth) / 2;
①屏幕宽度获取:
WindowManager manager = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE);
Display display = manager.getDefaultDisplay();
DisplayMetrics outMetrics = new DisplayMetrics();
display.getMetrics(outMetrics);
float width = outMetrics.widthPixels;
②图片宽度获取:
Bitmap bitmap=BitmapFactory.decodeResource(context.getResources(), R.drawable.id_category_selector);
int imgWidth=bitmap.getWidth();
③设置图片开始位置:
Matrix matrix = new Matrix();
matrix.postTranslate(left, 0);
selector.setImageMatrix(matrix);
④注册OnPageChangeListener的监听,处理onPageSelected方法,重点处理位移动画
float fromXDelta = currentTab*GlobalParams.WINDOW_WIDTH/titleCount;
float toXDelta = position * GlobalParams.WINDOW_WIDTH/titleCount;
Animation animation = new TranslateAnimation(fromXDelta, toXDelta, 0,0);
animation.setFillAfter(true);
animation.setDuration(300);
ivSelector.startAnimation(animation);
currentTab = position;
核心代码:
package cn.zengfansheng.lottery.view;
 
import java.util.ArrayList;
import java.util.List;
 
import org.apache.commons.lang3.StringUtils;
 
import android.annotation.SuppressLint;
import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Color;
import android.graphics.Matrix;
import android.graphics.Point;
import android.os.Build;
import android.support.v4.view.PagerAdapter;
import android.support.v4.view.ViewPager;
import android.support.v4.view.ViewPager.OnPageChangeListener;
import android.util.DisplayMetrics;
import android.view.Display;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.ViewGroup;
import android.view.WindowManager;
import android.view.animation.Animation;
import android.view.animation.TranslateAnimation;
import android.widget.BaseAdapter;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.ListView;
import android.widget.TextView;
import cn.zengfansheng.lottery.ConstantValue;
import cn.zengfansheng.lottery.GlobalParams;
import cn.zengfansheng.lottery.R;
import cn.zengfansheng.lottery.engine.CommonInfoEngine;
import cn.zengfansheng.lottery.factory.EngineFactory;
import cn.zengfansheng.lottery.net.protocol.Message;
import cn.zengfansheng.lottery.net.protocol.Olement;
import cn.zengfansheng.lottery.net.protocol.element.CurrentIssueElement;
import cn.zengfansheng.lottery.util.LogUtil;
import cn.zengfansheng.lottery.util.PromptManager;
 
public class HallView extends BaseView {
 
    // *****************属性声明*******************//
    private static final String TAG = "HallView";
 
    // 方案一: 存储服务器返回当期销售期信息
    // private Map<Integer, String> data;
 
    // 方案二:将每个彩种的用于展示当前销售期信息的TextView的引用,放入该集合
    // private List<TextView> tvLotterySummary;
 
    // *****************构造方法*******************//
    public HallView(Context context) {
        super(context);
    }
 
    // ********************标题的效果处理——下划线的位置处理******************** //
    // current*(屏幕宽度/3)/2 - 图片宽度/2
    private int titleCount;// 标题的个数
    private ImageView ivSelector;
 
    /**
     * 获取手机屏幕的宽度
     *
     * @return
     */

    @SuppressWarnings("deprecation")
    @SuppressLint("NewApi")
    public float getWindowWidth() {
 
        WindowManager manager = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE);
        Display display = manager.getDefaultDisplay();
 
        DisplayMetrics outMetrics = new DisplayMetrics();
        display.getMetrics(outMetrics);
        float width = outMetrics.widthPixels;
 
        // int width = 0;
        // android2.3
 
        int sdkVersion = Build.VERSION.SDK_INT;
        if (sdkVersion < 13) {// 低版本
            LogUtil.i(TAG, "低版本系统:" + sdkVersion);
            width = display.getWidth();
        } else {
            LogUtil.i(TAG, "高版本系统:" + sdkVersion);
            Point outSize = new Point();
            display.getSize(outSize);
            width = outSize.x;
        }
        return width;
    }

 
    // current*(屏幕宽度/3)/2 - 图片宽度/2
    /**
     * 设置初始位置
     */

    public void tabStripe() {
 
        GlobalParams.WINDOW_WIDTH = getWindowWidth();
        titleCount = TITLES.length;
 
        ivSelector = (ImageView) showView.findViewById(R.id.iv_category_selector_zl);
 
        Bitmap bitmap = BitmapFactory.decodeResource(context.getResources(), R.drawable.id_category_selector);
        // 图片宽度
        int imgWidth = bitmap.getWidth();
 
        float left = ((GlobalParams.WINDOW_WIDTH) / titleCount - imgWidth) / 2;
 
        Matrix matrix = new Matrix();
        matrix.postTranslate(left, 0);
        ivSelector.setImageMatrix(matrix );
 
    }
 
    // ********************ViewPager和PagerAdapter**************** //
 
    private final static String[] TITLES = new String[] { "福彩", "体彩", "高频彩" };
    // ViewPager
    private ViewPager vpViewPager;
    // ViewPagerAdapter适配器
    private MyPagetAdapter myPagetAdapter;
 
    // 中间显示的内容
    private List<View> views;
 
    //adapter
    private class MyPagetAdapter extends PagerAdapter{
        @Override
        public int getCount() {
            return TITLES.length;
        }
 
        @Override
        public boolean isViewFromObject(View view, Object object) {
            return view == object;
        }
 
        @Override
        public Object instantiateItem(ViewGroup container, int position) {
 
            View view = views.get(position);
            container.addView(view);
            return view;
        }
 
        @Override
        public void destroyItem(ViewGroup container, int position, Object object) {
            container.removeView(views.get(position));
        }
    }
 
    /**
     * ViewPager的初始化工作
     */

    public void initViewPager() {
 
        // 查找ViewPager
        vpViewPager = (ViewPager) this.findViewById(R.id.vp_category_hall_zl);
 
        // 设置ViewPager的数据适配器
        myPagetAdapter = new MyPagetAdapter();
        vpViewPager.setAdapter(myPagetAdapter);
 
        vpViewPager.addView(categoryList);
        // listViews.add(categoryList);
 
    }
 
    /**
     * 初始化ViewPager要显示的内容
     */

    public void initPagerViews(){
        //
        views = new ArrayList<View>();
        views.add(categoryList);
 
        TextView tv = new TextView(context);
 
        tv.setText("测试内容一");
        views.add(tv);
 
        tv = new TextView(context);
 
        tv.setText("测试内容二");
        views.add(tv);
    }
 
    // ********************ListView和ViewHolder****************//
    // 资源信息
    private static final int[] LOGORESIDS =  { R.drawable.id_ssq, R.drawable.id_3d, R.drawable.id_qlc };
 
    private static final int[] TITLERESIDS =   { R.string.is_hall_ssq_title, R.string.is_hall_3d_title, R.string.is_hall_qlc_title };
    // listview
    private ListView categoryList;
    //adapter
    private LotteryAdapter lotteryAdapter;
 
    private static class ViewHolder {
        private ImageView ivHallLotteryLogo;// 彩种Logo
        private TextView tvHallLotteryTitle;// 彩种Title
        private TextView tvHallLotterySummary;// 概要信息
        private ImageView ivHallLotteryBet;// 投注
    }
 
    private class LotteryAdapter extends BaseAdapter{
 
//        private  int[] LOGORESIDS =  { R.drawable.id_ssq, R.drawable.id_3d, R.drawable.id_qlc };
//        private  int[] TITLERESIDS =   { R.string.is_hall_ssq_title, R.string.is_hall_3d_title, R.string.is_hall_qlc_title };
 
        @Override
        public int getCount() {
            return LOGORESIDS.length;// FIXME:这里logoResIds如果不做成静态的或者不放在LotteryAdapter中,那么将获取不到这个数组的长度。
        }
        @Override
        public Object getItem(int position) {
            return null;
        }
        @Override
        public long getItemId(int position) {
            return position;
        }
        @Override
        public View getView(final int position, View convertView, ViewGroup parent) {
 
            LogUtil.i(TAG, "getView");
            View view = null;
            ViewHolder viewHolder = null;
            if (convertView != null && convertView instanceof LinearLayout) {
                view = convertView;
                viewHolder = (ViewHolder) view.getTag();
            } else {
 
                view = View.inflate(context, R.layout.zl_hall_lottery_item, null);
 
                viewHolder = new ViewHolder();
                viewHolder.ivHallLotteryLogo = (ImageView) view.findViewById(R.id.iv_hall_lottery_logo_zl);
                viewHolder.tvHallLotteryTitle = (TextView) view.findViewById(R.id.tv_hall_lottery_title_zl);
                viewHolder.tvHallLotterySummary = (TextView) view.findViewById(R.id.tv_hall_lottery_summary_zl);
                viewHolder.ivHallLotteryBet = (ImageView) view.findViewById(R.id.iv_hall_lottery_bet_zl);
 
                // 方案二:保存每一个需要变动的内容:tvHallLotterySummary
                // tvLotterySummary.add(viewHolder.tvHallLotterySummary);
 
                // 方案三:
                viewHolder.tvHallLotterySummary.setTag(position);// tag的用法二:唯一的标示一个控件
 
                view.setTag(viewHolder);// tag的用法一:存储数据
            }
 
            // logo
            viewHolder.ivHallLotteryLogo.setImageResource(LOGORESIDS[position]);
            // title
            viewHolder.tvHallLotteryTitle.setText(TITLERESIDS[position]);
 
            // 方案一:保存当前销售期信息到map
            //String info = data.get(position);
            //if (StringUtils.isNotBlank(info)) {
            //    viewHolder.tvHallLotterySummary.setText(info);
            //}
 
            viewHolder.ivHallLotteryBet.setOnClickListener(new OnClickListener() {
 
                @Override
                public void onClick(View v) {
                    switch (position) {
                            case 0:// 双色球
                                    // TODO: 双色球投注bet
 
                        break;
                        }
                    }
            });
            return view;
        }
    }
 
    /**
     * 初始化ListView
     */

    public void initListView(){
        // 1、showView
        showView = (ViewGroup) View.inflate(context, R.layout.zl_hall, null);
 
        // 2、listview初始化
        //categoryList = (ListView) showView.findViewById(R.id.lv_category_selector);
 
        // 由于ListView是加载到ViewPager中,所有不能findViewById了
        categoryList = new ListView(context);
 
        // 方案一:存储当前销售期信息(不变的内容也刷新,耗费资源,卡顿)
        // data = new HashMap<Integer, String>();
 
        // 方案二:保存要改变的TextView的引用(需要手动在ListView集合中维护一个List集合)
        // tvLotterySummary = new ArrayList<TextView>();
 
        // 3、adapter初始化
        lotteryAdapter = new LotteryAdapter();
 
        // 4、设置adapter
        categoryList.setAdapter(lotteryAdapter);
    }
 
    // ********************初始化购物大厅组件init()****************//
    /**
     * 1、初始化购物大厅组件
     */

    public void init() {
 
        // 初始化ListView
        initListView();
 
        // 初始化ViewPager
        initViewPager();
 
        // 初始化ViewPager中显示的内容
        initPagerViews();
 
        // 初始化图片的位置
        tabStripe();
 
        // 初始化TextView
        initTextView();

    }
 
    // ********************设置监听****************//
    private TextView tvCategoryFc;
    private TextView tvCategoryTc;
    private TextView tvCategoryGpc;
 
    public void initTextView() {
        tvCategoryFc = (TextView) this.findViewById(R.id.tv_category_fc_zl);
        tvCategoryTc = (TextView) this.findViewById(R.id.tv_category_tc_zl);
        tvCategoryGpc = (TextView) this.findViewById(R.id.tv_category_gpc_zl);
    }
 
    private int currentTab = 1;// 当前标题的位置
 
    @Override
    public void setListener() {
        // 设置ViewPager的监听事件,页面滑动切换事件
        vpViewPager.setOnPageChangeListener(new OnPageChangeListener() {
 
            // page被选择的时候
            @Override
            public void onPageSelected(int position) {
                // 下次切换的时候,重新设置颜色
                tvCategoryFc.setTextColor(Color.BLACK);
                tvCategoryTc.setTextColor(Color.BLACK);
                tvCategoryGpc.setTextColor(Color.BLACK);
                switch (position) {
                case 0:
                    tvCategoryFc.setTextColor(Color.RED);
                    break;
                case 1:
                    tvCategoryTc.setTextColor(Color.RED);
                    break;
                case 2:
                    tvCategoryGpc.setTextColor(Color.RED);
                    break;
                }
                float fromXDelta = currentTab*GlobalParams.WINDOW_WIDTH/titleCount;
                float toXDelta = position * GlobalParams.WINDOW_WIDTH/titleCount;
                Animation animation = new TranslateAnimation(fromXDelta, toXDelta, 0,0);
                animation.setFillAfter(true);
                animation.setDuration(300);
 
                ivSelector.startAnimation(animation);
 
                // 记住当前位置
                currentTab = position;
            }
 
            @Override
            public void onPageScrolled(int arg0, float arg1, int arg2) {
            }
 
            @Override
            public void onPageScrollStateChanged(int arg0) {
            }
        });
    }
    @Override
    public void onResume() {
        getCurrentIssueInfo();
    }
    @Override
    public int getViewId() {
        return ConstantValue.VIEW_HALL;
    }
 
    // **************************修改界面的提示信息****************************//
 
    /**
     * 修改界面的提示信息
     *
     * @param element
     */

    private void changeNotice(CurrentIssueElement element) {
 
        String info = context.getResources().getString(
                R.string.is_hall_common_summary);
 
        // 当前期次
        String issue = element.getIssue();
        // 剩余投注时间
        String lasttime = element.getLasttime();
 
        info = StringUtils.replaceEach(info, new String[] { "ISSUE", "TIME" },
                new String[] { issue, getLasttime(lasttime) });
 
        // 方案一:将从服务器获取到的数据存储到Map<Integer,String>
        // data中(存储当前销售期信息(不变的内容也刷新,耗费资源,卡顿))
        // 方案一问题:每次获取数据都会刷新一下listview的item,但有的东西不需要变化
        // data.put(0, info);
        // adapter.notifyDataSetChanged();// 让每一个listview的item刷新一下
 
        // 方案二:现在listview中需要改变的只有textview中的内容,阶段只需要更新TextView的显示内容,与item其他空间没有关系
        // 解决:创建一个集合在getView向集合添加TextView的引用
        // 方案二问题:ListView需要维护一个List集合
        // TextView tvSummery = tvLotterySummary.get(0);
        // tvSummery.setText(info);
 
        // 方案三:tag
        TextView tvSummery = (TextView) categoryList.findViewWithTag(0);// 将对应位置的组件取出来
        tvSummery.setText(info);
 
        // note:什么时候用notifyDataSetChanged(),什么时候用findViewWithTag()?
        // ①当ListView中需要进行增删item时候notifyDataSetChanged();
        // ②当需要更新Item中信息时候,一般使用优化的方式完成,
        // ③扩展:ListView懒加载,ListView滚动的时候不加载数据(不往item添加数据),在停下来的时候加载数据
 
    }
 
    // ********************************异步的从服务器上获取数据************************************//
    /**
     * 获取当前销售期信息(从服务器上获取最新数据)
     */

    public void getCurrentIssueInfo(){
 
        // 优化3:使用已有AsyncTask类进行数据的获取,将其丢到BaseView中
        new MyHttpAsyncTask<Integer>() {
 
            @Override
            protected Message doInBackground(Integer... params) {
 
                // 1、获取业务的对象(用工厂类来获取)
                CommonInfoEngine infoEngine = EngineFactory.getEngineImplInstance(CommonInfoEngine.class);
                // 2、执行相应的方法
                Message message = infoEngine.getCurrentIssueInfo(params[0]);
                return message;
            }
            @Override
            protected void onPostExecute(Message result) {
                super.onPostExecute(result);
                // 界面的展示
                if (result != null) {// 从服务器上获取的message不为null
                    Olement olement = result.getBody().getOlement();
                    if (0 == (olement.getErrorcode())) {// 服务器返回正确,为0
                        CurrentIssueElement element = (CurrentIssueElement) result.getBody().getElements().get(0);
                        changeNotice(element);
                    } else {// 服务器返回不正确
                        PromptManager.showToast(context, olement.getErrormsg());
                    }
                } else {// 没有拿到数据
                    PromptManager.showToast(context, "您好,服务器繁忙,请稍后再试!");
                }
            }
        }.executeProxy(ConstantValue.SSQ);
    }
 
    // ********************************将秒时间转换成日时分格式************************************//
    /**
     * 将秒时间转换成日时分格式
     *
     * @param lasttime
     * @return
     */

    public String getLasttime(String lasttime) {
        StringBuffer result = new StringBuffer();
        if (StringUtils.isNumericSpace(lasttime)) {
            int time = Integer.parseInt(lasttime);
            int day = time / (24 * 60 * 60);
            result.append(day).append("天");
            if (day > 0) {
                time = time - day * 24 * 60 * 60;
            }
            int hour = time / 3600;
            result.append(hour).append("时");
            if (hour > 0) {
                time = time - hour * 60 * 60;
            }
            int minute = time / 60;
            result.append(minute).append("分");
        }
        return result.toString();
    }
}