Android截屏SurfaceView黑屏問(wèn)題的解決辦法
最近項(xiàng)目中有截屏的需求,普通的view截屏方法網(wǎng)上一搜一大把,但是SurfaceView截屏黑屏問(wèn)題很多文章說(shuō)的并不清楚,自己參考了一些別的博客,再加上自己的思考,算是找到了一種解決方案。
1、首先看我們一般是怎么用SurfaceView的
public class SuperSurfaceView extends SurfaceView implements SurfaceHolder.Callback {
SurfaceHolder surfaceHolder;
public SuperSurfaceView(Context context) {
super(context);
surfaceHolder = this.getHolder();
surfaceHolder.addCallback(this);
}
@Override
public void surfaceChanged(SurfaceHolder holder, int format, int width,
int height) {
}
@Override
public void surfaceCreated(SurfaceHolder holder) {
new Thread(new MyThread()).start();
}
@Override
public void surfaceDestroyed(SurfaceHolder holder) {
}
class MyThread implements Runnable {
@Override
public void run() {
Canvas canvas = surfaceHolder.lockCanvas(null);//獲取畫(huà)布
Paint mPaint = new Paint();
mPaint.setColor(Color.BLUE);
canvas.drawRect(new RectF(100, 100, 1000, 550), mPaint);
surfaceHolder.unlockCanvasAndPost(canvas);//解鎖畫(huà)布,提交畫(huà)好的圖像
}
}
}
從以上代碼中,可以看到在MyThread的run方法中創(chuàng)建了一塊畫(huà)布,進(jìn)行SurfaceView的繪制,但是我們知道SurfaceView是雙緩沖機(jī)制,這個(gè)Canvas上的內(nèi)容我們拿不到,所以截屏出來(lái)是黑屏。所以,要拿到這個(gè)畫(huà)布上的內(nèi)容,就自己創(chuàng)建一個(gè)畫(huà)布,將這些內(nèi)容畫(huà)到自己的Canvas上,就可以了。
2、拿到SurfaceView畫(huà)布上的bitmap,看修改過(guò)后的代碼
public abstract class SuperSurfaceView extends SurfaceView implements SurfaceHolder.Callback {
SurfaceHolder surfaceHolder;
public SuperSurfaceView(Context context) {
super(context);
surfaceHolder = this.getHolder();
surfaceHolder.addCallback(this);
}
@Override
public void surfaceChanged(SurfaceHolder holder, int format, int width,
int height) {
}
@Override
public void surfaceCreated(SurfaceHolder holder) {
new Thread(new MyThread()).start();
}
@Override
public void surfaceDestroyed(SurfaceHolder holder) {
}
class MyThread implements Runnable {
@Override
public void run() {
Canvas canvas = surfaceHolder.lockCanvas(null);//獲取畫(huà)布
doDraw(canvas);
surfaceHolder.unlockCanvasAndPost(canvas);//解鎖畫(huà)布,提交畫(huà)好的圖像
}
}
//將繪制圖案的方法抽象出來(lái),讓子類(lèi)實(shí)現(xiàn),調(diào)用getBitmap方法時(shí)就會(huì)調(diào)用此方法
protected abstract void doDraw(Canvas canvas);
//調(diào)用該方法將doDraw繪制的圖案繪制在自己的canvas上
public Bitmap getBitmap() {
Bitmap bitmap = Bitmap.createBitmap(getWidth(), getHeight(), Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(bitmap);
doDraw(canvas);
return bitmap;
}
}
3、下面看MainActivity中如何使用
Button bt = (Button) findViewById(R.id.bt);
FrameLayout fl = (FrameLayout) findViewById(R.id.fl);
//用到surfaceview需繼承SuperSurfaceView才能截到屏,否則截出來(lái)是黑屏
SuperSurfaceView surfaceView = new SuperSurfaceView(this) {
@Override
protected void doDraw(Canvas canvas) {
Paint mPaint = new Paint();
mPaint.setColor(Color.BLUE);
canvas.drawRect(new RectF(100, 100, 1000, 550), mPaint);
}
};
fl.addView(surfaceView);
bt.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
//調(diào)用該方法即可得到surfaceview上繪制的圖案
Bitmap bitmap = surfaceView.getBitmap();
}
});
補(bǔ)充:如果界面上還有其他控件需要一起截屏,可以將截到的surfaceview的bitmap和用普通辦法截到的不含surfaceview的bitmap拼接起來(lái)就OK了,至于兩個(gè)bitmap合為一個(gè)bitmap的方法,百度一下有很多,不再贅述。
以上就是本文的全部?jī)?nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
相關(guān)文章
Android自定義View實(shí)現(xiàn)縱向跑馬燈效果詳解
對(duì)于跑馬燈效果在我們?nèi)粘J褂玫腶pp中還是很常見(jiàn)的,比如外賣(mài)app的商家公告就使用了此效果,但是它是橫向滾動(dòng)的,橫向滾動(dòng)多適用于單條信息;但凡涉及到多條信息的滾動(dòng)展示,用縱向滾動(dòng)效果會(huì)有更好的用戶(hù)體驗(yàn),今天我們通過(guò)自定義View來(lái)看看如何實(shí)現(xiàn)縱向跑馬燈效果。2016-11-11
在RecyclerView中實(shí)現(xiàn)button的跳轉(zhuǎn)功能
本次實(shí)驗(yàn)就是在RecyclerView中添加一個(gè)button控件并實(shí)現(xiàn)監(jiān)聽(tīng),使鼠標(biāo)點(diǎn)擊時(shí)可以跳轉(zhuǎn)到另外一個(gè)設(shè)計(jì)好的界面,對(duì)RecyclerView實(shí)現(xiàn)button跳轉(zhuǎn)功能感興趣的朋友一起看看吧2021-10-10
仿iPhone風(fēng)格對(duì)話框(附件包含例子/jar包/jar包源碼)
這個(gè)對(duì)框完全繼承、仿照AlertDialog,只是實(shí)現(xiàn)了自定義效果;另外,沒(méi)有實(shí)現(xiàn)setIcon,因?yàn)閕phone中的對(duì)話框多數(shù)都沒(méi)有圖標(biāo);附件包含例子、jar包、jar包源碼2013-01-01
Android手機(jī)開(kāi)發(fā) 控件 TextView文字居中
本文主要介紹Android手機(jī)開(kāi)發(fā)TextView居中的方法,希望能幫到大家。2016-05-05
Android開(kāi)發(fā)之自定義View(視圖)用法詳解
這篇文章主要介紹了Android開(kāi)發(fā)之自定義View(視圖)用法,結(jié)合實(shí)例形式分析了Android自定義視圖的實(shí)現(xiàn)方法與使用注意事項(xiàng),需要的朋友可以參考下2016-10-10
Android Studio編寫(xiě)AIDL文件后如何實(shí)現(xiàn)自動(dòng)編譯生成
這篇文章主要介紹了Android Studio編寫(xiě)AIDL文件后如何實(shí)現(xiàn)自動(dòng)編譯生成,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧2020-03-03
Android P實(shí)現(xiàn)靜默安裝的方法示例(官方Demo)
這篇文章主要介紹了Android P實(shí)現(xiàn)靜默安裝,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2020-02-02
Flutter使用Overlay與ColorFiltered新手引導(dǎo)實(shí)現(xiàn)示例
這篇文章主要介紹了Flutter使用Overlay與ColorFiltered新手引導(dǎo)實(shí)現(xiàn)示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2022-10-10

