Android UI進(jìn)階之仿iphone的tab效果二
接著上篇文章繼續(xù)完成。在android中把這個(gè)仿iphone效果的tab寫完,這個(gè)例子參考國外rolle3k共享的代碼。
上篇博客我們寫了一個(gè)Itab類,介紹了背景的繪制和簡單的一個(gè)圖的貼圖方法。我們繼續(xù)來完成Itab這個(gè)類,同時(shí)把他放到MainAcitvity(繼承Activity)這個(gè)類內(nèi)部,這樣,整個(gè)程序只需一個(gè)類就可以了。(上篇博客例子運(yùn)行需要再建一個(gè)Activity的子類來作為lanucher)??纯创a
- public static class iTab extends View {
- private Paint mPaint;//背景畫筆
- private Paint mActiveTextPaint;//選中
- private Paint mInactiveTextPaint;//未選中
- private ArrayList<TabMember> mTabMembers;//tab成員
- private int mActiveTab;
- private OnTabClickListener mOnTabClickListener = null;
- public iTab( Context context, AttributeSet attrs ) //構(gòu)造器,在里面初始化畫筆 {
- super(context, attrs);
- mTabMembers = new ArrayList<MainActivity.iTab.TabMember>( );
- mPaint = new Paint( );
- mActiveTextPaint = new Paint( );
- mInactiveTextPaint = new Paint( );
- mPaint.setStyle( Paint.Style.FILL );
- mPaint.setColor( 0xFFFFFF00 );
- mPaint.setAntiAlias(true);
- mActiveTextPaint.setTextAlign( Align.CENTER );
- mActiveTextPaint.setTextSize( 12 );
- mActiveTextPaint.setColor( 0xFFFFFFFF );
- mActiveTextPaint.setAntiAlias(true);
- mInactiveTextPaint.setTextAlign( Align.CENTER );
- mInactiveTextPaint.setTextSize( 12 );
- mInactiveTextPaint.setColor( 0xFF999999 );
- mInactiveTextPaint.setAntiAlias(true);
- mActiveTab = 0;
- }
- @Override
- protected void onDraw( Canvas canvas ) {
- super.onDraw( canvas );
- Rect r = new Rect( );
- this.getDrawingRect( r );
- // 計(jì)算每個(gè)標(biāo)簽?zāi)苁褂枚嗌傧袼?nbsp;
- int singleTabWidth = r.right / ( mTabMembers.size( ) != 0 ? mTabMembers.size( ) : 1 );
- // 繪制背景
- canvas.drawColor( 0xFF000000 );
- mPaint.setColor( 0xFF434343 );
- canvas.drawLine( r.left, r.top + 1, r.right, r.top + 1, mPaint );
- int color = 46;
- for( int i = 0; i < 24; i++ ) {
- mPaint.setARGB( 255, color, color, color );
- canvas.drawRect( r.left, r.top + i + 1, r.right, r.top + i + 2, mPaint );
- color--;
- }
- // 繪制每一個(gè)tab
- for( int i = 0; i < mTabMembers.size( ); i++ )
- {
- TabMember tabMember = mTabMembers.get( i );
- Bitmap icon = BitmapFactory.decodeResource( getResources( ), tabMember.getIconResourceId( ) );
- Bitmap iconColored = Bitmap.createBitmap( icon.getWidth(), icon.getHeight(), Bitmap.Config.ARGB_8888 );
- Paint p = new Paint( Paint.ANTI_ALIAS_FLAG | Paint.FILTER_BITMAP_FLAG);
- Canvas iconCanvas = new Canvas( );
- iconCanvas.setBitmap( iconColored );
- if( mActiveTab == i )//為已選中的tab繪制一個(gè)白藍(lán)的漸變色,未選中的繪制一個(gè)白灰的漸變色
- {
- p.setShader( new LinearGradient( 0, 0, icon.getWidth(), icon.getHeight(),
- 0xFFFFFFFF, 0xFF54C7E1, Shader.TileMode.CLAMP ) );
- }
- else {
- p.setShader( new LinearGradient( 0, 0, icon.getWidth(), icon.getHeight(),
- 0xFFA2A2A2, 0xFF5F5F5F, Shader.TileMode.CLAMP ) );
- }
- iconCanvas.drawRect( 0, 0, icon.getWidth( ), icon.getHeight( ), p );
- for( int x = 0; x < icon.getWidth(); x++ )
- {
- for( int y = 0; y < icon.getHeight(); y++ )
- {
- if( ( icon.getPixel(x, y) & 0xFF000000 ) == 0 )
- {
- iconColored.setPixel( x, y, 0x00000000 );
- }
- }
- }
- // 計(jì)算tab圖片的位置
- int tabImgX = singleTabWidth * i + ( singleTabWidth / 2 - icon.getWidth( ) / 2 );
- // 繪制tab圖片 選中的和未選中的
- if( mActiveTab == i )
- {
- mPaint.setARGB( 37, 255, 255, 255 );
- canvas.drawRoundRect( new RectF( r.left + singleTabWidth * i + 3, r.top + 3,
- r.left + singleTabWidth * ( i + 1 ) - 3, r.bottom - 2 ), 5, 5, mPaint );
- canvas.drawBitmap( iconColored, tabImgX , r.top + 5, null );
- canvas.drawText( tabMember.getText( ),
- singleTabWidth * i + ( singleTabWidth / 2), r.bottom - 2, mActiveTextPaint );
- } else
- {
- canvas.drawBitmap( iconColored, tabImgX , r.top + 5, null );
- canvas.drawText( tabMember.getText( ),
- singleTabWidth * i + ( singleTabWidth / 2), r.bottom - 2, mInactiveTextPaint );
- }
- }
- }
- /*120
- * 觸摸事件
- */
- @Override
- public boolean onTouchEvent( MotionEvent motionEvent )
- {
- Rect r = new Rect( );
- this.getDrawingRect( r );
- float singleTabWidth = r.right / ( mTabMembers.size( ) != 0 ? mTabMembers.size( ) : 1 );
- int pressedTab = (int) ( ( motionEvent.getX( ) / singleTabWidth ) - ( motionEvent.getX( ) / singleTabWidth ) % 1 );
- mActiveTab = pressedTab;
- if( this.mOnTabClickListener != null)
- this.mOnTabClickListener.onTabClick( mTabMembers.get( pressedTab ).getId( ) );
- }
- this.invalidate();
- return super.onTouchEvent( motionEvent );
- }
- void addTabMember( TabMember tabMember )
- {
- mTabMembers.add( tabMember );
- }
- void setOnTabClickListener( OnTabClickListener onTabClickListener )
- {
- mOnTabClickListener = onTabClickListener;
- }
- public static class TabMember//處理tab成員
- {
- protected int mId;
- protected String mText;
- protected int mIconResourceId;
- TabMember( int Id, String Text, int iconResourceId )
- {
- mId = Id;
- mIconResourceId = iconResourceId;
- mText = Text;
- }
- public int getId( )
- {
- return mId;169
- }
- public String getText( )
- {
- return mText;
- }
- public int getIconResourceId( )
- {
- return mIconResourceId;
- }
- public void setText( String Text )
- {
- mText = Text;
- }
- public void setIconResourceId( int iconResourceId )
- {
- mIconResourceId = iconResourceId;189
- }
- public static interface OnTabClickListener193 {
- 、public abstract void onTabClick( int tabId );
- }
- }
這是MainActivity這個(gè)類里面的兩個(gè)static類,看我寫的注釋和上篇博客的內(nèi)容應(yīng)該都能理解。其中還定義了觸摸事件,實(shí)現(xiàn)點(diǎn)擊tab出現(xiàn)不同布局的效果。接下來我們只需要在我們的layout上添加就可以了,我們繼續(xù)寫一個(gè)內(nèi)部類
- public static class iRelativeLayout extends RelativeLayout//注意,還是聲明為靜態(tài)
- {
- private Paint mPaint;
- private Rect mRect;
- public iRelativeLayout( Context context, AttributeSet attrs )
- {
- super(context, attrs);
- mRect = new Rect( );
- mPaint = new Paint( );
- mPaint.setStyle( Paint.Style.FILL_AND_STROKE );
- mPaint.setColor( 0xFFCBD2D8 );
- }
- @Override
- protected void onDraw( Canvas canvas )
- {
- super.onDraw( canvas );
- canvas.drawColor( 0xFFC5CCD4 );
- this.getDrawingRect( mRect );
- for( int i = 0; i < mRect.right; i += 7 )//繪制屏幕背景的紋理效果
- {
- canvas.drawRect( mRect.left + i, mRect.top, mRect.left + i + 2, mRect.bottom, mPaint );
- }
- }
- }
- private static final int TAB_HIGHLIGHT = 1;
- private static final int TAB_CHAT = 2;
- private static final int TAB_LOOPBACK = 3;
- private static final int TAB_REDO = 4;
- private iTab mTabs;
- private LinearLayout mTabLayout_One;
- private LinearLayout mTabLayout_Two;
- private LinearLayout mTabLayout_Three;
- private LinearLayout mTabLayout_Four;
- private LinearLayout mTabLayout_Five;
- @Override
- public void onCreate(Bundle savedInstanceState)
- {
- super.onCreate(savedInstanceState);
- setContentView(R.layout.main);
- mTabs = (iTab) this.findViewById( R.id.Tabs );
- mTabLayout_One = (LinearLayout) this.findViewById( R.id.TabLayout_One );
- mTabLayout_Two = (LinearLayout) this.findViewById( R.id.TabLayout_Two );
- mTabLayout_Three = (LinearLayout) this.findViewById( R.id.TabLayout_Three );
- mTabLayout_Four = (LinearLayout) this.findViewById( R.id.TabLayout_Four );
- mTabLayout_Five = (LinearLayout) this.findViewById( R.id.TabLayout_Four );//偷個(gè)懶,不寫第五個(gè)界面啦
- mTabs.addTabMember( new TabMember( TAB_HIGHLIGHT, "精選", R.drawable.jingxuan ) );
- mTabs.addTabMember( new TabMember( TAB_CHAT, "類別", R.drawable.cat ) );
- mTabs.addTabMember( new TabMember( TAB_LOOPBACK, "25大排行榜", R.drawable.rank ) );
- mTabs.addTabMember( new TabMember( TAB_REDO, "搜索", R.drawable.search ) );
- mTabs.addTabMember( new TabMember( TAB_REDO, "更新", R.drawable.download ) );//添加tab
- /*初始顯示第一個(gè)界面*/
- mTabLayout_One.setVisibility( View.VISIBLE );
- mTabLayout_Two.setVisibility( View.GONE );
- mTabLayout_Three.setVisibility( View.GONE );
- mTabLayout_Four.setVisibility( View.GONE );
- mTabs.setOnTabClickListener( new OnTabClickListener( ) {
- @Override
- public void onTabClick( int tabId )//實(shí)現(xiàn)點(diǎn)擊事件
- {
- if( tabId == TAB_HIGHLIGHT )
- {
- mTabLayout_One.setVisibility( View.VISIBLE );
- mTabLayout_Two.setVisibility( View.GONE );
- mTabLayout_Three.setVisibility( View.GONE );
- mTabLayout_Four.setVisibility( View.GONE );
- } else if( tabId == TAB_CHAT )
- {
- mTabLayout_One.setVisibility( View.GONE );
- mTabLayout_Two.setVisibility( View.VISIBLE );
- mTabLayout_Three.setVisibility( View.GONE );
- mTabLayout_Four.setVisibility( View.GONE );
- } else if( tabId == TAB_LOOPBACK )
- {
- mTabLayout_One.setVisibility( View.GONE );
- mTabLayout_Two.setVisibility( View.GONE );
- mTabLayout_Three.setVisibility( View.VISIBLE );
- mTabLayout_Four.setVisibility( View.GONE );
- } else if( tabId == TAB_REDO )
- {
- mTabLayout_One.setVisibility( View.GONE );
- mTabLayout_Two.setVisibility( View.GONE );
- mTabLayout_Three.setVisibility( View.GONE );
- mTabLayout_Four.setVisibility( View.VISIBLE );
- }
- }
- });
- }
其中onDraw()方法里面實(shí)現(xiàn)了背景的紋理效果,配合xml里面背景色的配置,實(shí)現(xiàn)了如下圖所示的效果:
是不是非常漂亮呢。下面就是xml里面的配置了
- <?xml version="1.0" encoding="utf-8"?>
- <view xmlns:android="http://schemas.android.com/apk/res/android"
- class="com.notice520.MainActivity$iRelativeLayout"
- android:orientation="vertical"
- android:layout_width="fill_parent"
- android:layout_height="fill_parent"
- android:background = "#C5CCD4FF"
- >
- <LinearLayout
- android:id = "@+id/TabLayout_One"
- android:layout_width = "fill_parent"
- android:layout_height = "fill_parent"
- android:layout_above = "@+id/Tabs"
- >
- <ScrollView android:layout_width="fill_parent" android:layout_height="wrap_content">
- <RelativeLayout
- android:layout_width = "fill_parent"
- android:layout_height = "fill_parent"
- android:visibility = "visible"
- >
- <TextView
- android:textColor="@android:color/black"
- android:textSize="30sp"
- android:layout_width = "wrap_content"
- android:layout_height = "wrap_content"
- android:text = "春節(jié)快樂!!"
- />
- </RelativeLayout>
- </ScrollView>
- </LinearLayout>
- <LinearLayout
- android:id = "@+id/TabLayout_Two"
- android:layout_width = "fill_parent"
- android:layout_height = "fill_parent"
- android:layout_above = "@+id/Tabs"
- >
- <ScrollView android:layout_width="fill_parent" android:layout_height="wrap_content">
- <RelativeLayout
- android:layout_width = "fill_parent"
- android:layout_height = "fill_parent"
- android:visibility = "visible"
- android:layout_above = "@+id/Tabs"
- >
- <Button
- android:layout_width = "wrap_content"
- android:layout_height = "wrap_content"
- android:text = "祝大家事業(yè)有成!"
- android:textSize = "30sp"
- />
- </RelativeLayout>
- </ScrollView>
- </LinearLayout>
- <LinearLayout
- android:id = "@+id/TabLayout_Three"
- android:layout_width = "fill_parent"
- android:layout_height = "fill_parent"
- android:layout_above = "@+id/Tabs"
- >
- <ScrollView android:layout_width="fill_parent" android:layout_height="wrap_content">
- <RelativeLayout
- android:layout_width = "fill_parent"
- android:layout_height = "fill_parent"
- android:visibility = "visible"
- android:layout_above = "@+id/Tabs"
- >
- <ImageView
- android:layout_width = "fill_parent"
- android:layout_height = "fill_parent"
- android:src="@drawable/newq"
- />
- </RelativeLayout>
- </ScrollView>
- </LinearLayout>
- <LinearLayout
- android:id = "@+id/TabLayout_Four"
- android:layout_width = "fill_parent"
- android:layout_height = "fill_parent"
- android:layout_above = "@+id/Tabs"
- >
- <ScrollView android:layout_width="fill_parent" android:layout_height="wrap_content">
- <RelativeLayout
- android:id = "@+id/TabLayout_Four"
- android:layout_width = "fill_parent"
- android:layout_height = "fill_parent"
- android:visibility = "visible"
- android:layout_above = "@+id/Tabs"
- >
- <TextView
- android:textColor="@android:color/black"
- android:layout_width = "wrap_content"
- android:layout_height = "wrap_content"
- android:text = "很簡單,是么"
- />
- </RelativeLayout>
- </ScrollView>
- </LinearLayout>
- <view
- class="com.notice520.MainActivity$iTab"
- android:id="@+id/Tabs"
- android:layout_width = "fill_parent"
- android:layout_height = "49px"
- android:layout_alignParentBottom = "true"
- />
- </view>108
來看看最終的效果吧
Android UI進(jìn)階之仿iphone的tab效果算是完了,不知道有沒有幫助到你。
【編輯推薦】
Android應(yīng)用之Activity傳參數(shù)與跳轉(zhuǎn)