今天要來提提有關ViewPager與TabLayout的應用,與先前介紹過的TabLayout+Fragment有點類似,但ViewPager多了一個可以滑動切換的功能,那麼等等就來做Day5照片選取的延伸,如果還沒看過Day5的文章可以點選這裡。
與之前一樣,假如選取照片後發生錯誤,則須添加權限至Manifest中。
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
另外在UI的部分也有做了一些更動,將ImageView更換下來並加上ViewPager&TabLayout。
<androidx.constraintlayout.widget.ConstraintLayout
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"
tools:context=".MainActivity">
<Button
android:id="@+id/btn_picker"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Button"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHorizontal_bias="0.498"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintVertical_bias="0.903" />
<androidx.viewpager.widget.ViewPager
android:id="@+id/viewPager"
android:layout_width="0dp"
android:layout_height="0dp"
app:layout_constraintBottom_toTopOf="@+id/guideline"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHorizontal_bias="0.461"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintVertical_bias="0.031" />
<androidx.constraintlayout.widget.Guideline
android:id="@+id/guideline"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="horizontal"
app:layout_constraintGuide_percent="0.6" />
<androidx.constraintlayout.widget.Guideline
android:id="@+id/guideline2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="horizontal"
app:layout_constraintGuide_percent="0.72" />
<com.google.android.material.tabs.TabLayout
android:id="@+id/tabLayout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHorizontal_bias="0.0"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="@+id/guideline2"/>
</androidx.constraintlayout.widget.ConstraintLayout>
接著來設計ViewPager的調配器,首先要讓他繼承PagerAdapter並複寫四個方法:
添加完後並加入ImageView List的constructor,並開始進行設計。
public class ViewPagerAdapter extends PagerAdapter {
private List<ImageView> imgList;
public ViewPagerAdapter(@NonNull List<ImageView> imgList) {
this.imgList=imgList;
}
//實例圖片數
@Override
public int getCount() {
return imgList.size();
}
//判斷instantiateItem回的物件和view是否一樣
@Override
public boolean isViewFromObject(@NonNull View view, @NonNull Object object) {
return view==object;
}
//實例圖片
@Override
public Object instantiateItem(@NonNull ViewGroup container, int position){
ImageView imageView = imgList.get(position);
container.addView(imageView);
return imageView;
}
//移除圖片
@Override
public void destroyItem(ViewGroup container,int position, Object object){
container.removeView((View) object);
}
}
而在綁定完元件後,首先就是ViewPager及TabLayout的互相同步,會用到這兩個方法:
//...綁定(viewPager、tabLayout)
viewPager.addOnPageChangeListener(new TabLayout.TabLayoutOnPageChangeListener(tabLayout));
tabLayout.setupWithViewPager(viewPager);
接著來設計主程式:
public class MainActivity extends AppCompatActivity {
private Button btn_picker;
private ImageView imageView;
private ContentResolver resolver;
private List<ImageView> imgList;
private ViewPager viewPager;
private TabLayout tabLayout;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
imgList = new ArrayList<>();
resolver=this.getContentResolver();
tabLayout=findViewById(R.id.tabLayout);
viewPager=findViewById(R.id.viewPager);
btn_picker=findViewById(R.id.btn_picker);
btn_picker.setOnClickListener(view->{
//打開相簿
Intent intent = new Intent();
intent.setType("image/*");
intent.setAction(Intent.ACTION_GET_CONTENT);
//選擇相片後接回傳
startActivityForResult(intent, 1);
});
//將tablayout和viewpager相互綁定
viewPager.addOnPageChangeListener(new TabLayout.TabLayoutOnPageChangeListener(tabLayout));
tabLayout.setupWithViewPager(viewPager);
}
//選取照片後回傳呼叫的function
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if (resultCode == RESULT_OK) {
Uri uri = data.getData();//取得相片路徑
try {
//將該路徑的圖片轉成bitmap
Bitmap bitmap = BitmapFactory.decodeStream(resolver.openInputStream(uri));
imageView=new ImageView(this);
//設定ImageView圖片
imageView.setImageBitmap(bitmap);
imgList.add(imageView);
viewPager.setAdapter(new ViewPagerAdapter(imgList));
//選完照片後,將tab重建
tabLayout.removeAllTabs();
for(int position=0;position<imgList.size();position++) {
tabLayout.addTab(tabLayout.newTab().setText("Image"));
}
} catch (FileNotFoundException e) {
e.printStackTrace();
}
}
super.onActivityResult(requestCode, resultCode, data);
}
}