很多软件在编辑框处都有一键清除的按钮,这里介绍一下其实现方式
xml文件添加如下,使得清除按钮位于EditText的最右方
然后就是在java文件onCreate函数中实现逻辑了,这里我们所用到的控件为TextWatcher
private EditText login_username;
private Button login_username_clear;
private TextWatcher login_username_watcher;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_login_register);
login_username = (EditText)findViewById(R.id.login_username);
login_username_clear = (Button)findViewById(R.id.login_username_clear);
login_username.addTextChangedListener(login_username_watcher);
login_username_watcher = new TextWatcher() {
public void onTextChanged(CharSequence s, int start, int before, int count) {}
public void beforeTextChanged(CharSequence s, int start, int count,int after) {}
public void afterTextChanged(Editable s) {
login_password.setText("");
if(s.toString().length()>0){
login_username_clear.setVisibility(View.VISIBLE);
}else{
login_username_clear.setVisibility(View.INVISIBLE);
}
}
};
}
这样就实现了一键清除效果按钮了
我使用Toolbar组件来实现了logo和APP名称的显示,同时还在右侧增加了小组件以便于功能拓展
首先要把原有的ActionBar删除,这里需要修改AndriodManifest文件
删除了之后,就可以在xml文件中加入自定义的Toolbar了
其中的PopWindowBackgroundStyle如下
随后仍然是修改java文件
private Toolbar toolbar;
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main_part);
toolbar = findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.main_menu, menu);
return super.onCreateOptionsMenu(menu);
}
这里的main_menu就是自定义的右侧功能组文件,可以选择添加自己想要的功能,这里我定义了一个系统自带的搜索按钮和一个自定义的按钮
PlusActionProvider类用于自定义新按钮的功能
public class PlusActionProvider extends ActionProvider {
/**
* Creates a new instance.
*
* @param context Context for accessing resources.
*/
private Context context;
public PlusActionProvider(Context context) {
super(context);
this.context = context;
}
@Override
public View onCreateActionView() {
return null;
}
@Override
public void onPrepareSubMenu(SubMenu subMenu) {
subMenu.clear();
subMenu.add(("新建跑腿任务"))
.setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() {
@Override
public boolean onMenuItemClick(MenuItem item) {
Intent intent = new Intent(getContext(),creat_errand_activity.class);
getContext().startActivity(intent);
return true;
}
});
subMenu.add(("新建问卷任务"))
.setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() {
@Override
public boolean onMenuItemClick(MenuItem item) {
Intent intent = new Intent(getContext(),createQuestionare.class);
getContext().startActivity(intent);
return true;
}
});
}
@Override
public boolean hasSubMenu() {
return true;
}
}
三个界面支持点击下方按钮切换或滑动切换
首先要明白的是这三个界面都是在同一个activity下,其中的页面内容可以通过修改ViewPager中绑定的Fragment来实现,上方的Toolbar则可以通过如上一个话题的onCreateOptionsMenu函数来实现修改
xml文件修改如下
activity页面如下
private ViewPager fragment_vp;
private RadioGroup tabs_rg;
private List fragments;
private FragmentPagerAdapter adapter;
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main_part);
fragment_vp = findViewById(R.id.fragment_vp);
tabs_rg = findViewById(R.id.tabs_rg);
fragments = new ArrayList<>(3);
fragments.add(MainFragment.newInstance("首页"));
fragments.add(TasksFragment.newInstance("任务"));
fragments.add(MeFragment.newInstance("我的"));
adapter = new MyFragmentPagerAdapter(getSupportFragmentManager(), fragments);
fragment_vp.setAdapter(adapter);
fragment_vp.addOnPageChangeListener(mPageChangeListener);
tabs_rg.setOnCheckedChangeListener(mOnCheckedChangeListener);
}
@Override
protected void onDestroy() {
super.onDestroy();
fragment_vp.removeOnPageChangeListener(mPageChangeListener);
}
private ViewPager.OnPageChangeListener mPageChangeListener = new ViewPager.OnPageChangeListener() {
@Override
public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
}
@Override
public void onPageSelected(int position) {
RadioButton radioButton = (RadioButton) tabs_rg.getChildAt(position);
radioButton.setChecked(true);
}
@Override
public void onPageScrollStateChanged(int state) {
}
};
private RadioGroup.OnCheckedChangeListener mOnCheckedChangeListener = new RadioGroup.OnCheckedChangeListener() {
@Override
public void onCheckedChanged(RadioGroup group, int checkedId) {
for (int i = 0; i < group.getChildCount(); i++) {
if (group.getChildAt(i).getId() == checkedId) {
fragment_vp.setCurrentItem(i);
if(headerUri != null)
{
CircleImageView btn = findViewById(R.id.headerPic);
if(btn == null)
{
return;
}
btn.setImageURI(headerUri);
}
if(sex == Constants.FEMALE)
{
ImageView sexImage = findViewById(R.id.sexImage);
if(sexImage == null)
return;
sexImage.setImageResource(R.mipmap.girl);
}
else
{
ImageView sexImage = findViewById(R.id.sexImage);
if(sexImage == null)
return;
sexImage.setImageResource(R.mipmap.boy);
}
return;
}
}
}
};
private class MyFragmentPagerAdapter extends FragmentPagerAdapter {
private List mList;
public MyFragmentPagerAdapter(FragmentManager fm, List list) {
super(fm);
this.mList = list;
}
@Override
public Fragment getItem(int position) {
return this.mList == null ? null : this.mList.get(position);
}
@Override
public int getCount() {
return this.mList == null ? 0 : this.mList.size();
}
}
最后再分别完成各个Fragment的内容就可以实现页面切换了
java文件如下,由于我是在Fragment中实现,所以会和在Activity中实现有所不同
public class MainFragment extends Fragment {
private Spinner spinner1, spinner2, spinner3, spinner4;
private List missionslist = new ArrayList();//missionslist为显示的内容,
private List totallist = new ArrayList(); //totallist为所有mission内容,ques_list和err_list分别为问卷任务和跑腿任务
private List questionare_missionslist = new ArrayList();
private List errand_missionslist = new ArrayList();
private String[] mItems1,mItems2,mItems3,mItems4;
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
View rootView = inflater.inflate(R.layout.main_fragment, container, false);
setHasOptionsMenu(true);
spinner1 = rootView.findViewById(R.id.spinner1);
spinner2 = rootView.findViewById(R.id.spinner2);
spinner3 = rootView.findViewById(R.id.spinner3);
spinner4 = rootView.findViewById(R.id.spinner4);
mItems1 = getResources().getStringArray(R.array.spin1);
mItems2 = getResources().getStringArray(R.array.spin2);
mItems3 = getResources().getStringArray(R.array.spin3);
mItems4 = getResources().getStringArray(R.array.spin4);
ArrayAdapter adapter1=new ArrayAdapter(getActivity(),android.R.layout.simple_spinner_dropdown_item, mItems1);
ArrayAdapter adapter2=new ArrayAdapter(getActivity(),android.R.layout.simple_spinner_dropdown_item, mItems2);
ArrayAdapter adapter3=new ArrayAdapter(getActivity(),android.R.layout.simple_spinner_dropdown_item, mItems3);
ArrayAdapter adapter4=new ArrayAdapter(getActivity(),android.R.layout.simple_spinner_dropdown_item, mItems4);
adapter1.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
adapter2.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
adapter3.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
adapter4.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
//绑定 Adapter到控件
spinner1.setAdapter(adapter1);
spinner2.setAdapter(adapter2);
spinner3.setAdapter(adapter3);
spinner4.setAdapter(adapter4);
iniSpiner();
}
private void iniSpiner(){//用于排序、筛选
spinner1.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() { //对问卷或跑腿任务进行筛选
@Override
public void onItemSelected(AdapterView> parent, View view, int position, long id) {
if(position == 0){
missionslist.clear();
missionslist.addAll(totallist);
}
else if(position == 1){
missionslist.clear();
missionslist.addAll(questionare_missionslist);
}
else{
missionslist.clear();
missionslist.addAll(errand_missionslist);
}
adapter.notifyDataSetChanged();
}
@Override
public void onNothingSelected(AdapterView> parent) {
}
});
spinner2.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener(){ //对酬劳进行排序
@Override
public void onItemSelected(AdapterView> parent, View view, int position, long id) {
if(position == 0){
MissionsSortUtil.sortById(missionslist);
}
else if(position == 1){
MissionsSortUtil.sortByPriceUp(missionslist);
}
else {
MissionsSortUtil.sortByPriceDown(missionslist);
}
adapter.notifyDataSetChanged();
}
@Override
public void onNothingSelected(AdapterView> parent) {
}
});
spinner3.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener(){ //对截止时间进行排序
@Override
public void onItemSelected(AdapterView> parent, View view, int position, long id) {
if(position == 0){
MissionsSortUtil.sortById(missionslist);
}
else if(position == 1){
MissionsSortUtil.sortByTimeUp(missionslist);
}
else {
MissionsSortUtil.sortByTimeDown(missionslist);
}
adapter.notifyDataSetChanged();
}
@Override
public void onNothingSelected(AdapterView> parent) {
}
});
}
}
上面的iniSpiner函数仅是我所需要的功能,大家可根据自己的需求自行更改
还有上面的arrays文件则是用来显示spinner下拉后的内容
- 所有类型
- 问卷任务
- 跑腿任务
- 任务酬劳
- 升序
- 降序
- 截止时间
- 时间充裕
- 时间急迫
- tag
- tag1
- tag2
- 我发布的
- 我接受的
- 全部
- 已完成
- 未完成
- 已过期
上面代码中的几个MissionsSortUtil.sortBy函数也是我自己定义的排序函数,大家也可以根据自己Listview中的定义的属性来进行排序
public class MissionsSortUtil {
static Comparator missionComparatorById = new Comparator() {
@Override
public int compare(Mission lhs, Mission rhs) {
if(lhs.getMissionId() > rhs.getMissionId())
return 1;
return -1; //注意此处不是0
}
};
static Comparator missionComparatorByPriceUp = new Comparator() {
@Override
public int compare(Mission lhs, Mission rhs) {
if(lhs.getMoney() < rhs.getMoney())
return 1;
return -1; //注意此处不是0
}
};
static Comparator missionComparatorByPriceDown = new Comparator() {
@Override
public int compare(Mission lhs, Mission rhs) {
if(lhs.getMoney() > rhs.getMoney())
return 1;
return -1; //注意此处不是0
}
};
static Comparator missionComparatorByTimeUp = new Comparator() {
@Override
public int compare(Mission lhs, Mission rhs) {
SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
try {
if(sdf.parse(lhs.getDeadLine()).getTime() < sdf.parse(rhs.getDeadLine()).getTime())
return 1;
} catch (ParseException e) {
e.printStackTrace();
}
return -1;
}
};
static Comparator missionComparatorByTimeDown = new Comparator() {
@Override
public int compare(Mission lhs, Mission rhs) {
SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
try {
if(sdf.parse(lhs.getDeadLine()).getTime() > sdf.parse(rhs.getDeadLine()).getTime())
return 1;
} catch (ParseException e) {
e.printStackTrace();
}
return -1;
}
};
public static void sortById(List missionsArray) {
Collections.sort(missionsArray, missionComparatorById);
}
public static void sortByPriceUp(List missionsArray) {
Collections.sort(missionsArray, missionComparatorByPriceUp);
}
public static void sortByPriceDown(List missionsArray) {
Collections.sort(missionsArray, missionComparatorByPriceDown);
}
public static void sortByTimeUp(List missionsArray) {
Collections.sort(missionsArray, missionComparatorByTimeUp);
}
public static void sortByTimeDown(List missionsArray) {
Collections.sort(missionsArray, missionComparatorByTimeDown);
}
}
当我们使用Listview来显示我们从后台拿到的数据时,我们可能会想要有一个功能使得数据能够在想要的时候进行刷新,于是我就使用SwipeRefreshLayout实现了下拉刷新效果
xml文件更改如下
java文件如下
swipeRefreshLayout = rootView.findViewById(R.id.swipeLayout);
swipeRefreshLayout.setSize(SwipeRefreshLayout.DEFAULT);
swipeRefreshLayout.setProgressViewEndTarget(true, 200);
swipeRefreshLayout.setOnRefreshListener(new SwipeRefreshLayout.OnRefreshListener() {
@Override
public void onRefresh() {
swipeRefreshLayout.setRefreshing(true);
getMissions();
}
});
其中的setRefreshing函数即让它显示搜索时的转圈圈效果,这个效果需要手动关闭,即在getMissions函数结尾加上swipeRefreshLayout.setRefreshing(false);即可
以上就是我对这次大项目所总结出的几个界面UI实用的小技巧,希望能够帮助到大家