本文链接http://blog.youkuaiyun.com/jan_s/article/details/50772360,转载请留言
简单介绍
Butter knife是大神JakeWharton的一款Android利器,多数开发者都应该了解和使用过,这把黄油刀最大的吸引人的地方就是简化了android程序编写中的view,findviewById(id)和setOnxxxListener事件的写法,它使用了一种很简洁的注解写法,例如
你会发现没有了findviewById这种超累的代码片段了,哈哈,这就值得让我们为这把黄油刀点赞!
简单使用
1.先下载butterknife的jar包,本文示例代码用的是版本7.0.1,可能与旧版本有些方法名不一样。如果用的是as:直接用gradle:
compile 'com.jakewharton:butterknife:7.0.1'
@bind方式就是简化了findviewbyid的代码,但在使用之前,一定要在Acivity中初始化Butterknife.bind(activity)。
先上本地demo的activity_main.xml,你可以直接跳过这段,没有具体的内容,主要是看这么引用这些控件的id.
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context=".ExampleActivity">
<LinearLayout
android:id="@+id/layout1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
<TextView
android:id="@+id/app_title_text"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="123"
android:gravity="center"
android:textSize="20sp" />
<Button
android:id="@+id/bind_btn"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/bind_me" />
<TextView
android:id="@+id/text_content"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="@string/cool_text"
android:textSize="20sp"
android:visibility="invisible" />
</LinearLayout>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_below="@+id/layout1"
android:background="#ADE8BA"
android:orientation="vertical">
<fragment
android:id="@+id/example_fragment"
android:name="org.jan.butterknife.demo.ExampleFragment"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
</LinearLayout>
</RelativeLayout>
ExampleActivity,先看看我们怎么使用butter knife获取控件引用,以及快速注册点击事件的。
其实就是两个步骤:1.初始化butterknifeimport android.os.Bundle; import android.support.v7.app.AppCompatActivity; import android.util.TypedValue; import android.view.View; import android.widget.Button; import android.widget.TextView; import android.widget.Toast; import butterknife.Bind; import butterknife.BindString; import butterknife.ButterKnife; import butterknife.OnClick; import butterknife.OnLongClick; import static android.widget.Toast.LENGTH_SHORT; /** * butterknife的简单使示例代码 */ public class ExampleActivity extends AppCompatActivity { /** * 2:7.0+版本的butterKnife将使用bind注解 * 注:因为注解用到了反射机制,所以这里的所有用到butterKnife的注解的变量都是非private的 */ @Bind(R.id.bind_btn) Button button; @Bind(R.id.text_content) TextView mCoolText; @Bind(R.id.app_title_text) TextView mTitleText; //绑定预定义的字符串资源,还有其他的一些方法如:@BindBool, @BindColor, @BindDimen, @BindDrawable, @BindInt @BindString(R.string.butterknife_demo) String title; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); //1.将绑定该Activity ButterKnife.bind(this); //3.已经不再需要一个个findviewbyid了,可以直接调用,非常省心 userFieldToDo(); } private void userFieldToDo() { button.setTextSize(TypedValue.COMPLEX_UNIT_DIP, 20); mTitleText.setText(title); mCoolText.setText("bind textview"); } /** * 4.@Onclick可以根据view's id来注册一个点击事件 * 方法参数是可选的,可以传一个view,或者widget, * 这里是无参的,你可以写成onClickBindButton(View view)或onClickBindButton(Button btn) */ @OnClick(R.id.bind_btn) void onClickBindButton() { mCoolText.setVisibility(View.VISIBLE); Toast.makeText(this, "I bind it!", LENGTH_SHORT).show(); } /** * 绑定长按事件,这里要有返回一个boolean值,默认为false * @return */ @OnLongClick(R.id.bind_btn) boolean onLongClickBindButton(){ Toast.makeText(this, "Let me go!", LENGTH_SHORT).show(); return true; } @Override public void onBackPressed() { super.onBackPressed(); finish(); } }
2.bind所需要的widget
3.在fragment中的话可以选择解除绑定。
这样写到底有没有用呢?看看效果吧,别搞了半天还是奔溃的。
果然是可行的,好东西果断要分享啊!
2.可能有人会有疑问,在Activity中这样做是可行的,但如果换在Fragment中或者listview的Adapter中,是否也可以用butterknife来简化代码呢,答案是肯定可以的。
** * 在fragment中的butterknifey运用 */ public class ExampleFragment extends Fragment { // @Bind(R.id.fragment_title) TextView mTitleText; @Bind(R.id.example_listview) ListView mListview; public ExampleFragment() { } @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); } @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { View view = inflater.inflate(R.layout.fragment_example, container, false); //1.bind方法很是很灵活的 ButterKnife.bind(this, view); //2.如果遇到必须要利用findviewbyid的方式来引用某个view的话,你可以使用下面这种方式 mTitleText = ButterKnife.findById(view,R.id.fragment_title); mTitleText.setGravity(Gravity.CENTER_HORIZONTAL); mTitleText.setText("Example Fragment"); SimpleAdapter adapter = new SimpleAdapter(getContext()); mListview.setAdapter(adapter); return view; } //给listview注册了一个onItemClick事件,这里的会传入一个position @OnItemClick(R.id.example_listview) void onItemClick(int position){ String item = mListview.getAdapter().getItem(position).toString(); Toast.makeText(getContext(),"i clicked "+item,Toast.LENGTH_SHORT).show(); } @Override public void onResume() { super.onResume(); } @Override public void onPause() { super.onPause(); } @Override public void onDestroyView() { super.onDestroyView(); //2.解除绑定 ButterKnife.unbind(this); } }
fragment_example.xml 这是fragment的布局文件,就是展示一个简单的listview.
Listview使用的SimpleAdapter.java<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" tools:context="org.jan.butterknife.demo.ExampleFragment"> <LinearLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="vertical"> <TextView android:id="@+id/fragment_title" android:layout_width="wrap_content" android:layout_height="wrap_content"/> <ListView android:id="@+id/example_listview" android:layout_width="match_parent" android:layout_height="wrap_content" android:divider="#FFFFFF" android:dividerHeight="1dp" /> </LinearLayout> </FrameLayout>
simple_list_item.xml 这是list_item的布局。import android.content.Context; import android.graphics.drawable.Drawable; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.BaseAdapter; import android.widget.ImageView; import android.widget.TextView; import butterknife.Bind; import butterknife.BindDrawable; import butterknife.ButterKnife; public class SimpleAdapter extends BaseAdapter { private static final String[] CONTENTS = "谁也 跟不上 我的 节奏 德玛西亚 啦啦 啦啦啦".split(" "); private final LayoutInflater inflater; public SimpleAdapter(Context context) { inflater = LayoutInflater.from(context); } @Override public int getCount() { return CONTENTS.length; } @Override public String getItem(int position) { return CONTENTS[position]; } @Override public long getItemId(int position) { return position; } @Override public View getView(int position, View view, ViewGroup parent) { ViewHolder holder; if (view != null) { holder = (ViewHolder) view.getTag(); } else { view = inflater.inflate(R.layout.simple_list_item, parent, false); holder = new ViewHolder(view); view.setTag(holder); } String s = getItem(position); holder.word.setText(s); holder.imageView.setBackground(holder.defaultImage); return view; } /** * 看ViewHolder的变量就知道我们又省去在getview方法里不停的findviewbyid了 */ static class ViewHolder { @Bind(R.id.hehe_image) ImageView imageView; @Bind(R.id.hehe_text) TextView word; @BindDrawable(R.drawable.main_icon_service) Drawable defaultImage; ViewHolder(View view) { //这里黄油刀在构造函数中久把fragment中的视图绑定了 ButterKnife.bind(this, view); } } }
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="horizontal"> <ImageView android:id="@+id/hehe_image" android:layout_width="wrap_content" android:layout_height="wrap_content" /> <TextView android:id="@+id/hehe_text" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="test" android:textSize="16sp" /> </LinearLayout>
还有一些事件的写法我这里就不一一举例了。详细的使用我们可以看--->DOC<-----
最后,谢谢阅读。