Android实现透明度可变的标题栏效果

时间:2021-09-16 08:41:53

我们在做类似于个人主页类应用的时候,可能会遇到这样的需求,效果如下

Android实现透明度可变的标题栏效果

Android实现透明度可变的标题栏效果

相信大家应该看明白是什么效果了,就是随着列表的滑动,上面的标题栏的透明度会随之变化。在ios中,有很多的软件有这种效果,下面,我们看一下这种效果是如何实现的。
先看一下项目的目录

Android实现透明度可变的标题栏效果

我们可以看到,目录结构很简单,因为我这个地方是使用的xlistview代替的listview,有很多文件都是xlistview自带的,所以显得文件多一些,如果没使用过xlistview,请先百度xlistview看看。
这里面,我们需要重点关注的只有一个文件,就是mainactivity,我们的关键代码都在这里,下面,我们看一下代码实现

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
/**
 * 透明度可变的标题栏
 *
 * @author zhao kaiqiang
 *
 * @time 2014-6-20 上午11:46:42
 */
public class mainactivity extends activity implements onscrolllistener {
 
 private xlistview listview;
 // 标题栏的布局
 private relativelayout rl_title;
 // listview的头布局
 private view headerview;
 // 头布局的高度
 private int headerheight;
 private layoutinflater inflater;
 private handler handler = new handler();
 
 @override
 protected void oncreate(bundle savedinstancestate) {
 super.oncreate(savedinstancestate);
 setcontentview(r.layout.activity_main);
 
 rl_title = (relativelayout) findviewbyid(r.id.rl_title);
 listview = (xlistview) findviewbyid(r.id.list);
 
 rl_title.getbackground().setalpha(0);
 inflater = layoutinflater.from(this);
 headerview = inflater.inflate(r.layout.header_listview, null);
 // 添加头布局
 listview.addheaderview(headerview);
 listview.setadapter(new myadapter());
 // 设置滚动监听
 listview.setonscrolllistener(this);
 // 设置可以刷新与加载更多
 listview.setpullloadenable(true);
 listview.setpullrefreshenable(true);
 listview.setxlistviewlistener(new ixlistviewlistener() {
 
  @override
  public void onrefresh() {
  // 单纯的模拟刷新过程
  handler.postdelayed(new runnable() {
 
   @override
   public void run() {
   listview.stoprefresh();
   }
  }, 500);
  }
 
  @override
  public void onloadmore() {
  // 单纯的模拟加载过程
  handler.postdelayed(new runnable() {
 
   @override
   public void run() {
   listview.stoploadmore();
   }
  }, 500);
  }
 });
 
 }
 
 // 自定义适配器
 private class myadapter extends baseadapter {
 
 // 默认显示10个item
 @override
 public int getcount() {
  return 10;
 }
 
 @override
 public object getitem(int position) {
  return position;
 }
 
 @override
 public long getitemid(int position) {
  return position;
 }
 
 @override
 public view getview(int position, view convertview, viewgroup parent) {
  if (convertview == null) {
  convertview = inflater.inflate(r.layout.item_list, null);
  }
 
  return convertview;
 }
 
 }
 
 @override
 public void onscrollstatechanged(abslistview view, int scrollstate) {
 
 }
 
 // 最重要的方法,标题栏的透明度变化在这个方法实现
 @override
 public void onscroll(abslistview listview, int firstvisibleitem,
  int visibleitemcount, int totalitemcount) {
 // 判断当前最上面显示的是不是头布局,因为xlistview有刷新控件,所以头布局的位置是1,即第二个
 if (firstvisibleitem == 1) {
  // 获取头布局
  view view = listview.getchildat(0);
  if (view != null) {
  // 获取头布局现在的最上部的位置的相反数
  int top = -view.gettop();
  // 获取头布局的高度
  headerheight = view.getheight();
  // 满足这个条件的时候,是头布局在xlistview的最上面第一个控件的时候,只有这个时候,我们才调整透明度
  if (top <= headerheight && top >= 0) {
   // 获取当前位置占头布局高度的百分比
   float f = (float) top / (float) headerheight;
   rl_title.getbackground().setalpha((int) (f * 255));
   // 通知标题栏刷新显示
   rl_title.invalidate();
  }
  }
 } else if (firstvisibleitem > 1) {
  rl_title.getbackground().setalpha(255);
 } else {
  rl_title.getbackground().setalpha(0);
 }
 }
 
}

代码是不是不复杂?我们只需要实现onscroll方法就可以,在这里面,完成我们对headerview的位置的检测,然后通过headerview的高度和显示的高度来计算比例,设置到titlebar的背景图片的透明度即可。

是不是很神奇,希望大家喜欢。