让fragmentTabhost这类固定的bar能够滑动起来

最近,做了个项目同事使用了FragmentTabhost来作为软件的底部的选择类似actionbar的功能,点击不同的按钮加载不同的fragment,但是老板希望能够让他能够滑动起来,原本想的很简单,准备直接加个scrollview来实现,实际做起来发现,scrollview 的Touchevent被拦截了无法获取,查了下资料顺便回顾了一下android的拦截机制,故决定从高层的分发入手自己实现一个类似scrollview的功能。

说一下思路吧,实现滚动的方式有很多,我选择了自己感觉比较简单的scrollBy来实现,同时移动的是在父容器中的位置,所以现在布局文件中在bottom位置留了个Linearlayout作为滑动的区域,由于需要重写高层容器的onInterceptTouchEvent方法,用来作为scrollview的linearlayout需要自己实例化,这时再重写onInterceptTouchEvent方法,在MotionEvent.ACTION_DOWN:中获得按下时的坐标,在获得move后的坐标得到offset量这样就能狗实现滑动的效果(注意在move最后要将startX和startY重新进行赋值),这时滑动便能够实现了。

但是,这时出现了一个问题,就是在滑动后,还是有点击按钮的事件触发,我们在滑动时并不需要将up分发下级view因此我们在得到offset大于3时判定此时在进行滑动,不将up分发出去。此时便已经能够实现滑动时不触发按钮的点击事件。

但是此时仍然觉得不是很完美,那就是view可以一直滑动到边界,最后甚至不能够在拉出来,于是便写定一个最多允许滑动的值,当滑动值超过allowOffsetlength时,只允许往左滑动,小于-allowOffsetlength时只允许往右滑动,其他时候,左右都可以滑动。

直接上代码:

LinearLayout container = (LinearLayout) view.findViewById(R.id.container);

		LinearLayout mContainer = new LinearLayout(this) {
			int startX = 0;
			int offsetX = 0;
			boolean isMove = false;
			int totalOffsetWidth = 0;//已滑动距离
			int allowOffsetlength ;//允许滑动的距离 

			@Override
			public boolean onInterceptTouchEvent(MotionEvent ev) {

				switch (ev.getAction()) {
				case MotionEvent.ACTION_DOWN:
					startX = (int) ev.getRawX();
					isMove = false;
					allowOffsetlength=getWidth() / 2;
				case MotionEvent.ACTION_MOVE:
					offsetX = (int) ev.getX() - startX;
					
				
					if(totalOffsetWidth>=allowOffsetlength){
						direction=LEFT;
					}else if(totalOffsetWidth<=-allowOffsetlength){
						direction=RIGHT;
					}else{
						direction= <span style="font-family: Arial, Helvetica, sans-serif;">ALL</span><span style="font-family: Arial, Helvetica, sans-serif;">;</span><span style="font-family: Arial, Helvetica, sans-serif;">;</span><span style="font-family: Arial, Helvetica, sans-serif;">
</span>					}
					
					switch(direction){
					case ALL:
						totalOffsetWidth += offsetX;
						scrollBy(-offsetX, 0);
						break;
					case LEFT:
						if(offsetX<0){
							totalOffsetWidth += offsetX;
							scrollBy(-offsetX, 0);
						}
						break;
					case RIGHT:
						if(offsetX>0){
							totalOffsetWidth += offsetX;
							scrollBy(-offsetX, 0);
						}
						break;
					}

					startX = (int) ev.getX();
					if (Math.abs(offsetX) > 3) {
						isMove = true;
					}
					break;

				case MotionEvent.ACTION_UP:
					if (isMove) {
						return true;
					}
				}
				return super.onInterceptTouchEvent(ev);
			}
		};

		mContainer.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT));

		mTabHost = new FragmentTabHost(this);
		mTabHost.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT));
		mTabHost.setup(this, getSupportFragmentManager(), R.id.realtabcontent);
		mTabHost.offsetLeftAndRight(200);

		//得到fragment的个数
		int count = fragmentArray.length;

		for (int i = 0; i < count; i++) {
			//为每一个Tab按钮设置图标、文字和内容
			TabSpec tabSpec = mTabHost.newTabSpec(mTextviewArray[i]).setIndicator(getTabItemView(i));

			//将Tab按钮添加进Tab选项卡中
			mTabHost.addTab(tabSpec, fragmentArray[i], null);
			//设置Tab按钮的背景
			//mTabHost.getTabWidget().getChildAt(i).setBackgroundResource(R.drawable.selector_tab_background);
		}

		container.addView(mContainer);
		mContainer.addView(mTabHost);

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值