之前开发项目的时候一直没有做更换头像这一块,因为开发的东西很少有需要用户进行登录的,最近比较闲,记录一下修改头像这一块,
就不说需求了 看图
场景很简单,也符合更换头像的需求
描述:点击头像 ,弹出菜单 选择拍照、相册选择、取消
使用语言kotlin 语言 菜单使用popupWindow ,先上菜单布局
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#55555555">
<TextView
android:id="@+id/photograph"
android:layout_width="match_parent"
android:layout_height="45dp"
android:layout_above="@+id/line"
android:layout_marginLeft="10dp"
android:layout_marginRight="10dp"
android:background="@drawable/setting_up_selector"
android:gravity="center"
android:text="拍照"
android:textColor="#0479FE"
android:textSize="18sp" />
<TextView
android:id="@+id/line"
android:layout_width="match_parent"
android:layout_height="0.1dp"
android:layout_above="@+id/albums"
android:layout_marginLeft="10dp"
android:layout_marginRight="10dp"
android:background="#D9D8D3" />
<TextView
android:id="@+id/albums"
android:layout_width="match_parent"
android:layout_height="45dp"
android:layout_above="@+id/cancel"
android:layout_marginLeft="10dp"
android:layout_marginRight="10dp"
android:background="@drawable/setting_down_selector"
android:gravity="center"
android:text="从相册选择"
android:textColor="#0479FE"
android:textSize="18sp" />
<LinearLayout
android:id="@+id/cancel"
android:layout_width="match_parent"
android:layout_height="45dp"
android:layout_alignParentBottom="true"
android:layout_margin="10dp"
android:background="@drawable/setting_one_selector">
<TextView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:gravity="center"
android:text="取 消"
android:textColor="#0479FE"
android:textSize="18sp" />
LinearLayout>
RelativeLayout>
这就是途中的那个布局样式
第一步、先实现点击头像弹出菜单
/**
* 展示对话框
*/
private fun showPopupWindow() {
/**
* 在这里首先说明一下popupWindow 和AlertDialog 的区别
* AlertDialog 不能显示在指定的位置 只能显示在屏幕的中间
* popupWindow 可以显示在任意的位置
*/
var layoutInflater = getSystemService(Context.LAYOUT_INFLATER_SERVICE) as LayoutInflater
if (popupWindow == null) {
var view = layoutInflater.inflate(R.layout.pop_select_photo, null)
albums = view.findViewById(R.id.albums) as TextView
cancel = view.findViewById(R.id.cancel) as LinearLayout
photograph = view.findViewById(R.id.photograph) as TextView
popupWindow = PopupWindow(view, android.app.ActionBar.LayoutParams.MATCH_PARENT,
android.app.ActionBar.LayoutParams.MATCH_PARENT, true)
initPop()
}
popupWindow?.animationStyle = android.R.style.Animation_InputMethod
popupWindow?.isFocusable = true
popupWindow?.isOutsideTouchable = true
popupWindow?.setBackgroundDrawable(BitmapDrawable())
popupWindow?.softInputMode = WindowManager.LayoutParams.SOFT_INPUT_ADJUST_RESIZE
popupWindow?.showAtLocation(mAvatar, Gravity.CENTER, 0, 0)
}
ok ,完成这一步之后,先做拍照的
/**
* 拍照
*/
private fun takePhoto() {
val intent = Intent(MediaStore.ACTION_IMAGE_CAPTURE)//android.media.action.IMAGE_CAPTURE
if (hasSdcard()) {
file = File(Environment.getExternalStorageDirectory(), PHOTO_FILE_NAME)
//从文件中创建Uri
val uri = Uri.fromFile(file)
intent.putExtra(MediaStore.EXTRA_OUTPUT, uri)
}
startActivityForResult(intent, PHOTO_REQUEST_CAMERA)
}
然后是相册选择,其实使用这个Action Android会把手机中是从图片的容器都打开让你进行选择
private fun takeGallery() {
val intent = Intent(Intent.ACTION_PICK)
intent.type = "image/*"
startActivityForResult(intent, PHOTO_REQUEST_GALLERY)
}
OK ,完成以上两步之后,我们在做裁剪图片,要设置成头像一定是要进行裁剪的,我们可以使用Android系统的裁剪,也可以使用自己定义的,我在这边为了方便就使用系统的,好的,看一下裁剪的方法
/**
* 裁剪图片
*/
private fun crop(uri: Uri?) {
val intent = Intent("com.android.camera.action.CROP")
intent.setDataAndType(uri, "image/*")
intent.putExtra("crop", "true")
//裁剪框的比例 1:1
intent.putExtra("aspectX", 1)
intent.putExtra("aspectY", 1)
//裁剪后输出的图片的尺寸的大小
intent.putExtra("outputX", 200)
intent.putExtra("outputY", 200)
//图片的格式
intent.putExtra("outputFormat", "JPEG")
//取消人脸识别
intent.putExtra("noFaceDetection", false)
intent.putExtra("return-data", true)
startActivityForResult(intent, PHOTO_REQUEST_CUT)
}
OK ,这样就完成了拍照和选择图片 、裁剪等工作,然后因该发现一个问题,上面的代码中启动Activity都是startActivityForResult 是的,我们重写
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
super.onActivityResult(requestCode, resultCode, data)
when (requestCode) {
PHOTO_REQUEST_GALLERY -> {
//从相册返回的数据
if (data != null) {
val uri = data.data
crop(uri)
}
}
PHOTO_REQUEST_CAMERA -> {
//相机返回的数据
if (hasSdcard()) {
crop(Uri.fromFile(file))
} else {
Toast.makeText(this, "没有找到存储卡", Toast.LENGTH_SHORT).show()
}
}
PHOTO_REQUEST_CUT -> {
//裁剪的图片
if (data != null) {
val bitmap: Bitmap = data.getParcelableExtra("data")
mAvatar.setImageBitmap(bitmap)
}
}
}
}
这就完成了头像的更换 当然头像现在还没有传到服务器,你只需要传到服务器就行了,在合适的位置
源码下载 https://gitee.com/kongxiaoan/codes/4hubs6t3q2kec8d7a0izp10