垂直的seekbar

看下效果:





1
package org.qianyukun.core.views; 2 import android.content.Context; 3 import android.graphics.Canvas; 4 import android.graphics.Rect; 5 import android.graphics.drawable.Drawable; 6 import android.util.AttributeSet; 7 import android.view.MotionEvent; 8 import android.view.View; 9 import android.view.ViewConfiguration; 10 import android.view.ViewGroup; 11 import android.view.ViewParent; 12 import android.widget.SeekBar; 13 14 public class VerticalSeekBar extends SeekBar 15 { 16 Drawable mThumb; 17 private boolean mIsDragging; 18 private float mTouchDownY; 19 private int mScaledTouchSlop; 20 private boolean isInScrollingContainer = false; 21 22 public boolean isInScrollingContainer() 23 { 24 return isInScrollingContainer; 25 } 26 27 public void setInScrollingContainer(boolean isInScrollingContainer) 28 { 29 this.isInScrollingContainer = isInScrollingContainer; 30 } 31 32 /** 33 * On touch, this offset plus the scaled value from the position of the 34 * touch will form the progress value. Usually 0. 35 */ 36 float mTouchProgressOffset; 37 38 public VerticalSeekBar(Context context, AttributeSet attrs, int defStyle) 39 { 40 super(context, attrs, defStyle); 41 mScaledTouchSlop = ViewConfiguration.get(context).getScaledTouchSlop(); 42 43 } 44 45 public VerticalSeekBar(Context context, AttributeSet attrs) 46 { 47 super(context, attrs); 48 } 49 50 public VerticalSeekBar(Context context) 51 { 52 super(context); 53 } 54 55 @Override 56 protected void onSizeChanged(int w, int h, int oldw, int oldh) 57 { 58 59 super.onSizeChanged(h, w, oldh, oldw); 60 61 } 62 63 @Override 64 protected synchronized void onMeasure(int widthMeasureSpec, 65 int heightMeasureSpec) 66 { 67 super.onMeasure(heightMeasureSpec, widthMeasureSpec); 68 setMeasuredDimension(getMeasuredHeight(), getMeasuredWidth()); 69 } 70 71 @Override 72 protected synchronized void onDraw(Canvas canvas) 73 { 74 canvas.rotate(90); 75 canvas.translate(0, -getWidth()); 76 super.onDraw(canvas); 77 } 78 79 @Override 80 public boolean onTouchEvent(MotionEvent event) 81 { 82 if (!isEnabled()) 83 { 84 return false; 85 } 86 87 switch (event.getAction()) 88 { 89 case MotionEvent.ACTION_DOWN: 90 if (isInScrollingContainer()) 91 { 92 mTouchDownY = event.getY(); 93 } 94 else 95 { 96 setPressed(true); 97 // System.out.println(event.getY()); 98 invalidate(); 99 onStartTrackingTouch(); 100 trackTouchEvent(event); 101 attemptClaimDrag(); 102 103 onSizeChanged(getWidth(), getHeight(), 0, 0); 104 } 105 break; 106 107 case MotionEvent.ACTION_MOVE: 108 if (mIsDragging) 109 { 110 trackTouchEvent(event); 111 } 112 else 113 { 114 final float y = event.getY(); 115 if (Math.abs(y - mTouchDownY) > mScaledTouchSlop) 116 { 117 System.out.println("mScaledTouchSlop "+mScaledTouchSlop); 118 setPressed(true); 119 invalidate(); 120 onStartTrackingTouch(); 121 trackTouchEvent(event); 122 attemptClaimDrag(); 123 } 124 } 125 onSizeChanged(getWidth(), getHeight(), 0, 0); 126 break; 127 128 case MotionEvent.ACTION_UP: 129 if (mIsDragging) 130 { 131 trackTouchEvent(event); 132 onStopTrackingTouch(); 133 setPressed(false); 134 } 135 else 136 { 137 // Touch up when we never crossed the touch slop threshold 138 // should 139 // be interpreted as a tap-seek to that location. 140 onStartTrackingTouch(); 141 trackTouchEvent(event); 142 onStopTrackingTouch(); 143 } 144 onSizeChanged(getWidth(), getHeight(), 0, 0); 145 // ProgressBar doesn't know to repaint the thumb drawable 146 // in its inactive state when the touch stops (because the 147 // value has not apparently changed) 148 invalidate(); 149 break; 150 } 151 return true; 152 153 } 154 155 private void trackTouchEvent(MotionEvent event) 156 { 157 final int height = getHeight(); 158 final int top = getPaddingTop(); 159 final int bottom = getPaddingBottom(); 160 final int available = height - top - bottom; 161 162 int y = (int) event.getY(); 163 164 float scale; 165 float progress = 0; 166 167 if (y > height - bottom) 168 { 169 scale = 1.0f; 170 } 171 else if (y < top) 172 { 173 scale = 0.0f; 174 } 175 else 176 { 177 scale = (float) (y - top) / (float) available; 178 progress = mTouchProgressOffset; 179 } 180 181 final int max = getMax(); 182 progress += scale * max; 183 184 setProgress((int) progress); 185 186 } 187 188 /** 189 * This is called when the user has started touching this widget. 190 */ 191 void onStartTrackingTouch() 192 { 193 mIsDragging = true; 194 } 195 196 /** 197 * This is called when the user either releases his touch or the touch is 198 * canceled. 199 */ 200 void onStopTrackingTouch() 201 { 202 mIsDragging = false; 203 } 204 205 private void attemptClaimDrag() 206 { 207 ViewParent p = getParent(); 208 if (p != null) 209 { 210 p.requestDisallowInterceptTouchEvent(true); 211 } 212 } 213 214 @Override 215 public synchronized void setProgress(int progress) 216 { 217 218 super.setProgress(progress); 219 onSizeChanged(getWidth(), getHeight(), 0, 0); 220 221 } 222 223 @Override 224 public void setThumb(Drawable thumb) { 225 super.setThumb(thumb); 226 mThumb = thumb; 227 } 228 public Drawable getSeekBarThumb() { 229 return mThumb; 230 } 231 232 }

 

最近在做PDF文档的浏览,文档右侧有一个垂直的透明的滑动块,来快速定位文档位置和显示当前页面的位置。

由于原生的seekbar是水平的,所以需要可自定义View了。虽然View的自定义这块,了解的不够深,但是够用了。

 

实现方式:继承SeekBar,在onDrow()中将画布旋转,然后平移到能够显示的位置。添加滑动事件。

 

1 mPageSlider = new VerticalSeekBar(context);
2         mPageSlider.setThumb(getResources().getDrawable(
3                 R.drawable.pdfseekbarthum));//添加thumb样式
4         mPageSlider.setProgressDrawable(getResources().getDrawable(
5                 R.drawable.seek_progress));//添加进度条样式
6         mPageSlider.setBackgroundResource(R.color.toolbar);
7         mPageSlider.setThumbOffset(0);//这句比较重要,使thumb显示完整

 

记录每一行代码,滴水穿石!

posted @ 2015-10-23 10:08  Alter  阅读(410)  评论(0编辑  收藏  举报