概述
1. 简介
本文将记录的是一些有效的自定义指示器demo,诚然Indicator的开源框架还是比较多的,我们在具体具体中可以衡量。一些简单的自定义基础还是有必要好好掌握的。
2. demo样例
2.1 图片背景选择(stateListDrawable)+ViewPager样式
stateListDrawable相关文章:
首先看下效果吧:Android UI之stateListDrawable stateListAnimator ripple背景的综合运用
如下图所示,可以滑动viewPager来滑动头部的指示器;也可以通过点击指示器来选择不同的界面
具体实现:
首先就是布局咯:和 tabLayout+ViewPager的形式是一样的布局
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
tools:context=".indicator.IndicatorOneActivity">
<LinearLayout
android:layout_gravity="center_horizontal"
android:layout_width="wrap_content"
android:layout_height="50dp"
android:background="#ffce3d3a">
<ImageView
android:id="@+id/iv_title_gank"
android:layout_width="55dp"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:background="?attr/selectableItemBackgroundBorderless"
android:src="@drawable/titlebar_disco" />
<ImageView
android:id="@+id/iv_title_one"
android:layout_width="55dp"
android:layout_height="match_parent"
android:background="?attr/selectableItemBackgroundBorderless"
android:src="@drawable/titlebar_music" />
<ImageView
android:id="@+id/iv_title_dou"
android:layout_width="55dp"
android:layout_height="match_parent"
android:background="?attr/selectableItemBackgroundBorderless"
android:src="@drawable/titlebar_friends" />
</LinearLayout>
<android.support.v4.view.ViewPager
android:id="@+id/viewPager"
android:descendantFocusability="blocksDescendants"
android:layout_width="match_parent"
android:layout_height="match_parent">
</android.support.v4.view.ViewPager>
<!-- android:descendantFocusability="blocksDescendants"
解决滑动冲突的
-->
</LinearLayout>
单个imageView的指示器背景布局如下:stateListDrawable
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:drawable="@drawable/titlebar_music_selected" android:state_selected="true"/>
<item android:drawable="@drawable/titlebar_music_normal" android:state_selected="false"/>
<item android:drawable="@drawable/titlebar_music_normal" android:state_pressed="false"/>
</selector>
activity中的核心代码如下:
// 设置点击事件 --- 改变之前判断是否被选中了---
private void setListener() {
ivGank.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
//不然cpu会有损耗
if (mViewPager.getCurrentItem() != 0) {
ivGank.setSelected(true);
ivBook.setSelected(false);
ivMe.setSelected(false);
mViewPager.setCurrentItem(0);
}
}
});
ivBook.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
//不然cpu会有损耗
if (mViewPager.getCurrentItem() != 1) {
ivGank.setSelected(false);
ivBook.setSelected(true);
ivMe.setSelected(false);
mViewPager.setCurrentItem(1);
}
}
});
ivMe.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
//不然cpu会有损耗
if (mViewPager.getCurrentItem() != 2) {
ivGank.setSelected(false);
ivBook.setSelected(false);
ivMe.setSelected(true);
mViewPager.setCurrentItem(2);
}
}
});
}
private void setViewPager() {
ArrayList<Fragment> fragments = new ArrayList<>();
fragments.add(new GankFragment());
fragments.add(new GankFragment());
fragments.add(new MeFragment());
mViewPager.setAdapter(new MyFragmentAdapter(getSupportFragmentManager(),fragments));
mViewPager.setOffscreenPageLimit(2);
// 设置viewpage滑动监听 ---- 当滑到某个界面时 标题背景改变
mViewPager.addOnPageChangeListener(this);
// 设置默认选中第一个 通过选中的背景设置切换
ivGank.setSelected(true);
mViewPager.setCurrentItem(0);
}
还是很easy的,因为我们接触的项目有可能TabLayout不能满足我们的需求,这时候可以去GitHub上找轮子,也可以自己来定义View,也算是一种积累吧。总之 viewPager这一组件讲真还是特别重要的,有必要好好的学习下。
2.2 RadioGroup样例
可以观察下效果:
<RadioGroup
android:layout_marginTop="20dp"
android:layout_gravity="center_horizontal"
android:id="@+id/radioGroup"
android:orientation="horizontal"
android:layout_width="wrap_content"
android:layout_height="wrap_content">
<RadioButton
android:id="@+id/rb1"
android:padding="8dp"
android:button="@null"
android:text="贡献周榜"
android:background="@drawable/drawable_selector_left"
android:textColor="@color/text_radio_color"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<RadioButton
android:id="@+id/rb2"
android:padding="8dp"
android:button="@null"
android:text="贡献总榜"
android:background="@drawable/drawable_selector_right"
android:textColor="@color/text_radio_color"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
</RadioGroup>
text_radio_color.xml
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:color="#000000" android:state_checked="false" />
<item android:color="#00ff00" android:state_checked="true" />
</selector>
drawable_selector_right.xml
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:state_checked="true" android:drawable="@drawable/drawable_right_selected_true"/>
<item android:state_checked="false" android:drawable="@drawable/drawable_right_selected_false"/>
</selector>
<!--false -->
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle" >
<solid
android:color="#ffffff"/>
<corners
android:topRightRadius="5dp"
android:bottomRightRadius="5dp"/>
</shape>
<!--true-->
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle" >
<solid
android:color="#ff0000"/>
<corners
android:topRightRadius="5dp"
android:bottomRightRadius="5dp"/>
</shape>
2.3 究极RadiaButton实现仿58同城热门城市选择
首先看下效果吧:
如上所示,基本和58上的一样。下面将解析具体的绘制。
布局文件如下:
<com.example.mydairytestproject.views.WubaTownRadioGroup
android:layout_gravity="center_horizontal"
android:gravity="center"
android:orientation="horizontal"
android:id="@+id/city_hot_tab"
android:layout_marginTop="100dp"
android:layout_width="wrap_content"
android:layout_height="wrap_content">
<RadioButton android:textSize="14sp"
android:id="@+id/city"
android:textColor="@color/city_hot_tab_text_color"
android:gravity="center"
android:background="@drawable/city_left_bg"
android:layout_width="80dp"
android:layout_height="29dp"
android:button="@null"
android:text="城市" />
<RadioButton android:textSize="14sp"
android:id="@+id/town"
android:textColor="@color/city_hot_tab_text_color"
android:gravity="center"
android:background="@drawable/city_center_bg"
android:layout_width="80dp"
android:layout_height="29dp"
android:button="@null"
android:text="乡镇" />
<RadioButton android:textSize="14sp"
android:id="@+id/country"
android:textColor="@color/city_hot_tab_text_color"
android:gravity="center"
android:background="@drawable/city_right_bg"
android:layout_width="80dp"
android:layout_height="29dp"
android:button="@null"
android:text="海外" />
</com.example.mydairytestproject.views.WubaTownRadioGroup>
和前面的案例是相类似的,无非就是 radioGroup+radioButton+stateListDrawable+colorSelector等完成的效果。这里drawable包括color文件我就不给出来了,和前面的案例相类似。值得注意的是,可以发现58案例比简易案例多了边缘框和中间的分割线,这就是不同点,也是需要指出的具体细节,接下来就相应的进行解析。
编写自定义控件继承自RadioGroup,绘制背景边框,接着再绘制分割线即可。代码如下所示。
public class WubaTownRadioGroup extends RadioGroup
{
// 边缘 分割线颜色
private int bgColor = Color.parseColor("#ff552e");
// 画笔
private Paint mpaint;
// 圆弧半径 === 注意这里的半径 应当和xml里设置的左右的corners 呈对应关系
private int roundWidth;
// 边缘线宽度
private int strokeWidth;
public WubaTownRadioGroup(Context paramContext)
{
super(paramContext);
}
public WubaTownRadioGroup(Context paramContext, AttributeSet paramAttributeSet)
{
super(paramContext, paramAttributeSet);
}
private void drawDivider(Canvas paramCanvas)
{
if (getOrientation() == LinearLayout.HORIZONTAL)
{
int j = getChildCount();
if (j > 1)
{
int i = 1;
while (i < j)
{
int k = getChildAt(i).getLeft();
paramCanvas.drawLine(k, 0.0F, k, getMeasuredHeight(), this.mpaint);
i += 1;
}
}
}
}
private void drawRoundBackGround(Canvas paramCanvas)
{
this.roundWidth = ((int)TypedValue.applyDimension(1, 4.0F, getResources().getDisplayMetrics()));
float f = this.mpaint.getStrokeWidth() - 1.0F;
// 绘制圆角矩形
paramCanvas.drawRoundRect(new RectF(
0.0F + f,
0.0F + f,
getMeasuredWidth() - f,
getMeasuredHeight() - f),
this.roundWidth,
this.roundWidth,
this.mpaint);
}
private void initPaint()
{
// 这里要做适配
this.strokeWidth = ((int) TypedValue.applyDimension(1, 1.0F, getResources().getDisplayMetrics()));
this.mpaint = new Paint();
this.mpaint.setStrokeWidth(this.strokeWidth);
// 设置抗锯齿 优化显示效果
this.mpaint.setAntiAlias(true);
// 设置防止抖动
this.mpaint.setDither(true);
this.mpaint.setStyle(Paint.Style.STROKE);
this.mpaint.setColor(this.bgColor);
}
@Override
protected void dispatchDraw(Canvas paramCanvas)
{
super.dispatchDraw(paramCanvas);
if ((getMeasuredHeight() > 0) && (getMeasuredWidth() > 0))
{
initPaint();
drawRoundBackGround(paramCanvas);
drawDivider(paramCanvas);
}
}
public void setBgColor(int paramInt)
{
this.bgColor = paramInt;
}
}
最后
以上就是花痴羽毛为你收集整理的Android UI之自定义头部指示器实现仿网易云音乐地区选择1. 简介 2. demo样例的全部内容,希望文章能够帮你解决Android UI之自定义头部指示器实现仿网易云音乐地区选择1. 简介 2. demo样例所遇到的程序开发问题。
如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。
发表评论 取消回复