一、高级组件
1.自动完成文本框AutoCompleteTextView
有以下常用xml属性
android:completionHint用于为弹出的下拉菜单指定标题
android:completionThreshold指定用户输入至少几个字符开始提示
android:dropDownHeigh/Weightt指定下拉菜单高度和宽度
android:popupBackground指定下拉菜单的背景
xml文件如下
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="match_parent">
<AutoCompleteTextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="@+id/autoview"
android:completionThreshold="2"
android:layout_weight="3"/>
<Button
android:id="@+id/get"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="获取内容"
android:layout_weight="1"
android:layout_marginLeft="10dp"/>
</LinearLayout>
java代码如下
package com.thundersoft.chapter2;
import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.widget.ArrayAdapter;
import android.widget.AutoCompleteTextView;
import android.widget.Button;
import android.widget.Toast;
import androidx.annotation.Nullable;
import com.thundersoft.session1.R;
public class AutoViewActivity extends Activity {
static final String[] strings = new String[]{"aadfdfdf","aawerwewe","aaxcxx","aawerw","aadfcv","aa123123"};
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.autocompletetextview);
AutoCompleteTextView textView = findViewById(R.id.autoview);
Button get = findViewById(R.id.get);
ArrayAdapter<String> adapter = new ArrayAdapter<>(this, android.R.layout.simple_dropdown_item_1line, strings);
textView.setAdapter(adapter);
get.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Toast.makeText(AutoViewActivity.this, textView.getText().toString(), Toast.LENGTH_SHORT).show();
}
});
}
}
java代码中,定义了一个static final类的字符串,接着在oncreate中定义数组适配器,将字符串放进适配器并且加载,就可完成提示
虚拟机可以增加中文语言,也可以输入中文字符串测试
2.进度条ProgressBar
后台进行前台现实,引出进度条
进度条的xml属性
android:max 一般为100,即进度条的最大值
android:progress 指定进度条的值,通常在java里和线程相关联
android:progressDrawable 设置进度条的轨道形式
进度条的style风格
?android:attr/progressBarStyleHorizontal细长条
?android:attr/progressBarStyleLarge/Small大/小圆形
@android:style/Widget.ProgressBar.Large/Small大/小跳远、旋转画面的进度条
@android:style/Widget.ProgressBar.Horizontal粗长条
xml代码如下
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="match_parent">
<AutoCompleteTextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="@+id/autoview"
android:completionThreshold="2"
android:layout_weight="3"/>
<Button
android:id="@+id/get"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="获取内容"
android:layout_weight="1"
android:layout_marginLeft="10dp"/>
</LinearLayout>
java代码如下
package com.thundersoft.chapter2;
import android.app.Activity;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.view.View;
import android.widget.ProgressBar;
import android.widget.Toast;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import com.thundersoft.session1.R;
public class ProgressBarActivity extends Activity {
private int status = 0;
private Handler handler;
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.progressbar);
ProgressBar bar1 = findViewById(R.id.bar1);
ProgressBar bar2 = findViewById(R.id.bar2);
handler = new Handler(){
@Override
public void handleMessage(Message msg) {
if (msg.what==0x111){
bar1.setProgress(status);
bar2.setProgress(status);
}else {
Toast.makeText(ProgressBarActivity.this, "操作完成", Toast.LENGTH_SHORT).show();
bar1.setVisibility(View.GONE);
bar2.setVisibility(View.GONE);
}
}
};
new Thread(new Runnable() {
@Override
public void run() {
while (true){
status = doWork();
Message message = new Message();
if (status<100){
message.what=0x111;
handler.sendMessage(message);
}else {
message.what=0x110;
handler.sendMessage(message);
break;
}
}
}
int doWork(){
status += Math.random()*10;
try{
Thread.sleep(200);
} catch (InterruptedException e) {
e.printStackTrace();
}
return status;
}
}).start();
}
}
定义一个处理消息的handler对象,在oncreate方法中,利用匿名内部类来实例化处理消息的handler对象,重写了其中的handleMessage方法,实现了耗时操作没有完成的时候就更新进度,否则就进度条不显示
message.what=0x111相当于一个case,what即为case的条件,它是为了判断what的值来进行相应操作,相当于一个判断中间值
线程方面,每一次dowork方法status都会增加0~1乘以10,接着暂停0.2s,当status小于100时就会发送0x111的消息,否则发送0x110的消息,如果是0x111就通过setProgress操作更新progressbar,否则就让进度条消失并且显示toast
不过我们可以使用AsyncTask来更加好的控制进程
下面演示了进度条完成后加载图片的一系列操作
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="@+id/linearlayout">
<ProgressBar
android:id="@+id/bartest"
android:layout_width="match_parent"
android:layout_height="wrap_content"
style="?android:attr/progressBarStyleHorizontal"
android:max="100"/>
</LinearLayout>
package com.thundersoft.chapter2;
import android.app.Activity;
import android.os.AsyncTask;
import android.os.Bundle;
import android.view.View;
import android.view.ViewGroup;
import android.view.Window;
import android.widget.FrameLayout;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.ProgressBar;
import androidx.annotation.Nullable;
import com.thundersoft.session1.R;
public class Test1Activity extends Activity {
private int image[] = new int[]{R.drawable.jpg1,R.drawable.jpg2,R.drawable.jpg3,R.drawable.jpg4,R.drawable.jpg5};
private LinearLayout linearLayout;
private ProgressBar progressBar;
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
requestWindowFeature(Window.FEATURE_PROGRESS);
setContentView(R.layout.test1);
linearLayout = findViewById(R.id.linearlayout);
progressBar = findViewById(R.id.bartest);
new MyTack().execute();
}
class MyTack extends AsyncTask<Void,Integer,LinearLayout>{
@Override
protected LinearLayout doInBackground(Void... params) {
LinearLayout layout = new LinearLayout(Test1Activity.this);
for (int i = 1; i < image.length+1; i++) {
ImageView imageView = new ImageView(Test1Activity.this);
imageView.setLayoutParams(new ViewGroup.LayoutParams(200,200));
imageView.setImageResource(image[i-1]);
try {
layout.addView(imageView);
Thread.sleep(5000);
} catch (InterruptedException e) {
e.printStackTrace();
}
publishProgress(i);
}
return layout;
}
@Override
protected void onProgressUpdate(Integer... values) {
progressBar.setProgress(values[0]*20);
super.onProgressUpdate(values);
}
@Override
protected void onPostExecute(LinearLayout result) {
progressBar.setVisibility(View.GONE);
linearLayout.addView(result);
super.onPostExecute(result);
}
}
}
可以见得,这里通过了建立了一个内部类的匿名对象来调用execute方法执行AsyncTask里的内容
而这个内部类继承了AsyncTask需要传入几个参数,重写几个方法
查看AsyncTask源码,可以看到它的形参是AsyncTask<Params, Progress, Result>
? Params代表着启动任务执行的输入参数的类型,在这里,直接启动不需要任务执行则为void
? Progress代表着后台完成的进度条类型,这里是int的包装类
? Result是结束后返回的类型,返回给了线性布局
参数解决了,接下来是方法,这里重写了四个方法,分别是onPreExecute,doInBackground,onProgressUpdate和onPostExecute
? onPreExecute指的是在线程启动前被调用,里面写一些初始化的方法,因为这里使用的是xml的progressbar,所以可以不用重写这个方法(自带的propressbar看不清,实在是太小了)
? doInBackground在AsyncTask中是abstract方法,一定要被实现,它的内容是后台线程将要完成的任务。这里的任务就是循环图片数组,然后放进imageview中,每放一张sleep一段时间,但是这个过程需要被观察到,于是就要通过publishProgress(i);来更新进度条
? onProgressUpdate就是每次publishProgress(i)来执行的代码,每次更新就更新进度条进度
? onPostExecute是线程完成时自动启用的方法,这里的进度条完成后将进度条给取消显示,接着显示图片内容
最后通过new MyTack().execute();来执行这四个步骤方法完成显示
需要注意的是,异步任务只能被执行一次
不过这个进度条是在标题栏外面的,如果想让标题栏在进度条里面需要用到自定义标题栏
写一个自定义的标题xml,把之前另外一个线性布局的进度条剪贴过来
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="定制的标题栏"
android:textStyle="bold"
android:textColor="#FFFF0000"
/>
<ProgressBar
android:id="@+id/bartest"
android:layout_width="match_parent"
android:layout_height="wrap_content"
style="?android:attr/progressBarStyleHorizontal"
android:max="100"/>
</LinearLayout>
需要自定义一下主题还有在清单文件里更改主题
<?xml version="1.0" encoding="utf-8"?>
<resources>
<style name="TitleBackgroundColor">
<item name="android:background">#00BFFF</item>
</style>
<style name="titlestyle" parent="android:Theme" >
<item name="android:windowTitleSize">40dip</item>
<item name="android:windowTitleBackgroundStyle">@style/TitleBackgroundColor</item>
</style>
</resources>
android:theme="@style/titlestyle" >
java更改如下代码即可
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
requestWindowFeature(Window.FEATURE_CUSTOM_TITLE);
setContentView(R.layout.test1);
getWindow().setFeatureInt(Window.FEATURE_CUSTOM_TITLE,R.layout.title);
linearLayout = findViewById(R.id.linearlayout);
progressBar = findViewById(R.id.bartest);
new MyTack().execute();
}
3.拖动条和星级评分条SeekBar RatingBar
拖动条的xml和java代码如下
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<SeekBar
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="@+id/seekbar"
android:max="100"
android:padding="20dp"
/>
<TextView
android:id="@+id/info1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="提示信息1"
android:textSize="20dp"/>
<TextView
android:id="@+id/info2"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="提示信息2"
android:textSize="20dp"/>
</LinearLayout>
package com.thundersoft.chapter2;
import android.app.Activity;
import android.os.Bundle;
import android.widget.SeekBar;
import android.widget.TextView;
import androidx.annotation.Nullable;
import com.thundersoft.session1.R;
public class SeekRatingBarActivity extends Activity {
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.seekratingbar);
SeekBar seekBar=findViewById(R.id.seekbar);
TextView info1=findViewById(R.id.info1);
TextView info2=findViewById(R.id.info2);
seekBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
@Override
public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
String s = String.valueOf(progress);
info1.setText(s);
}
@Override
public void onStartTrackingTouch(SeekBar seekBar) {
info2.setText("开始滑动");
}
@Override
public void onStopTrackingTouch(SeekBar seekBar) {
info2.setText("停止滑动");
}
});
}
}
Seekbar空间的监听器方法需要重写三个方法
值得注意的是Textview里不能传入int否则会报错,需要转换为Sring类型
星级评分条xml如下
<RatingBar
android:id="@+id/ratingbar"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:isIndicator="false"
android:numStars="5"
android:rating="3.5" />
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="提交"
android:id="@+id/submit"/>
nubStars为星星数量,rating是初始星星,isindicator设置为false表示可以更改
RatingBar ratingBar = findViewById(R.id.ratingbar);
Button submit = findViewById(R.id.submit);
submit.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
ratingBar.setStepSize(1);
float rating = ratingBar.getRating();
String s1 = String.valueOf((int)rating);
Toast.makeText(SeekRatingBarActivity.this, s1, Toast.LENGTH_SHORT).show();
}
});
注意转换为String
另外ratingBar还有getProgress获取进度方法,getStepSize获取每个最少改变多少个星级
ratingBar.setStepSize(1);可以放在oncreate当中
4.选项卡TabHost
tabhost的xml有几点需要注意
<?xml version="1.0" encoding="utf-8"?>
<TabHost xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:orientation="vertical"
android:id="@android:id/tabhost"
android:layout_height="match_parent">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<TabWidget
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="@android:id/tabs"/>
<FrameLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="@android:id/tabcontent"/>
</LinearLayout>
</TabHost>
TabHost作为总标签,且TabHost和TabWidget与FrameLayout的id必须固定,且一定要是@android的这种写法
java代码如下
package com.thundersoft.chapter2;
import android.app.Activity;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.widget.TabHost;
import androidx.annotation.Nullable;
import com.thundersoft.session1.R;
public class TableHostActivity extends Activity {
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.tabhost);
TabHost tabhost = findViewById(android.R.id.tabhost);
tabhost.setup();
LayoutInflater from = LayoutInflater.from(this);
from.inflate(R.layout.tab1,tabhost.getTabContentView());
from.inflate(R.layout.tab2,tabhost.getTabContentView());
tabhost.addTab(tabhost.newTabSpec("tab1")
.setIndicator("第一个页面")
.setContent(R.id.l1));
tabhost.addTab(tabhost.newTabSpec("tab2")
.setIndicator("第二个页面")
.setContent(R.id.l2));
}
}
其中,tab1和tab2是两个页面中的xml文件,l1和l2是这两个xml的布局id
5.图像切换器ImageSwitche
图像切换器需要建立图像工厂,xml文件如下
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<ImageSwitcher
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="@+id/imageswitcher"/>
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content">
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="上一张"
android:id="@+id/before"/>
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="下一张"
android:id="@+id/after"/>
</LinearLayout>
</LinearLayout>
java代码如下
package com.thundersoft.chapter2;
import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.view.ViewGroup;
import android.view.animation.AnimationUtils;
import android.widget.Button;
import android.widget.ImageSwitcher;
import android.widget.ImageView;
import android.widget.ViewSwitcher;
import androidx.annotation.Nullable;
import com.thundersoft.session1.R;
public class ImageSwitcherActivity extends Activity {
int index = 0;
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
int[] image = new int[]{R.drawable.jpg1,R.drawable.jpg2,R.drawable.jpg3,R.drawable.jpg4,R.drawable.jpg5};
super.onCreate(savedInstanceState);
setContentView(R.layout.imageswitcher);
ImageSwitcher imageSwitcher = findViewById(R.id.imageswitcher);
imageSwitcher.setInAnimation(AnimationUtils.loadAnimation(ImageSwitcherActivity.this, android.R.anim.fade_in));
imageSwitcher.setOutAnimation(AnimationUtils.loadAnimation(ImageSwitcherActivity.this, android.R.anim.fade_out));
imageSwitcher.setFactory(
new ViewSwitcher.ViewFactory() {
@Override
public View makeView() {
ImageView imageView = new ImageView(ImageSwitcherActivity.this);
imageView.setScaleType(ImageView.ScaleType.FIT_CENTER);
imageView.setLayoutParams(new ImageSwitcher.LayoutParams(
ViewGroup.LayoutParams.WRAP_CONTENT,ViewGroup.LayoutParams.WRAP_CONTENT
));
return imageView;
}
}
);
imageSwitcher.setImageResource(image[index]);
Button before = findViewById(R.id.before);
Button after = findViewById(R.id.after);
before.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (index > 0 ){
index --;
}else {
index = image.length - 1;
}
imageSwitcher.setImageResource(image[index]);
}
});
after.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (index < image.length - 1 ){
index ++;
}else {
index = 0;
}
imageSwitcher.setImageResource(image[index]);
}
});
}
}
优先定义image的图片数组,以及一个为0的index坐标,找到imageSwitcher的id并且新建对象,设置它的渐入渐出的动画
并且设置它的工厂对象,新建一个ViewFactory的工厂对象重写makeView方法,在方法里实例化一个imageview对象,为这个对象设置位置的大小,并返回
设置默认显示的图片,并且设置点击事件,每一次点击重设显示图像功能
6.网格视图GridView
网格视图有以下xml属性
android:columnWidth用于设置每一列的宽度
android:verticalSpacing/horizontalSpacing用于设置各元素之间的垂直/水平间距
android:numColumns设置列数,通常大于一,如果为一建议使用ListView
android:stretchMode设置拉伸模式
? none不拉伸
? spacingWidth仅拉伸元素之间的间距
? columnWidth仅拉伸表格元素本身
? spacingWidthUniform表格元素本身和元素之间的间距一起拉伸
演示xml如下
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent">
<GridView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:stretchMode="columnWidth"
android:numColumns="3"
android:id="@+id/gridview"/>
</LinearLayout>
同时还要设置每一个格子的view
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent">
<ImageView
android:layout_width="150dp"
android:layout_height="150dp"
android:id="@+id/imageview"
android:scaleType="fitXY"
android:paddingLeft="10px"
/>
<TextView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:padding="5px"
android:layout_gravity="center"
android:id="@+id/titleview"/>
</LinearLayout>
java代码如下
package com.thundersoft.chapter2;
import android.app.Activity;
import android.os.Bundle;
import android.widget.GridView;
import android.widget.SimpleAdapter;
import androidx.annotation.Nullable;
import com.thundersoft.session1.R;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;
public class GridViewActivity extends Activity {
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.gridview);
GridView gridView = findViewById(R.id.gridview);
int[] image = new int[]{R.drawable.jpg1,R.drawable.jpg2,R.drawable.jpg3,R.drawable.jpg4,R.drawable.jpg5};
String[] title = {"头像1", "头像2", "头像3", "头像4", "头像5"};
ArrayList<Map<String, Object>> list = new ArrayList<>();
for (int i = 0; i < title.length; i++) {
HashMap<String, Object> map = new HashMap<>();
map.put("imageview",image[i]);
map.put("titleview",title[i]);
list.add(map);
}
SimpleAdapter simpleAdapter = new SimpleAdapter(this,
list,
R.layout.items,
new String[]{"titleview", "imageview"},
new int[]{R.id.titleview, R.id.imageview});
gridView.setAdapter(simpleAdapter);
}
}
使用simpleAdapter适配器配置图片和文字,以上内容见上一篇的列表视图的适配器解释
也可以使用BaseAdapter适配器
BaseAdapter baseAdapter = new BaseAdapter(){
@Override
public int getCount() {
return image.length;
}
@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) {
ImageView imageView;
if (convertView==null){
imageView = new ImageView(com.thundersoft.chapter2.GridViewActivity.this);
imageView.setScaleType(ImageView.ScaleType.CENTER_INSIDE);
imageView.setPadding(5,0,5,0);
}else {
imageView=(ImageView) convertView;
}
imageView.setImageResource(image[position]);
return imageView;
}
};
gridView.setAdapter(baseAdapter);
通过new一个BaseAdapter对象,重写其中的方法
getView方法中,如果convertView为空的话,就是这imageview,为它设置缩放方式和内边距,并且设置显示图片
getItemId是获得当前选项id的方法
getItem是获得当前选项的方法
getCount是获得当前数量方法
也就是说,BaseAdapter自己通过java代码的方式新建了每一个网格布局
7.画廊视图Gallery
画廊视图有点类似于一个看图片的软件,可以左右切换,它有一下主要的xml属性
android:animationDuration用于设置列表项切换时的动画时间
android:spacing用于设置列表项之间的间距
android:unselectedAlpha用于设置没有选中的列表项的透明度
示例xml如下
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent">
<Gallery
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="@+id/gallery"
android:spacing="20px"
android:unselectedAlpha="0.3"
/>
</LinearLayout>
java代码如下
package com.thundersoft.chapter2;
import android.app.Activity;
import android.content.res.TypedArray;
import android.os.Bundle;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AdapterView;
import android.widget.BaseAdapter;
import android.widget.Gallery;
import android.widget.GridLayout;
import android.widget.ImageView;
import android.widget.Toast;
import androidx.annotation.Nullable;
import com.thundersoft.session1.R;
public class GalleryActivity extends Activity {
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.gallery);
int[] image = new int[]{R.drawable.jpg1,R.drawable.jpg2,R.drawable.jpg3,R.drawable.jpg4,R.drawable.jpg5};
Gallery gallery = findViewById(R.id.gallery);
BaseAdapter baseAdapter = new BaseAdapter(){
@Override
public int getCount() {
return image.length;
}
@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) {
ImageView imageView;
if (convertView==null){
imageView = new ImageView(com.thundersoft.chapter2.GalleryActivity.this);
imageView.setScaleType(ImageView.ScaleType.FIT_XY);
imageView.setPadding(5,0,5,0);
imageView.setLayoutParams(new Gallery.LayoutParams(400,350));
TypedArray typedArray = obtainStyledAttributes(R.styleable.Gallery);
imageView.setBackgroundResource(typedArray.getResourceId(
R.styleable.Gallery_android_galleryItemBackground,0
));
}else {
imageView=(ImageView) convertView;
}
imageView.setImageResource(image[position]);
return imageView;
}
};
gallery.setAdapter(baseAdapter);
gallery.setSelection(image.length/2);
gallery.setOnItemClickListener(new AdapterView.OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
Toast.makeText(GalleryActivity.this, String.valueOf(position+1), Toast.LENGTH_SHORT).show();
}
});
}
}
这里使用的baseAdapter和网格视图的相同,不过新增了几个设置,setLayoutParams可以设置imageView的宽高,typeArray可以指定它的样式,需要在values里新建attr.xml
<?xml version="1.0" encoding="utf-8"?>
<resources>
<declare-styleable name="Gallery">
<attr name="android:galleryItemBackground"/>
</declare-styleable>
</resources>
另外,gallery不要忘记了配置适配器和选中的图片,这里选择的中间的图片
画廊视图可以和图像切换器结合做成幻灯片选择播放
还是得通过imageSwitcher.setFactory的方法初始化is,通过gallery.setAdapter(baseAdapter);的方式初始化gallery
最后设置
gallery.setOnItemClickListener(new AdapterView.OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
imageSwitcher.setImageResource(image[position]);
}
});
效果如下
|