Android自定義控件實(shí)現(xiàn)按鈕滾動(dòng)選擇效果
本文實(shí)例為大家分享了Android實(shí)現(xiàn)按鈕滾動(dòng)選擇效果的具體代碼,供大家參考,具體內(nèi)容如下
效果圖

代碼實(shí)現(xiàn)
package com.demo.ui.view;
import android.annotation.TargetApi;
import android.content.Context;
import android.os.Build;
import android.os.Handler;
import android.support.v4.content.ContextCompat;
import android.view.Gravity;
import android.view.MotionEvent;
import android.view.View;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.RelativeLayout;
import android.widget.TextView;
import com.demo.R;
import com.demo.factory.Axis;
import com.demo.utils.LogUtils;
import java.util.ArrayList;
import java.util.List;
public class AirTemperatureView extends RelativeLayout{
private Context context;
private TextView tv;
private TextView tv_middle;
// private TextView tv_middle_small;
private RelativeLayout Auto_layout;
private StringScrollPicker stringScrollPicker;
private List<CharSequence> newList;
private ImageView img;
private ImageView img_left;
private ImageView img_right;
private int mPosition;
private Handler handler = new Handler();
/**
* 延遲線程,看是否還有下一個(gè)字符輸入
*/
private Runnable delayRun = new Runnable() {
@Override
public void run() {
stringScrollPicker.setVisibility(INVISIBLE);
img.setBackgroundResource(R.drawable.air_temp_bg);
tv_middle.setText(newList.get(mPosition));
//tv.setText("電池剩余"+newList.get(mPosition)+"%提醒你");
tv_middle.setVisibility(VISIBLE);
img_right.setVisibility(VISIBLE);
img_left.setVisibility(VISIBLE);
if(mListener != null) {
mListener.setAirTemper(mPosition+18);
}
LogUtils.e("空調(diào)刷新===","溫度");
}
};
public AirTemperatureView(Context context){
super(context);
this.context = context;
init();
}
@TargetApi(Build.VERSION_CODES.M)
public void init(){
super.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT, Axis.scaleX(230)));
LinearLayout parent = new LinearLayout(context);
parent.setOrientation(LinearLayout.VERTICAL);
LayoutParams parent_Params = new LayoutParams(LayoutParams.MATCH_PARENT, Axis.scaleX(230));
super.addView(parent,parent_Params);
RelativeLayout tv_layout = new RelativeLayout(context);
LinearLayout.LayoutParams tv_layout_Params = new LinearLayout.LayoutParams(LayoutParams.MATCH_PARENT, Axis.scaleX(50));
parent.addView(tv_layout,tv_layout_Params);
tv = new TextView(context);
tv.setText("溫度");
tv.setTextSize(Axis.scaleTextSize(36));
tv.setTextColor(ContextCompat.getColor(context, R.color.white_70_color));//
LayoutParams tv_Params = new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
tv_Params.addRule(RelativeLayout.CENTER_IN_PARENT);
tv_layout.addView(tv,tv_Params);
/**
* 滑動(dòng)選擇器
*/
Auto_layout = new RelativeLayout(context);
LinearLayout.LayoutParams Auto_layout_Params = new LinearLayout.LayoutParams(LayoutParams.MATCH_PARENT, Axis.scaleX(150));
Auto_layout_Params.setMargins(0,Axis.scaleX(30),0,0);
parent.addView(Auto_layout,Auto_layout_Params);
img = new ImageView(context);
img.setId(R.id.EleRemindImage);
img.setBackgroundResource(R.drawable.air_temp_bg);
LayoutParams img_Params = new LayoutParams(Axis.scaleX(150), Axis.scaleX(150));
img_Params.addRule(RelativeLayout.CENTER_IN_PARENT);
Auto_layout.addView(img,img_Params);
img_left = new ImageView(context);
img_left.setBackgroundResource(R.drawable.battery_point);
LayoutParams img_left_Params = new LayoutParams(Axis.scaleX(14), Axis.scaleX(14));
img_left_Params.addRule(RelativeLayout.CENTER_VERTICAL);
img_left_Params.addRule(RelativeLayout.LEFT_OF,R.id.EleRemindImage);
img_left_Params.setMargins(0,0,Axis.scaleX(134),0);
Auto_layout.addView(img_left,img_left_Params);
img_right = new ImageView(context);
img_right.setBackgroundResource(R.drawable.battery_point);
LayoutParams img_right_Params = new LayoutParams(Axis.scaleX(14), Axis.scaleX(14));
img_right_Params.addRule(RelativeLayout.CENTER_VERTICAL);
img_right_Params.addRule(RelativeLayout.RIGHT_OF,R.id.EleRemindImage);
img_right_Params.setMargins(Axis.scaleX(134),0,0,0);
Auto_layout.addView(img_right,img_right_Params);
tv_middle = new TextView(context);
tv_middle.setTextSize(Axis.scaleTextSize(64));
tv_middle.setGravity(Gravity.CENTER);
tv_middle.setTextColor(0xFFFFFFFF);
LayoutParams tv_middle_Params = new LayoutParams(Axis.scaleX(150), Axis.scaleX(150));
tv_middle_Params.addRule(RelativeLayout.CENTER_IN_PARENT);
Auto_layout.addView(tv_middle,tv_middle_Params);
newList = new ArrayList<>();
newList.add("18");
newList.add("19");
newList.add("20");
newList.add("21");
newList.add("22");
newList.add("23");
newList.add("24");
newList.add("25");
newList.add("26");
newList.add("27");
newList.add("28");
newList.add("29");
newList.add("30");
newList.add("31");
newList.add("32");
tv_middle.setText(newList.get(0));
stringScrollPicker = new StringScrollPicker(context);
stringScrollPicker.setHorizontal(true);
stringScrollPicker.setVisibleItemCount(5);//可見5個(gè) 第3個(gè) (3-1)個(gè)位中間
stringScrollPicker.setCenterPosition(2);
stringScrollPicker.setIsCirculation(true);
stringScrollPicker.setCanTap(true);
stringScrollPicker.setDisallowInterceptTouch(true);
LayoutParams stringScrollPicker_Params = new LayoutParams(LayoutParams.MATCH_PARENT,Axis.scaleX(150));
Auto_layout.addView(stringScrollPicker,stringScrollPicker_Params);
stringScrollPicker.setData(newList);
stringScrollPicker.setOnSelectedListener(new ScrollPickerView.OnSelectedListener() {
@Override
public void onSelected(ScrollPickerView scrollPickerView, final int position) {
mPosition = position;
handler.postDelayed(delayRun, 1500);
}
});
stringScrollPicker.setOnSelectedListener(new StringScrollPicker.OnDataSelectedListener() {
@Override
public void DataSelected(CharSequence data) {
//tv.setText("電池剩余"+data+"%提醒你");
}
});
stringScrollPicker.setSelectedPosition(0,false);//中間Item位置
stringScrollPicker.setVisibility(INVISIBLE);
stringScrollPicker.setOnTouchListener(new OnTouchListener() {
@Override
public boolean onTouch(View v, MotionEvent event) {
switch (event.getAction()){
case MotionEvent.ACTION_DOWN:
img.setBackgroundResource(R.drawable.battery_btn_p);
if(delayRun!=null){
handler.removeCallbacks(delayRun);
}
break;
}
return false;
}
});
img.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
stringScrollPicker.setVisibility(VISIBLE);
tv_middle.setVisibility(INVISIBLE);
img_right.setVisibility(INVISIBLE);
img_left.setVisibility(INVISIBLE);
img.setBackgroundResource(R.drawable.battery_btn_p);
}
});
}
/**
* 風(fēng)速設(shè)置
* @param mPosition
*/
public void setAirTemperature(int mPosition){
/**
* 在設(shè)置的時(shí)候不刷新
*/
if(stringScrollPicker.getVisibility() == INVISIBLE){
if(mPosition > 32){
mPosition = 32;
}
stringScrollPicker.setSelectedPosition(mPosition-18,false);
tv_middle.setText(newList.get(mPosition-18));
}
}
public TemperatureListener mListener;
public void setOnTemperatureListener (TemperatureListener listener) {
mListener = listener;
}
public interface TemperatureListener {
void setAirTemper(int temperature);
}
}
StringScrollPicker 類
package com.demo.ui.view;
import android.annotation.TargetApi;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.os.Build;
import android.support.annotation.RequiresApi;
import android.text.Layout;
import android.text.StaticLayout;
import android.text.TextPaint;
import android.util.AttributeSet;
import android.util.Log;
import com.demo.factory.Axis;
import com.demo.utils.ColorUtil;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
public class StringScrollPicker extends ScrollPickerView<CharSequence> {
private int mMeasureWidth;
private int mMeasureHeight;
private TextPaint mPaint; //
private int mMinTextSize = Axis.scaleX(64); // 最小的字體
private int mMaxTextSize = Axis.scaleX(64); // 最大的字體
// 字體漸變顏色
private int mStartColor = Color.WHITE; // 中間選中item的顏色
private int mEndColor = Color.GRAY; // 上下兩邊的顏色
private int mMaxLineWidth = -1; // 最大的行寬,默認(rèn)為itemWidth.超過后文字自動(dòng)換行
private Layout.Alignment mAlignment = Layout.Alignment.ALIGN_CENTER; // 對(duì)齊方式,默認(rèn)居中
@TargetApi(Build.VERSION_CODES.CUPCAKE)
public StringScrollPicker(Context context) {
this(context, null);
}
@RequiresApi(api = Build.VERSION_CODES.CUPCAKE)
public StringScrollPicker(Context context, AttributeSet attrs) {
this(context, attrs, 0);
}
@RequiresApi(api = Build.VERSION_CODES.CUPCAKE)
public StringScrollPicker(Context context, AttributeSet attrs,
int defStyleAttr) {
super(context, attrs, defStyleAttr);
mPaint = new TextPaint(Paint.ANTI_ALIAS_FLAG);
mPaint.setStyle(Paint.Style.FILL);
mPaint.setColor(Color.BLACK);
setData(new ArrayList<CharSequence>(Arrays.asList(new String[]{
"one", "two", "three", "four", "five", "six", "seven", "eight", "nine", "ten", "eleven", "twelve"
})));
}
/**
* @param startColor 正中間的顏色
* @param endColor 上下兩邊的顏色
*/
public void setColor(int startColor, int endColor) {
mStartColor = startColor;
mEndColor = endColor;
invalidate();
}
/**
* item文字大小
*
* @param minText 沒有被選中時(shí)的最小文字
* @param maxText 被選中時(shí)的最大文字
*/
public void setTextSize(int minText, int maxText) {
mMinTextSize = minText;
mMaxTextSize = maxText;
invalidate();
}
public int getStartColor() {
return mStartColor;
}
public int getEndColor() {
return mEndColor;
}
public int getMinTextSize() {
return mMinTextSize;
}
public int getMaxTextSize() {
return mMaxTextSize;
}
public int getMaxLineWidth() {
return mMaxLineWidth;
}
/**
* 最大的行寬,默認(rèn)為itemWidth.超過后文字自動(dòng)換行
* @param maxLineWidth
*/
public void setMaxLineWidth(int maxLineWidth) {
mMaxLineWidth = maxLineWidth;
}
/**
* 最大的行寬,默認(rèn)為itemWidth.超過后文字自動(dòng)換行
* @return
*/
public Layout.Alignment getAlignment() {
return mAlignment;
}
public void setAlignment(Layout.Alignment alignment) {
mAlignment = alignment;
}
@Override
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
super.onSizeChanged(w, h, oldw, oldh);
mMeasureWidth = getMeasuredWidth();
mMeasureHeight = getMeasuredHeight();
if (mMaxLineWidth < 0) {
mMaxLineWidth = getItemWidth();
}
}
@Override
public void drawItem(Canvas canvas, List<CharSequence> data, int position, int relative, float moveLength, float top) {
CharSequence text = data.get(position);
int itemSize = getItemSize();
// 設(shè)置文字大小
if (relative == -1) { // 上一個(gè)
if (moveLength < 0) { // 向上滑動(dòng)
mPaint.setTextSize(mMinTextSize);
} else { // 向下滑動(dòng)
mPaint.setTextSize(mMinTextSize + (mMaxTextSize - mMinTextSize)
* moveLength / itemSize);
}
} else if (relative == 0) { // 中間item,當(dāng)前選中
mPaint.setTextSize(mMinTextSize + (mMaxTextSize - mMinTextSize)
* (itemSize - Math.abs(moveLength)) / itemSize);
} else if (relative == 1) { // 下一個(gè)
if (moveLength > 0) { // 向下滑動(dòng)
mPaint.setTextSize(mMinTextSize);
} else { // 向上滑動(dòng)
mPaint.setTextSize(mMinTextSize + (mMaxTextSize - mMinTextSize)
* -moveLength / itemSize);
}
} else { // 其他
mPaint.setTextSize(mMinTextSize);
}
StaticLayout layout = new StaticLayout(text, 0, text.length(), mPaint, mMaxLineWidth, mAlignment, 1.0F, 0.0F, true, null, 0);
float x = 0;
float y = 0;
float lineWidth = layout.getWidth();
if (isHorizontal()) { // 水平滾動(dòng)
x = top + (getItemWidth() - lineWidth) / 2;
y = (getItemHeight() - layout.getHeight()) / 2;
} else { // 垂直滾動(dòng)
x = (getItemWidth() - lineWidth) / 2;
y = top + (getItemHeight() - layout.getHeight()) / 2;
}
// 計(jì)算漸變顏色
computeColor(relative, itemSize, moveLength,text);
// canvas.drawText(text, x, y, mPaint);
canvas.save();
canvas.translate(x, y);
layout.draw(canvas);
canvas.restore();
}
/**
* 計(jì)算字體顏色,漸變
*
* @param relative 相對(duì)中間item的位置
*/
private String lastString;
private String nowSring;
private void computeColor(int relative, int itemSize, float moveLength, CharSequence text) {
int color = mEndColor; // 其他默認(rèn)為mEndColor
if (relative == -1 || relative == 1) { // 上一個(gè)或下一個(gè)
// 處理上一個(gè)item且向上滑動(dòng) 或者 處理下一個(gè)item且向下滑動(dòng) ,顏色為mEndColor
if ((relative == -1 && moveLength < 0)
|| (relative == 1 && moveLength > 0)) {
color = mEndColor;
} else { // 計(jì)算漸變的顏色
float rate = (itemSize - Math.abs(moveLength))
/ itemSize;
color = ColorUtil.computeGradientColor(mStartColor, mEndColor, rate);
}
} else if (relative == 0) { // 中間item
float rate = Math.abs(moveLength) / itemSize;
color = ColorUtil.computeGradientColor(mStartColor, mEndColor, rate);
nowSring = text.toString();
if(nowSring != lastString){
Log.e("text=====",text+"");
if(mListener != null){
mListener.DataSelected(text);
}
}
lastString = nowSring;
}
mPaint.setColor(color);
}
public interface OnDataSelectedListener {
void DataSelected(CharSequence data);
}
public void setOnSelectedListener(OnDataSelectedListener listener) {
mListener = listener;
}
public OnDataSelectedListener mListener;
}
ScrollPickerView 類
package com.demo.ui.view;
import android.animation.Animator;
import android.animation.AnimatorListenerAdapter;
import android.animation.ValueAnimator;
import android.annotation.TargetApi;
import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Canvas;
import android.graphics.Paint;
import android.graphics.drawable.ColorDrawable;
import android.graphics.drawable.Drawable;
import android.os.Build;
import android.support.annotation.RequiresApi;
import android.util.AttributeSet;
import android.util.DisplayMetrics;
import android.view.GestureDetector;
import android.view.MotionEvent;
import android.view.View;
import android.view.ViewParent;
import android.view.animation.Interpolator;
import android.widget.Scroller;
import com.demo.R;
import com.demo.utils.LogUtils;
import java.util.ArrayList;
import java.util.List;
/**
* 滾動(dòng)選擇器,帶慣性滑動(dòng)
*/
public abstract class ScrollPickerView<T> extends View {
private int mVisibleItemCount = 3; // 可見的item數(shù)量
private boolean mIsInertiaScroll = true; // 快速滑動(dòng)時(shí)是否慣性滾動(dòng)一段距離,默認(rèn)開啟
private boolean mIsCirculation = true; // 是否循環(huán)滾動(dòng),默認(rèn)開啟
/*
不允許父組件攔截觸摸事件,設(shè)置為true為不允許攔截,此時(shí)該設(shè)置才生效
當(dāng)嵌入到ScrollView等滾動(dòng)組件中,為了使該自定義滾動(dòng)選擇器可以正常工作,請(qǐng)?jiān)O(shè)置為true
*/
private boolean mDisallowInterceptTouch = false;
private int mSelected; // 當(dāng)前選中的item下標(biāo)
private int mLastSelected; // 當(dāng)前選中的item下標(biāo)
private List<T> mData;
private int mItemHeight = 0; // 每個(gè)條目的高度,當(dāng)垂直滾動(dòng)時(shí),高度=mMeasureHeight/mVisibleItemCount
private int mItemWidth = 0; // 每個(gè)條目的寬度,當(dāng)水平滾動(dòng)時(shí),寬度=mMeasureWidth/mVisibleItemCount
private int mItemSize; // 當(dāng)垂直滾動(dòng)時(shí),mItemSize = mItemHeight;水平滾動(dòng)時(shí),mItemSize = mItemWidth
private int mCenterPosition = -1; // 中間item的位置,0<=mCenterPosition<mVisibleItemCount,默認(rèn)為 mVisibleItemCount / 2
private int mCenterY; // 中間item的起始坐標(biāo)y(不考慮偏移),當(dāng)垂直滾動(dòng)時(shí),y= mCenterPosition*mItemHeight
private int mCenterX; // 中間item的起始坐標(biāo)x(不考慮偏移),當(dāng)垂直滾動(dòng)時(shí),x = mCenterPosition*mItemWidth
private int mCenterPoint; // 當(dāng)垂直滾動(dòng)時(shí),mCenterPoint = mCenterY;水平滾動(dòng)時(shí),mCenterPoint = mCenterX
private float mLastMoveY; // 觸摸的坐標(biāo)y
private float mLastMoveX; // 觸摸的坐標(biāo)X
private float mMoveLength = 0; // item移動(dòng)長(zhǎng)度,負(fù)數(shù)表示向上移動(dòng),正數(shù)表示向下移動(dòng)
private GestureDetector mGestureDetector;
private OnSelectedListener mListener;
private Scroller mScroller;
private boolean mIsFling; // 是否正在慣性滑動(dòng)
private boolean mIsMovingCenter; // 是否正在滑向中間
// 可以把scroller看做模擬的觸屏滑動(dòng)操作,mLastScrollY為上次觸屏滑動(dòng)的坐標(biāo)
private int mLastScrollY = 0; // Scroller的坐標(biāo)y
private int mLastScrollX = 0; // Scroller的坐標(biāo)x
private boolean mDisallowTouch = false; // 不允許觸摸
private Paint mPaint; //
private Drawable mCenterItemBackground = null; // 中間選中item的背景色
private boolean mCanTap = true; // 單擊切換選項(xiàng)或觸發(fā)點(diǎn)擊監(jiān)聽器
private boolean mIsHorizontal = false; // 是否水平滾動(dòng)
private boolean mDrawAllItem = false; // 是否繪制每個(gè)item(包括在邊界外的item)
@RequiresApi(api = Build.VERSION_CODES.CUPCAKE)
public ScrollPickerView(Context context, AttributeSet attrs) {
this(context, attrs, 0);
}
@TargetApi(Build.VERSION_CODES.HONEYCOMB)
@RequiresApi(api = Build.VERSION_CODES.CUPCAKE)
public ScrollPickerView(Context context, AttributeSet attrs,
int defStyleAttr) {
super(context, attrs, defStyleAttr);
mGestureDetector = new GestureDetector(getContext(),
new FlingOnGestureListener());
mScroller = new Scroller(getContext());
mAutoScrollAnimator = ValueAnimator.ofInt(0, 0);
mPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
mPaint.setStyle(Paint.Style.FILL);
init(attrs);
}
private void init(AttributeSet attrs) {
if (attrs != null) {
TypedArray typedArray = getContext().obtainStyledAttributes(attrs,
R.styleable.ScrollPickerView);
if (typedArray.hasValue(R.styleable.ScrollPickerView_spv_center_item_background)) {
setCenterItemBackground(typedArray.getDrawable(R.styleable.ScrollPickerView_spv_center_item_background));
}
setVisibleItemCount(typedArray.getInt(
R.styleable.ScrollPickerView_spv_visible_item_count,
getVisibleItemCount()));
setCenterPosition(typedArray.getInt(
R.styleable.ScrollPickerView_spv_center_item_position,
getCenterPosition()));
setIsCirculation(typedArray.getBoolean(R.styleable.ScrollPickerView_spv_is_circulation, isIsCirculation()));
setDisallowInterceptTouch(typedArray.getBoolean(R.styleable.ScrollPickerView_spv_disallow_intercept_touch, isDisallowInterceptTouch()));
setHorizontal(typedArray.getInt(R.styleable.ScrollPickerView_spv_orientation, mIsHorizontal ? 1 : 2) == 1);
typedArray.recycle();
}
}
@Override
protected void onDraw(Canvas canvas) {
if (mData == null || mData.size() <= 0) {
return;
}
// 選中item的背景色
if (mCenterItemBackground != null) {
mCenterItemBackground.draw(canvas);
}
// 只繪制可見的item
int length = Math.max(mCenterPosition + 1, mVisibleItemCount - mCenterPosition);
int position;
int start = Math.min(length, mData.size());
if (mDrawAllItem) {
start = mData.size();
}
// 上下兩邊
for (int i = start; i >= 1; i--) { // 先從遠(yuǎn)離中間位置的item繪制,當(dāng)item內(nèi)容偏大時(shí),較近的item覆蓋在較遠(yuǎn)的上面
if (mDrawAllItem || i <= mCenterPosition + 1) { // 上面的items,相對(duì)位置為 -i
position = mSelected - i < 0 ? mData.size() + mSelected - i
: mSelected - i;
// 傳入位置信息,繪制item
if (mIsCirculation) {
drawItem(canvas, mData, position, -i, mMoveLength, mCenterPoint + mMoveLength - i * mItemSize);
} else if (mSelected - i >= 0) { // 非循環(huán)滾動(dòng)
drawItem(canvas, mData, position, -i, mMoveLength, mCenterPoint + mMoveLength - i * mItemSize);
}
}
if (mDrawAllItem || i <= mVisibleItemCount - mCenterPosition) { // 下面的items,相對(duì)位置為 i
position = mSelected + i >= mData.size() ? mSelected + i
- mData.size() : mSelected + i;
// 傳入位置信息,繪制item
if (mIsCirculation) {
drawItem(canvas, mData, position, i, mMoveLength, mCenterPoint + mMoveLength + i * mItemSize);
} else if (mSelected + i < mData.size()) { // 非循環(huán)滾動(dòng)
drawItem(canvas, mData, position, i, mMoveLength, mCenterPoint + mMoveLength + i * mItemSize);
}
}
}
// 選中的item
drawItem(canvas, mData, mSelected, 0, mMoveLength, mCenterPoint + mMoveLength);
}
/**
* 繪制item
*
* @param canvas
* @param data 數(shù)據(jù)集
* @param position 在data數(shù)據(jù)集中的位置
* @param relative 相對(duì)中間item的位置,relative==0表示中間item,relative<0表示上(左)邊的item,relative>0表示下(右)邊的item
* @param moveLength 中間item滾動(dòng)的距離,moveLength<0則表示向上(右)滾動(dòng)的距離,moveLength>0則表示向下(左)滾動(dòng)的距離
* @param top 當(dāng)前繪制item的坐標(biāo),當(dāng)垂直滾動(dòng)時(shí)為頂部y的坐標(biāo);當(dāng)水平滾動(dòng)時(shí)為item最左邊x的坐標(biāo)
*/
public abstract void drawItem(Canvas canvas, List<T> data, int position, int relative, float moveLength, float top);
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
super.onMeasure(widthMeasureSpec, heightMeasureSpec);
}
@Override
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
super.onSizeChanged(w, h, oldw, oldh);
reset();
}
private void reset() {
if (mCenterPosition < 0) {
mCenterPosition = mVisibleItemCount / 2;
}
if (mIsHorizontal) {
mItemHeight = getMeasuredHeight();
mItemWidth = getMeasuredWidth() / mVisibleItemCount;
mCenterY = 0;
mCenterX = mCenterPosition * mItemWidth;
mItemSize = mItemWidth;
mCenterPoint = mCenterX;
} else {
mItemHeight = getMeasuredHeight() / mVisibleItemCount;
mItemWidth = getMeasuredWidth();
mCenterY = mCenterPosition * mItemHeight;
mCenterX = 0;
mItemSize = mItemHeight;
mCenterPoint = mCenterY;
}
if (mCenterItemBackground != null) {
mCenterItemBackground.setBounds(mCenterX, mCenterY, mCenterX + mItemWidth, mCenterY + mItemHeight);
}
}
@RequiresApi(api = Build.VERSION_CODES.FROYO)
@Override
public boolean onTouchEvent(MotionEvent event) {
if (mDisallowTouch) { // 不允許觸摸
return true;
}
if (mGestureDetector.onTouchEvent(event)) {
return true;
}
switch (event.getActionMasked()) {
case MotionEvent.ACTION_MOVE:
if (mIsHorizontal) {
if (Math.abs(event.getX() - mLastMoveX) < 0.1f) {
return true;
}
mMoveLength += event.getX() - mLastMoveX;
} else {
if (Math.abs(event.getY() - mLastMoveY) < 0.1f) {
return true;
}
mMoveLength += event.getY() - mLastMoveY;
}
mLastMoveY = event.getY();
mLastMoveX = event.getX();
checkCirculation();
invalidate();
break;
case MotionEvent.ACTION_UP:
mLastMoveY = event.getY();
mLastMoveX = event.getX();
moveToCenter();
break;
}
return true;
}
/**
* @param curr
* @param end
*/
private void computeScroll(int curr, int end, float rate) {
if (rate < 1) { // 正在滾動(dòng)
if (mIsHorizontal) {
// 可以把scroller看做模擬的觸屏滑動(dòng)操作,mLastScrollX為上次滑動(dòng)的坐標(biāo)
mMoveLength = mMoveLength + curr - mLastScrollX;
mLastScrollX = curr;
} else {
// 可以把scroller看做模擬的觸屏滑動(dòng)操作,mLastScrollY為上次滑動(dòng)的坐標(biāo)
mMoveLength = mMoveLength + curr - mLastScrollY;
mLastScrollY = curr;
}
checkCirculation();
invalidate();
} else { // 滾動(dòng)完畢
mIsMovingCenter = false;
mLastScrollY = 0;
mLastScrollX = 0;
// 直接居中,不通過動(dòng)畫
if (mMoveLength > 0) { //// 向下滑動(dòng)
if (mMoveLength < mItemSize / 2) {
mMoveLength = 0;
} else {
mMoveLength = mItemSize;
}
} else {
if (-mMoveLength < mItemSize / 2) {
mMoveLength = 0;
} else {
mMoveLength = -mItemSize;
}
}
checkCirculation();
mMoveLength = 0;
mLastScrollY = 0;
mLastScrollX = 0;
notifySelected(true);
invalidate();
}
}
@Override
public void computeScroll() {
if (mScroller.computeScrollOffset()) { // 正在滾動(dòng)
if (mIsHorizontal) {
// 可以把scroller看做模擬的觸屏滑動(dòng)操作,mLastScrollX為上次滑動(dòng)的坐標(biāo)
mMoveLength = mMoveLength + mScroller.getCurrX() - mLastScrollX;
} else {
// 可以把scroller看做模擬的觸屏滑動(dòng)操作,mLastScrollY為上次滑動(dòng)的坐標(biāo)
mMoveLength = mMoveLength + mScroller.getCurrY() - mLastScrollY;
}
mLastScrollY = mScroller.getCurrY();
mLastScrollX = mScroller.getCurrX();
checkCirculation(); // 檢測(cè)當(dāng)前選中的item
invalidate();
} else { // 滾動(dòng)完畢
if (mIsFling) {
mIsFling = false;
moveToCenter(); // 滾動(dòng)到中間位置
} else if (mIsMovingCenter) { // 選擇完成,回調(diào)給監(jiān)聽器
mMoveLength = 0;
mIsMovingCenter = false;
mLastScrollY = 0;
mLastScrollX = 0;
notifySelected(true);
}
}
}
public void cancelScroll() {
mLastScrollY = 0;
mLastScrollX = 0;
mIsFling = mIsMovingCenter = false;
mScroller.abortAnimation();
stopAutoScroll();
}
// 檢測(cè)當(dāng)前選擇的item位置
private void checkCirculation() {
if (mMoveLength >= mItemSize) { // 向下滑動(dòng)
// 該次滾動(dòng)距離中越過的item數(shù)量
int span = (int) (mMoveLength / mItemSize);
mSelected -= span;
if (mSelected < 0) { // 滾動(dòng)頂部,判斷是否循環(huán)滾動(dòng)
if (mIsCirculation) {
do {
mSelected = mData.size() + mSelected;
} while (mSelected < 0); // 當(dāng)越過的item數(shù)量超過一圈時(shí)
mMoveLength = (mMoveLength - mItemSize) % mItemSize;
} else { // 非循環(huán)滾動(dòng)
mSelected = 0;
mMoveLength = mItemSize;
if (mIsFling) { // 停止慣性滑動(dòng),根據(jù)computeScroll()中的邏輯,下一步將調(diào)用moveToCenter()
mScroller.forceFinished(true);
}
if (mIsMovingCenter) { // 移回中間位置
scroll(mMoveLength, 0);
}
}
} else {
mMoveLength = (mMoveLength - mItemSize) % mItemSize;
}
} else if (mMoveLength <= -mItemSize) { // 向上滑動(dòng)
// 該次滾動(dòng)距離中越過的item數(shù)量
int span = (int) (-mMoveLength / mItemSize);
mSelected += span;
if (mSelected >= mData.size()) { // 滾動(dòng)末尾,判斷是否循環(huán)滾動(dòng)
if (mIsCirculation) {
do {
mSelected = mSelected - mData.size();
} while (mSelected >= mData.size()); // 當(dāng)越過的item數(shù)量超過一圈時(shí)
mMoveLength = (mMoveLength + mItemSize) % mItemSize;
} else { // 非循環(huán)滾動(dòng)
mSelected = mData.size() - 1;
mMoveLength = -mItemSize;
if (mIsFling) { // 停止慣性滑動(dòng),根據(jù)computeScroll()中的邏輯,下一步將調(diào)用moveToCenter()
mScroller.forceFinished(true);
}
if (mIsMovingCenter) { // 移回中間位置
scroll(mMoveLength, 0);
}
}
} else {
mMoveLength = (mMoveLength + mItemSize) % mItemSize;
}
}
}
// 移動(dòng)到中間位置
private void moveToCenter() {
if (!mScroller.isFinished() || mIsFling || mMoveLength == 0) {
return;
}
cancelScroll();
// 向下滑動(dòng)
if (mMoveLength > 0) {
if (mIsHorizontal) {
if (mMoveLength < mItemWidth / 2) {
scroll(mMoveLength, 0);
} else {
scroll(mMoveLength, mItemWidth);
}
} else {
if (mMoveLength < mItemHeight / 2) {
scroll(mMoveLength, 0);
} else {
scroll(mMoveLength, mItemHeight);
}
}
} else {
if (mIsHorizontal) {
if (-mMoveLength < mItemWidth / 2) {
scroll(mMoveLength, 0);
} else {
scroll(mMoveLength, -mItemWidth);
}
} else {
if (-mMoveLength < mItemHeight / 2) {
scroll(mMoveLength, 0);
} else {
scroll(mMoveLength, -mItemHeight);
}
}
}
}
// 平滑滾動(dòng)
private void scroll(float from, int to) {
if (mIsHorizontal) {
mLastScrollX = (int) from;
mIsMovingCenter = true;
mScroller.startScroll((int) from, 0, 0, 0);
mScroller.setFinalX(to);
} else {
mLastScrollY = (int) from;
mIsMovingCenter = true;
mScroller.startScroll(0, (int) from, 0, 0);
mScroller.setFinalY(to);
}
invalidate();
}
// 慣性滑動(dòng),
private void fling(float from, float vel) {
if (mIsHorizontal) {
mLastScrollX = (int) from;
mIsFling = true;
// 最多可以慣性滑動(dòng)10個(gè)item
mScroller.fling((int) from, 0, (int) vel, 0, -10 * mItemWidth,
10 * mItemWidth, 0, 0);
} else {
mLastScrollY = (int) from;
mIsFling = true;
// 最多可以慣性滑動(dòng)10個(gè)item
mScroller.fling(0, (int) from, 0, (int) vel, 0, 0, -10 * mItemHeight,
10 * mItemHeight);
}
invalidate();
}
private void notifySelected(final boolean trigger) {
if (mListener != null) {
// 告訴監(jiān)聽器選擇完畢
post(new Runnable() {
@Override
public void run() {
if(mLastSelected != mSelected){
if(trigger){
mListener.onSelected(ScrollPickerView.this, mSelected);
}
}
mLastSelected = mSelected;
}
});
}
}
private boolean mIsAutoScrolling = false;
private ValueAnimator mAutoScrollAnimator;
private final static SlotInterpolator sAutoScrollInterpolator = new SlotInterpolator();
/**
* 自動(dòng)滾動(dòng)(必須設(shè)置為可循環(huán)滾動(dòng))
*
* @param position
* @param duration
* @param speed 每毫秒移動(dòng)的像素點(diǎn)
*/
@RequiresApi(api = Build.VERSION_CODES.HONEYCOMB)
public void autoScrollFast(final int position, long duration, float speed, final Interpolator interpolator) {
if (mIsAutoScrolling || !mIsCirculation) {
return;
}
cancelScroll();
mIsAutoScrolling = true;
int length = (int) (speed * duration);
int circle = (int) (length * 1f / (mData.size() * mItemSize) + 0.5f); // 圈數(shù)
circle = circle <= 0 ? 1 : circle;
int aPlan = circle * (mData.size()) * mItemSize + (mSelected - position) * mItemSize;
int bPlan = aPlan + (mData.size()) * mItemSize; // 多一圈
// 讓其盡量接近length
final int end = Math.abs(length - aPlan) < Math.abs(length - bPlan) ? aPlan : bPlan;
mAutoScrollAnimator.cancel();
mAutoScrollAnimator.setIntValues(0, end);
mAutoScrollAnimator.setInterpolator(interpolator);
mAutoScrollAnimator.setDuration(duration);
mAutoScrollAnimator.removeAllUpdateListeners();
if (end != 0) { // itemHeight為0導(dǎo)致endy=0
mAutoScrollAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
@Override
public void onAnimationUpdate(ValueAnimator animation) {
float rate = 0;
rate = animation.getCurrentPlayTime() * 1f / animation.getDuration();
computeScroll((int) animation.getAnimatedValue(), end, rate);
}
});
mAutoScrollAnimator.removeAllListeners();
mAutoScrollAnimator.addListener(new AnimatorListenerAdapter() {
@Override
public void onAnimationEnd(Animator animation) {
super.onAnimationEnd(animation);
mIsAutoScrolling = false;
}
});
mAutoScrollAnimator.start();
} else {
computeScroll(end, end, 1);
mIsAutoScrolling = false;
}
}
/**
* 自動(dòng)滾動(dòng),默認(rèn)速度為 0.6dp/ms
*
* @see ScrollPickerView#autoScrollFast(int, long, float, Interpolator)
*/
@RequiresApi(api = Build.VERSION_CODES.HONEYCOMB)
public void autoScrollFast(final int position, long duration) {
float speed = dip2px(0.6f);
autoScrollFast(position, duration, speed, sAutoScrollInterpolator);
}
/**
* 自動(dòng)滾動(dòng)
*
* @see ScrollPickerView#autoScrollFast(int, long, float, Interpolator)
*/
@RequiresApi(api = Build.VERSION_CODES.HONEYCOMB)
public void autoScrollFast(final int position, long duration, float speed) {
autoScrollFast(position, duration, speed, sAutoScrollInterpolator);
}
/**
* 滾動(dòng)到指定位置
*
* @param toPosition 需要滾動(dòng)到的位置
* @param duration 滾動(dòng)時(shí)間
* @param interpolator
*/
@RequiresApi(api = Build.VERSION_CODES.HONEYCOMB)
public void autoScrollToPosition(int toPosition, long duration, final Interpolator interpolator) {
toPosition = toPosition % mData.size();
final int endY = (mSelected - toPosition) * mItemHeight;
autoScrollTo(endY, duration, interpolator, false);
}
/**
* @param endY 需要滾動(dòng)到的位置
* @param duration 滾動(dòng)時(shí)間
* @param interpolator
* @param canIntercept 能否終止?jié)L動(dòng),比如觸摸屏幕終止?jié)L動(dòng)
*/
@RequiresApi(api = Build.VERSION_CODES.HONEYCOMB)
public void autoScrollTo(final int endY, long duration, final Interpolator interpolator, boolean canIntercept) {
if (mIsAutoScrolling) {
return;
}
final boolean temp = mDisallowTouch;
mDisallowTouch = !canIntercept;
mIsAutoScrolling = true;
mAutoScrollAnimator.cancel();
mAutoScrollAnimator.setIntValues(0, endY);
mAutoScrollAnimator.setInterpolator(interpolator);
mAutoScrollAnimator.setDuration(duration);
mAutoScrollAnimator.removeAllUpdateListeners();
mAutoScrollAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
@Override
public void onAnimationUpdate(ValueAnimator animation) {
float rate = 0;
rate = animation.getCurrentPlayTime() * 1f / animation.getDuration();
computeScroll((int) animation.getAnimatedValue(), endY, rate);
}
});
mAutoScrollAnimator.removeAllListeners();
mAutoScrollAnimator.addListener(new AnimatorListenerAdapter() {
@Override
public void onAnimationEnd(Animator animation) {
super.onAnimationEnd(animation);
mIsAutoScrolling = false;
mDisallowTouch = temp;
}
});
mAutoScrollAnimator.start();
}
/**
* 停止自動(dòng)滾動(dòng)
*/
@TargetApi(Build.VERSION_CODES.HONEYCOMB)
public void stopAutoScroll() {
mIsAutoScrolling = false;
mAutoScrollAnimator.cancel();
}
private static class SlotInterpolator implements Interpolator {
@Override
public float getInterpolation(float input) {
return (float) (Math.cos((input + 1) * Math.PI) / 2.0f) + 0.5f;
}
}
/**
* 快速滑動(dòng)時(shí),慣性滑動(dòng)一段距離
*
* @author huangziwei
*/
private class FlingOnGestureListener extends GestureDetector.SimpleOnGestureListener {
private boolean mIsScrollingLastTime = false;
public boolean onDown(MotionEvent e) {
if (mDisallowInterceptTouch) { // 不允許父組件攔截事件
ViewParent parent = getParent();
if (parent != null) {
parent.requestDisallowInterceptTouchEvent(true);
}
}
mIsScrollingLastTime = isScrolling(); // 記錄是否從滾動(dòng)狀態(tài)終止
// 點(diǎn)擊時(shí)取消所有滾動(dòng)效果
cancelScroll();
mLastMoveY = e.getY();
mLastMoveX = e.getX();
return true;
}
@Override
public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX,
final float velocityY) {
// 慣性滑動(dòng)
if (mIsInertiaScroll) {
cancelScroll();
if (mIsHorizontal) {
fling(mMoveLength, velocityX);
} else {
fling(mMoveLength, velocityY);
}
}
return true;
}
@RequiresApi(api = Build.VERSION_CODES.HONEYCOMB)
@Override
public boolean onSingleTapUp(MotionEvent e) {
mLastMoveY = e.getY();
mLastMoveX = e.getX();
float lastMove = 0;
if (isHorizontal()) {
mCenterPoint = mCenterX;
lastMove = mLastMoveX;
LogUtils.e("lastMove===",lastMove+"");
LogUtils.e("mCenterPoint===",mCenterPoint+"");
} else {
mCenterPoint = mCenterY;
lastMove = mLastMoveY;
}
if (mCanTap && !isScrolling() && !mIsScrollingLastTime) {
if (lastMove >= mCenterPoint && lastMove <= mCenterPoint + mItemSize) {
//performClick();
} else if (lastMove < mCenterPoint) {
int bs = (int)((mCenterPoint+mItemSize) - lastMove)/mItemSize;
int move = bs*mItemSize;
autoScrollTo(move, 150, sAutoScrollInterpolator, false);
} else if (lastMove > mCenterPoint + mItemSize) {
int bs = (int)((lastMove -mCenterPoint)/mItemWidth);
int move = -bs*mItemSize;
autoScrollTo(move, 150, sAutoScrollInterpolator, false);
} else {
moveToCenter();
}
} else {
moveToCenter();
}
return true;
}
}
public List<T> getData() {
return mData;
}
public void setData(List<T> data) {
if (data == null) {
mData = new ArrayList<T>();
} else {
this.mData = data;
}
mSelected = mData.size() / 2;
invalidate();
}
public T getSelectedItem() {
return mData.get(mSelected);
}
public int getSelectedPosition() {
return mSelected;
}
public void setSelectedPosition(int position,boolean trigger) {
if (position < 0 || position > mData.size() - 1
|| position == mSelected) {
return;
}
mSelected = position;
invalidate();
if (mListener != null) {
notifySelected(trigger);
}
}
public void setOnSelectedListener(OnSelectedListener listener) {
mListener = listener;
}
public OnSelectedListener getListener() {
return mListener;
}
public boolean isInertiaScroll() {
return mIsInertiaScroll;
}
public void setInertiaScroll(boolean inertiaScroll) {
this.mIsInertiaScroll = inertiaScroll;
}
public boolean isIsCirculation() {
return mIsCirculation;
}
public void setIsCirculation(boolean isCirculation) {
this.mIsCirculation = false;
}
public boolean isDisallowInterceptTouch() {
return mDisallowInterceptTouch;
}
public int getVisibleItemCount() {
return mVisibleItemCount;
}
public void setVisibleItemCount(int visibleItemCount) {
mVisibleItemCount = visibleItemCount;
reset();
invalidate();
}
/**
* 是否允許父元素?cái)r截事件,設(shè)置true后可以保證在ScrollView下正常滾動(dòng)
*/
public void setDisallowInterceptTouch(boolean disallowInterceptTouch) {
mDisallowInterceptTouch = disallowInterceptTouch;
}
public int getItemHeight() {
return mItemHeight;
}
public int getItemWidth() {
return mItemWidth;
}
/**
* @return 當(dāng)垂直滾動(dòng)時(shí),mItemSize = mItemHeight;水平滾動(dòng)時(shí),mItemSize = mItemWidth
*/
public int getItemSize() {
return mItemSize;
}
/**
* @return 中間item的起始坐標(biāo)x(不考慮偏移), 當(dāng)垂直滾動(dòng)時(shí),x = mCenterPosition*mItemWidth
*/
public int getCenterX() {
return mCenterX;
}
/**
* @return 中間item的起始坐標(biāo)y(不考慮偏移), 當(dāng)垂直滾動(dòng)時(shí),y= mCenterPosition*mItemHeight
*/
public int getCenterY() {
return mCenterY;
}
/**
* @return 當(dāng)垂直滾動(dòng)時(shí),mCenterPoint = mCenterY;水平滾動(dòng)時(shí),mCenterPoint = mCenterX
*/
public int getCenterPoint() {
return mCenterPoint;
}
public boolean isDisallowTouch() {
return mDisallowTouch;
}
/**
* 設(shè)置是否允許手動(dòng)觸摸滾動(dòng)
*
* @param disallowTouch
*/
public void setDisallowTouch(boolean disallowTouch) {
mDisallowTouch = disallowTouch;
}
/**
* 中間item的位置,0 <= centerPosition <= mVisibleItemCount
*
* @param centerPosition
*/
public void setCenterPosition(int centerPosition) {
if (centerPosition < 0) {
mCenterPosition = 0;
} else if (centerPosition >= mVisibleItemCount) {
mCenterPosition = mVisibleItemCount - 1;
} else {
mCenterPosition = centerPosition;
}
mCenterY = mCenterPosition * mItemHeight;
invalidate();
}
/**
* 中間item的位置,默認(rèn)為 mVisibleItemCount / 2
*
* @return
*/
public int getCenterPosition() {
return mCenterPosition;
}
public void setCenterItemBackground(Drawable centerItemBackground) {
mCenterItemBackground = centerItemBackground;
mCenterItemBackground.setBounds(mCenterX, mCenterY, mCenterX + mItemWidth, mCenterY + mItemHeight);
invalidate();
}
public void setCenterItemBackground(int centerItemBackgroundColor) {
mCenterItemBackground = new ColorDrawable(centerItemBackgroundColor);
mCenterItemBackground.setBounds(mCenterX, mCenterY, mCenterX + mItemWidth, mCenterY + mItemHeight);
invalidate();
}
public Drawable getCenterItemBackground() {
return mCenterItemBackground;
}
public boolean isScrolling() {
return mIsFling || mIsMovingCenter || mIsAutoScrolling;
}
public boolean isFling() {
return mIsFling;
}
public boolean isMovingCenter() {
return mIsMovingCenter;
}
public boolean isAutoScrolling() {
return mIsAutoScrolling;
}
public boolean isCanTap() {
return mCanTap;
}
/**
* 設(shè)置 單擊切換選項(xiàng)或觸發(fā)點(diǎn)擊監(jiān)聽器
*
* @param canTap
*/
public void setCanTap(boolean canTap) {
mCanTap = canTap;
}
public boolean isHorizontal() {
return mIsHorizontal;
}
public boolean isVertical() {
return !mIsHorizontal;
}
public void setHorizontal(boolean horizontal) {
if (mIsHorizontal == horizontal) {
return;
}
mIsHorizontal = horizontal;
reset();
if (mIsHorizontal) {
mItemSize = mItemWidth;
} else {
mItemSize = mItemHeight;
}
invalidate();
}
public void setVertical(boolean vertical) {
if (mIsHorizontal == !vertical) {
return;
}
mIsHorizontal = !vertical;
reset();
if (mIsHorizontal) {
mItemSize = mItemWidth;
} else {
mItemSize = mItemHeight;
}
invalidate();
}
public boolean isDrawAllItem() {
return mDrawAllItem;
}
public void setDrawAllItem(boolean drawAllItem) {
mDrawAllItem = drawAllItem;
}
/**
* @author huangziwei
*/
public interface OnSelectedListener {
void onSelected(ScrollPickerView scrollPickerView, int position);
}
public int dip2px(float dipVlue) {
DisplayMetrics metrics = getContext().getResources().getDisplayMetrics();
float sDensity = metrics.density;
return (int) (dipVlue * sDensity + 0.5F);
}
@Override
public void setVisibility(int visibility) {
super.setVisibility(visibility);
if (visibility == VISIBLE) {
moveToCenter();
}
}
}
ColorUtil 類
package com.demo.utils;
import android.graphics.Color;
/**
* 顏色工具欄
*/
public class ColorUtil {
/**
* 計(jì)算漸變后的顏色
*
* @param startColor 開始顏色
* @param endColor 結(jié)束顏色
* @param rate 漸變率(0,1)
* @return 漸變后的顏色,當(dāng)rate=0時(shí),返回startColor,當(dāng)rate=1時(shí)返回endColor
*/
public static int computeGradientColor(int startColor, int endColor, float rate) {
if (rate < 0) {
rate = 0;
}
if (rate > 1) {
rate = 1;
}
int alpha = Color.alpha(endColor) - Color.alpha(startColor);
int red = Color.red(endColor) - Color.red(startColor);
int green = Color.green(endColor) - Color.green(startColor);
int blue = Color.blue(endColor) - Color.blue(startColor);
return Color.argb(
Math.round(Color.alpha(startColor) + alpha * rate),
Math.round(Color.red(startColor) + red * rate),
Math.round(Color.green(startColor) + green * rate),
Math.round(Color.blue(startColor) + blue * rate));
}
}
調(diào)用
/**
* 溫度
*/
airTemperatureView = new AirTemperatureView(context);
LinearLayout.LayoutParams airTemperatureView_Params = new LinearLayout.LayoutParams(RelativeLayout.LayoutParams.MATCH_PARENT,Axis.scaleX(230));
airTemperatureView_Params.setMargins(0,Axis.scaleX(100),0,0);
bodyLayout.addView(airTemperatureView,airTemperatureView_Params);//父布局 addView()
airTemperatureView.setOnTemperatureListener(new AirTemperatureView.TemperatureListener() {
@Override
public void setAirTemper(int temperature) {
LogUtils.e("空調(diào)溫度===",temperature+"");
setTemperature(temperature);//網(wǎng)絡(luò)請(qǐng)求方法
}
});
以上就是本文的全部?jī)?nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
相關(guān)文章
Android操作存放在assets文件夾下SQLite數(shù)據(jù)庫的方法
這篇文章主要介紹了Android操作存放在assets文件夾下SQLite數(shù)據(jù)庫的方法,實(shí)例分析了Android操作SQLite數(shù)據(jù)庫的相關(guān)技巧,需要的朋友可以參考下2015-06-06
Android實(shí)現(xiàn)隨機(jī)圓形云標(biāo)簽效果
這篇文章主要為大家詳細(xì)介紹了Android實(shí)現(xiàn)隨機(jī)圓形云標(biāo)簽效果,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2018-05-05
Android 按后退鍵退出Android程序的實(shí)現(xiàn)方法
本篇文章介紹了,在Android中按后退鍵退出Android程序的實(shí)現(xiàn)方法。需要的朋友參考下2013-04-04
android實(shí)現(xiàn)關(guān)閉或開啟移動(dòng)網(wǎng)絡(luò)數(shù)據(jù)
本篇文章是對(duì)android實(shí)現(xiàn)關(guān)閉或開啟移動(dòng)網(wǎng)絡(luò)數(shù)據(jù)進(jìn)行了詳細(xì)的分析介紹,需要的朋友參考下2013-06-06
Android 自定義Switch開關(guān)按鈕的樣式實(shí)例詳解
本文主要講的是在Android原生Switch控件的基礎(chǔ)上進(jìn)行樣式自定義,內(nèi)容很簡(jiǎn)單,但是在實(shí)現(xiàn)的過程中還是遇到了一些問題,在此記錄下來,需要的朋友參考下吧2017-12-12
Android游戲開發(fā) 自定義手勢(shì)--輸入法手勢(shì)技術(shù)
本文主要介紹 Android游戲開發(fā)中自定義手勢(shì)--輸入法手勢(shì)技術(shù),這里提供了實(shí)現(xiàn)效果圖以及示例代碼,有開發(fā)手機(jī)游戲的朋友可以參考下2016-08-08
Android實(shí)現(xiàn)進(jìn)度條(ProgressBar)的功能與用法
這篇文章主要為大家詳細(xì)介紹了Android實(shí)現(xiàn)進(jìn)度條(ProgressBar)的功能與用法,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2020-08-08
Android設(shè)備上非root的抓包實(shí)現(xiàn)方法(Tcpdump方法)
通常我們?cè)贏ndroid應(yīng)用中執(zhí)行某個(gè)命令時(shí)會(huì)使用“Runtime.getRuntime().exec("命令路徑")”這種方式,但是當(dāng)我們執(zhí)行抓包操作時(shí),使用這條命令無論如何都不行,通過下面代碼打印結(jié)果發(fā)現(xiàn),該命令一定要在root權(quán)限下才能執(zhí)行,具體實(shí)現(xiàn)思路,請(qǐng)參考本教程2016-11-11
Android中Java instanceof關(guān)鍵字全面解析
instanceof關(guān)鍵字用于判斷一個(gè)引用類型變量所指向的對(duì)象是否是一個(gè)類(或接口、抽象類、父類)的實(shí)例.這篇文章主要介紹了Android中Java instanceof關(guān)鍵字全面解析的相關(guān)資料,需要的朋友可以參考下2016-07-07

