国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 系統 > Android > 正文

利用Android中BitmapShader制作自帶邊框的圓形頭像

2019-12-12 05:18:20
字體:
來源:轉載
供稿:網友

效果如下:

BitmapShader 的簡單介紹

關于 Shader是什么,Shader的種類有哪幾種以及如何使用不屬于本文范疇,對這方面不是很了解的同學,建議先去學習一下 Shader 的基本使用。

BitmapShader主要的作用就是 通過Paint對象,對 畫布進行指定的Bitmap填充,實現一系列效果,可以有以下三種模式進行選擇

      1.CLAMP - 拉伸,這里拉伸的是圖片的最后一個元素,不斷地重復,這個效果,在圖片比較小,而所要畫的面積比較大的時候會比較明顯。

      2.REPEAT - 重復,橫向縱向不斷地重復,不同于上一模式,這種模式在圖片比較小不能滿足要求是,會在橫向縱向不斷重復繪制圖形。

      3.MIRROR - 翻轉,這種模式和 REPEAT 是類似的,只不過這里的重復是翻轉著重復,和折紙的效果差不多。

而我們將要使用的是 CLAMP 模式,因為只要我們對圖形的大小進行控制,就可以避免圖像進行拉伸。

具體實現介紹

為了自定義 圖像,邊框寬度和顏色,我們首先在 res/values 目錄下,新建一個 attrs.xml文件,里面要書寫的內容如下所示

<?xml version="1.0" encoding="utf-8"?><resources> <declare-styleable name="MyCustomView">  <attr name="mborder_color" format="color"></attr>  <attr name="mborder_width" format="dimension"></attr>  <attr name="msrc" format="reference"></attr> </declare-styleable></resources>

當然,在這里還可以添加一些其他的特性。既然定義了我們想要使用的特性,那么我們就要在自定義View里面 解析這些屬性并且加以利用,解析過程如下所示

 TypedArray type = context.obtainStyledAttributes(attrs, R.styleable.MyCustomView); mBorderColor = type.getColor(R.styleable.MyCustomView_mborder_color,0); mDrawable = type.getDrawable(R.styleable.MyCustomView_msrc); //將獲得的 Drawable 轉換成 Bitmap BitmapDrawable bitmapDrawable = (BitmapDrawable) mDrawable; mBitmap = bitmapDrawable.getBitmap(); mBorderWidth = type.getDimensionPixelSize(R.styleable.MyCustomView_mborder_width, 2);

值得注意的是 mSrc 屬性的解析,由于獲得是 Drawable 對象,所以我們需要將其轉換為 Bitmap 對象。

下面就利用我們獲得的 Bitmap 對象進行圓形頭像的繪制,對 BitmapShader Paint 的初始化如下所示

  mSrcBitmap = Bitmap.createScaledBitmap(mBitmap, mWidth, mHeight, false);  mShader = new BitmapShader(mSrcBitmap, Shader.TileMode.CLAMP, Shader.TileMode.CLAMP);  mPaint = new Paint();  mPaint.setShader(mShader);  mRadius = (mWidth - mBorderWidth * 2 - 4) / 2;  mCircleX = (mWidth) / 2;  mCircleY = (mHeight) / 2;

mSrcBitmap是對獲得的圖像進行適當的縮小或者放大,以適應我們對圖形的要求,而這里的 mWidth mHeight 又是什么呢?實際上就是我們在 定義視圖在 layout_width layout_height中傳遞進來的值,不過在這里我對他們進行了處理,也就是選取最小值操作,這樣的話就可以避免由于寬大于高或者高大于寬而造成圖像填充不滿指定區域的現象。值得注意的是,自定義視圖,需要對 wrap_content 進行特殊處理,否則系統對該屬性的視圖不予以顯示。至于如何進行處理,可以看看本例的源碼,很簡單,相信很多人一看就知道或者說早就了然于胸。

還有一點需要強調的是這里的 mRadius ,也就是將要繪制的圓的半徑,為什么要減去邊框的寬度 乘 2 呢? 要知道,我們的圓是根據 視圖指定的寬度或者高度來畫的,如果我們所畫 的圓恰好是指定視圖的內切圓,那么邊框放在哪里呢?它肯定要被畫在視圖的外面,那樣我們就看不到完整的邊框了。所以,這么減去的意義在于為邊框騰出空間。

經過以上操作,我們就已經將圓形頭像繪制出來了,下面來繪制邊框,其實非常簡單,我只不過是又定義了一個  Paint 對象,并且利用它畫了一個圓而已,畫筆的初始化操作如下所示

  mBorderPaint = new Paint();  mBorderPaint.setStyle(Paint.Style.STROKE);  mBorderPaint.setStrokeWidth(mBorderWidth);  mBorderPaint.setColor(mBorderColor);  mBorderPaint.setStrokeCap(Paint.Cap.ROUND);

好了,下面就可以在onDraw()函數中,進行繪制了,如下所示

 @Override protected void onDraw(Canvas canvas) {  super.onDraw(canvas);  canvas.drawCircle(mCircleX, mCircleY, mRadius, mPaint);  canvas.drawCircle(mCircleX, mCircleY, mRadius, mBorderPaint); }

這樣,整個效果就算實現完畢了。下面來看看如何使用

 <com.example.hwaphon.patheffecttest.MyView   android:layout_width="wrap_content"   android:layout_height="wrap_content"   android:layout_marginBottom="16dp"   android:layout_marginRight="8dp"   app:mborder_color="@android:color/holo_green_light"   app:mborder_width="4dp"   app:msrc="@drawable/myview_test"/>

注意,一定要在容器中加上這么一句

具體實現的核心代碼

package com.example.hwaphon.patheffecttest;import android.content.Context;import android.content.res.TypedArray;import android.graphics.Bitmap;import android.graphics.BitmapShader;import android.graphics.Canvas;import android.graphics.Paint;import android.graphics.Shader;import android.graphics.drawable.BitmapDrawable;import android.graphics.drawable.Drawable;import android.util.AttributeSet;import android.view.View;/** * Created by Hwaphon on 2016/5/12. */public class MyView extends View { private Bitmap mBitmap; private Drawable mDrawable; private Bitmap mSrcBitmap; private BitmapShader mShader; private Paint mPaint; private int mWidth, mHeight; private int mRadius; private int mCircleX, mCircleY; private int mBorderColor; private Paint mBorderPaint; private int mBorderWidth; public MyView(Context context) {  this(context, null); } public MyView(Context context, AttributeSet attrs) {  super(context, attrs);  TypedArray type = context.obtainStyledAttributes(attrs, R.styleable.MyCustomView);  mBorderColor = type.getColor(R.styleable.MyCustomView_mborder_color,0);  mDrawable = type.getDrawable(R.styleable.MyCustomView_msrc);  //將獲得的 Drawable 轉換成 Bitmap  BitmapDrawable bitmapDrawable = (BitmapDrawable) mDrawable;  mBitmap = bitmapDrawable.getBitmap();  mBorderWidth = type.getDimensionPixelSize(R.styleable.MyCustomView_mborder_width, 2); } @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {  super.onMeasure(widthMeasureSpec, heightMeasureSpec);  mWidth = measureWidth(widthMeasureSpec);  mHeight = measureHeight(heightMeasureSpec);  int temp = mWidth > mHeight ? mHeight : mWidth;  mWidth = mHeight = temp;  initView();  setMeasuredDimension(mWidth, mHeight); } private int measureHeight(int heightMeasureSpec) {  int size = MeasureSpec.getSize(heightMeasureSpec);  int sizeMode = MeasureSpec.getMode(heightMeasureSpec);  int result = 0;  if (sizeMode == MeasureSpec.EXACTLY) {   result = size;  } else {   result = 200;   if (sizeMode == MeasureSpec.AT_MOST) {    result = Math.min(result, size);   }  }  return result; } private int measureWidth(int widthMeasureSpec) {  int size = MeasureSpec.getSize(widthMeasureSpec);  int sizeMode = MeasureSpec.getMode(widthMeasureSpec);  int result = 0;  if (sizeMode == MeasureSpec.EXACTLY) {   result = size;  } else {   result = 200;   if (sizeMode == MeasureSpec.AT_MOST) {    result = Math.min(result, size);   }  }  return result; } private void initView() {  mSrcBitmap = Bitmap.createScaledBitmap(mBitmap, mWidth, mHeight, false);  mShader = new BitmapShader(mSrcBitmap, Shader.TileMode.CLAMP, Shader.TileMode.CLAMP);  mPaint = new Paint();  mPaint.setShader(mShader);  mRadius = (mWidth - mBorderWidth * 2) / 2;  mCircleX = (mWidth) / 2;  mCircleY = (mHeight) / 2;  mBorderPaint = new Paint();  mBorderPaint.setStyle(Paint.Style.STROKE);  mBorderPaint.setStrokeWidth(mBorderWidth);  mBorderPaint.setColor(mBorderColor);  mBorderPaint.setStrokeJoin(Paint.Join.ROUND);  mBorderPaint.setStrokeCap(Paint.Cap.ROUND); } @Override protected void onDraw(Canvas canvas) {  super.onDraw(canvas);  canvas.drawCircle(mCircleX, mCircleY, mRadius, mPaint);  canvas.drawCircle(mCircleX, mCircleY, mRadius, mBorderPaint); }}

總結

以上就是Android利用BitmapShader制作自帶邊框圓形頭像的全部內容,希望這篇文章對大家開發Android的時候能有所幫助,如果有疑問大家可以留言交流。

發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
主站蜘蛛池模板: 上思县| 庆安县| 青川县| 杭州市| 涿州市| 西和县| 雅江县| 宜州市| 玛多县| 祥云县| 凤庆县| 石棉县| 上思县| 顺平县| 托里县| 庆阳市| 铜鼓县| 丰宁| 霍林郭勒市| 乌兰县| 香河县| 朝阳市| 邛崃市| 玉门市| 巴中市| 老河口市| 沙坪坝区| 阿拉善左旗| 雷山县| 思南县| 黎川县| 永靖县| 潜江市| 内江市| 交城县| 吴忠市| 弥渡县| 揭西县| 红河县| 会东县| 诏安县|