解決使用Skia圖形庫時遇到的幾個問題


  Skia是一個開源的2D圖形庫,提供通用的API,適用於工作中遇到的各種硬件和軟件平台。這是谷歌瀏覽器Chrome OS,Android的圖形引擎,Mozilla Firefox瀏覽器和Firefox OS,和許多其他產品。

  官方網站:https://skia.org/

  編譯及配置方法可以參考Skia簡介以及在Windows下編譯操作步驟。注意Windows下還需要添加鏈接庫:windowscodecs.lib usp10.lib以及需要添加一些預定義。

  簡單說一下我在用的時候遇到的幾個坑。

1. 畫任意曲線時,需要設置SkPaint的style,這個比較坑,找了好久,發現需要設置一下風格,否則使用SkPath類的moveTo()和lineTo()之后,畫出的任意曲線是填充過的。這個跟Qt或者其他圖形引擎不大相同。

    SkPaint paint;
    paint.setStyle(SkPaint::kStroke_Style);

2. 畫一張帶有透明背景的圖片,alpha和rgb是4個字節,設置alpha值為0,填充后的圖片即是透明的,之后再畫一張bitmap即可。

    SkCanvas canvas(new SkDevice(bitmap));
    canvas.clear(0x00000000);

3. 注意2的例子是網上好多人寫的,項目中用的時候發現內存泄漏的問題,new SkDevice改成棧上的就OK了。

簡單例子:

#include "stdafx.h"
#include "SkBitmap.h"
#include "SkDevice.h"
#include "SkPaint.h"
#include "SkRect.h"
#include "SkImageEncoder.h"
#include "SkTypeface.h"
#include "SkCanvas.h"

#pragma comment(lib,"core.lib")
#pragma comment(lib,"images.lib")
#pragma comment(lib,"ports.lib")
#pragma comment(lib,"opts.lib")
#pragma comment(lib,"utils.lib")

const char *pText = "Hello world!";

int _tmain(int argc, _TCHAR* argv[])
{
    const int width = 1024;
    const int height = 768;

    SkBitmap bitmap;
    SkPath path;
    
    SkPaint paint;
    paint.setStyle(SkPaint::kStroke_Style);
    paint.setColor(0xff1f78b4);
    paint.setStrokeWidth(8);

    bitmap.setConfig(SkBitmap::kARGB_8888_Config,width,height);
    bitmap.allocPixels();

    SkCanvas canvas(new SkDevice(bitmap));
    canvas.clear(0x00000000);// 背景為透明色

    {
        SkRect rc;
        rc.fLeft = 123;
        rc.fTop = 0;
        rc.fRight = 222;
        rc.fBottom = 50;
        canvas.drawOval(rc, paint);
    }

    {
        paint.setARGB(255, 255, 0, 0);
        paint.setTextSize(50);
        canvas.drawText(pText, strlen(pText), 500, 500, paint);
    }

    {
        paint.setColor(SK_ColorYELLOW);
        canvas.drawCircle(100, 100, 50, paint);
    }

    {
        SkPaint paint1, paint2, paint3;

        paint1.setTextSize(64.0f);
        paint1.setAntiAlias(true);
        paint1.setColor(0xff4281A4);
        paint1.setStyle(SkPaint::kFill_Style);

        paint2.setTextSize(64.f);
        paint2.setAntiAlias(true);
        paint2.setColor(0xff9CAFB7);
        paint2.setStyle(SkPaint::kStroke_Style);
        paint2.setStrokeWidth(SkIntToScalar(3));

        paint3.setTextSize(64.0f);
        paint3.setAntiAlias(true);
        paint3.setColor(0xffE6B89C);
        paint3.setTextScaleX(SkFloatToScalar(1.5f));

        const char text[] = "jiayayao@126.com";
        canvas.drawText(text, strlen(text), 200.0f, 64.0f,  paint1);
        canvas.drawText(text, strlen(text), 200.0f, 144.0f, paint2);
        canvas.drawText(text, strlen(text), 200.0f, 224.0f, paint3);
    }

    SkImageEncoder::EncodeFile("testSkia.png", bitmap,SkImageEncoder::kPNG_Type,100);

    return 0;
}

  Skia一個大的優勢是跨平台,比如在Windows平台可以用Direct3D圖形API或者Gdiplus負責底層實現,用Skia在上層繪圖,這樣繪圖邏輯基本可以不用修改,直接將bitmap的指針(char*)bitmap.getAddr32(0, 0)交給D3D繪制即可。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM