編輯:關於Android編程
已經好長時間沒更新博客了,今天給大家帶來一個橫向滾動的菜單,用的是HorizontalScrollView,但HorizontalScrollView不能在滾動時定位到某個菜單,因此監聽了onScrollChanged方法,代碼比較簡單,大家看代碼就行了,主要是封裝了一下,方便大家使用,項目github在底部會給出的。廢話不多說,先上效果圖:

這個控件已經進行了非常給力的封裝了,想必大家一定用的比較酸爽。
package com.horizontalscrollview;
import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.view.LayoutInflater;
import android.view.View;
import android.widget.ImageView;
import android.widget.TextView;
import android.widget.Toast;
import com.horizontalscrollview.view.HorizontalScrollMenuView;
import com.horizontalscrollview.view.adapter.BaseMenuAdapter;
public class MainActivity extends AppCompatActivity {
private int[] mDrawableId={R.drawable.image1,R.drawable.image3,R.drawable.image3};
private String[] mTitle={"菜單一","菜單二","菜單三"};
private HorizontalScrollMenuView mHorizontalScrollMenuView;
private MyMenuAdapter mMyMenuAdapter;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
initViews();
}
private void initViews(){
mHorizontalScrollMenuView= (HorizontalScrollMenuView) findViewById(R.id.hs_menu);
mMyMenuAdapter=new MyMenuAdapter();
mHorizontalScrollMenuView.setAdapter(mMyMenuAdapter);
mHorizontalScrollMenuView.notifyDataSetChanged();
}
class MyMenuAdapter extends BaseMenuAdapter{
@Override
public int getCount() {
return mTitle.length;
}
@Override
public View getView(final int position) {
View root= LayoutInflater.from(MainActivity.this).inflate(R.layout.menu_layout,null);
ImageView imageView= (ImageView) root.findViewById(R.id.iv_icon);
TextView tv_title= (TextView) root.findViewById(R.id.tv_title);
tv_title.setText(mTitle[position]);
imageView.setImageResource(mDrawableId[position]);
imageView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
Toast.makeText(MainActivity.this,"點擊了"+mTitle[position],Toast.LENGTH_SHORT).show();
}
});
return root;
}
@Override
public int getViewWidth() {
return 250;
}
}
}
用法已經貼出來了,下面有興趣的話看看源碼,沒興趣的話,我也沒轍,呵呵。。。
package com.horizontalscrollview.view.adapter;
import android.view.View;
/**
* Created by glh on 2016-08-11.
*/
public interface MenuAdapter {
int getCount();
View getView(int position);
}
package com.horizontalscrollview.view.adapter;
import android.util.SparseArray;
import android.view.View;
/**
* 菜單的抽象類,用戶子菜單View的保存
* Created by glh on 2016-08-11.
*/
public abstract class BaseMenuAdapter implements MenuAdapter{
private SparseArray mMenuArray=new SparseArray<>();
/**
* 獲取子View的寬度,必傳
* @return
*/
public abstract int getViewWidth();
public SparseArray getView(){
mMenuArray.clear();
for(int index=0,length=getCount();indexpackage com.horizontalscrollview.view;
import android.content.Context;
import android.os.Handler;
import android.os.Message;
import android.util.AttributeSet;
import android.util.SparseArray;
import android.view.LayoutInflater;
import android.view.MotionEvent;
import android.view.View;
import android.widget.LinearLayout;
import android.widget.RelativeLayout;
import com.horizontalscrollview.R;
import com.horizontalscrollview.util.DensityUtil;
import com.horizontalscrollview.view.adapter.BaseMenuAdapter;
/**
* 水平滾動的菜單
* Created by glh on 2016-08-11.
*/
public class HorizontalScrollMenuView extends RelativeLayout{
private Context mContext;
private View mRootView;
private LinearLayout ll_menu;//菜單容器
private ObservableHorizontalScrollView mObservableHorizontalScrollView;//滾動容器
private int mMenuIndex;
private int mScroll;
private int interval;//菜單最左邊和最右邊的距離
private int mMiddle;//菜單間隔距離
private int mViewWidth;//菜單寬度
private MyHandler mMyHandler;
private BaseMenuAdapter mBaseMenuAdapter;
public HorizontalScrollMenuView(Context context) {
this(context, null);
}
public HorizontalScrollMenuView(Context context, AttributeSet attrs) {
this(context, attrs, 0);
}
public HorizontalScrollMenuView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
this.mContext=context;
mMyHandler=new MyHandler();
interval=(DensityUtil.getWindowWidth(mContext) - DensityUtil.dip2px(250)) / 2;
mMiddle=DensityUtil.dip2px(25);
mViewWidth=DensityUtil.dip2px(250);
initView();
initEvent();
}
private void initView(){
mRootView= LayoutInflater.from(mContext).inflate(R.layout.horizontal_scroll_layout,this,true);
ll_menu= (LinearLayout) mRootView.findViewById(R.id.ll_menu);
mObservableHorizontalScrollView= (ObservableHorizontalScrollView) mRootView.findViewById(R.id.obh_view);
}
/**
* 添加菜單
*/
private void addMenu(){
ll_menu.removeAllViews();
SparseArray viewSparseArray=mBaseMenuAdapter.getView();
View intervalView;
for(int index=0,length=viewSparseArray.size();index
* 在最左邊增加一個(屏寬-菜單寬)/2的寬度的View,
* 目的在於使第一個菜單居中顯示。
*
*/
intervalView = new View(mContext);
intervalView.setLayoutParams(new LayoutParams(interval, 1));
ll_menu.addView(intervalView);
}
ll_menu.addView(viewSparseArray.get(index));
if (index == length-1) {
/**
*
* 在最右邊增加一個(屏寬-菜單寬)/2的寬度的View,
* 目的在於使最後一個菜單居中顯示。
*
*/
intervalView = new View(mContext);
intervalView.setLayoutParams(new LayoutParams(interval, 1));
ll_menu.addView(intervalView);
}else{
/**
* 兩個菜單之間留一點空隙
*/
intervalView = new View(mContext);
intervalView.setLayoutParams(new LayoutParams(mMiddle, 1));
ll_menu.addView(intervalView);
}
}
}
private void initEvent(){
mObservableHorizontalScrollView.setHorizontalScrollViewListener(new ObservableHorizontalScrollView.HorizontalScrollViewListener() {
@Override
public void onScrollChanged(ObservableHorizontalScrollView scrollView,
int x, int y, int oldx, int oldy) {
mMenuIndex = x / mViewWidth;//計算當前位置
mScroll = x % mViewWidth;
if (mScroll >= 0.5) {
mMenuIndex++;
}
if (oldx - x > 0) {
/**
* 菜單往右滑動
*/
mMenuIndex--;
}
}
});
mObservableHorizontalScrollView.setOnTouchListener(new OnTouchListener() {
@Override
public boolean onTouch(View v, MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_UP:
mMyHandler.sendEmptyMessage(0);
break;
default:
break;
}
return false;
}
});
}
/**
* 設置View
* @param adapter
*/
public void setAdapter(BaseMenuAdapter adapter){
this.mBaseMenuAdapter=adapter;
this.interval =(DensityUtil.getWindowWidth(mContext) - DensityUtil.dip2px(mBaseMenuAdapter.getViewWidth())) / 2;
this.mViewWidth=DensityUtil.dip2px(mBaseMenuAdapter.getViewWidth());
}
/**
* 刷新
*/
public void notifyDataSetChanged(){
addMenu();
}
/**
* 設置菜單間隔
* @param middle
*/
public void setMiddle(int middle){
mMiddle=DensityUtil.dip2px(middle);
}
class MyHandler extends Handler {
public MyHandler() {
}
@Override
public void handleMessage(Message msg) {
switch (msg.what) {
case 0:
mObservableHorizontalScrollView.smoothScrollTo(mMenuIndex * (mViewWidth + mMiddle), 0);
break;
}
}
}
}
項目地址(豪華套餐)
以下是完整的github項目地址
github項目源碼地址:點擊【項目源碼】
Android 界面開發顏色整理
下圖是幫助文檔中的關於界面開發的推薦色值,大家可以參考一下: 補充一些常用的顏色值: <color name=white>#f
android基礎部分再學習--AIDL
AIDL與其他IDL語言類似,你需要做一些工作。 它允許你定義客戶端與服務端達成一致的程序接口使用進程間通信相互交流。 在ANdroid上面,一個進程不能正常的訪問另一個
Android自定義View仿支付寶芝麻信用分儀表盤
先看下iOS的芝麻信用分截圖這是我做的效果,還是有點差距的支付寶9.9版本芝麻信用分的實現首先初始化各種畫筆,默認的size,padding,小圓點.(因為實在找不到原版
紅米3S和紅米3有什麼區別?紅米3S和紅米3哪個好?紅米3S和紅米3對比分析
時隔5個月時間,即6月14日,紅米3S作為紅米3的升級版,配備了高通骁龍430八核處理器,配備4100毫安時電池,定價699元起。紅米3S相對於紅米3的售價