整合文字與圖形
瞭解如何判斷轉譯文字字串的大小,以整合文字與SkiaSharp圖形
本文示範如何測量文字、將文字調整為特定大小,以及將文字與其他圖形整合:
該影像也包含圓角矩形。 SkiaSharp Canvas
類別包含 DrawRect
繪製矩形的方法,以及 DrawRoundRect
繪製圓角矩形的方法。 這些方法可讓矩形定義為 SKRect
值或其他方式。
[ 框架文字 ] 頁面會在頁面上置中一個簡短的文字字串,並以由一對圓角矩形組成的框架括住它。 類別 FramedTextPage
會顯示其完成方式。
在 SkiaSharp 中 SKPaint
,您可以使用 類別來設定文字和字型屬性,但您也可以使用它來取得轉譯的文字大小。 下列 PaintSurface
事件處理程式的開頭會呼叫兩個不同的 MeasureText
方法。 第一 MeasureText
次呼叫具有簡單的 string
自變數,並根據目前的字型屬性傳回文字的圖元寬度。 然後,程式會根據呈現的SKPaint
寬度、目前的TextSize
屬性和顯示區域的寬度,計算物件的新TextSize
屬性。 此計算設定 TextSize
文字字串,以 90% 的螢幕寬度呈現:
void OnCanvasViewPaintSurface(object sender, SKPaintSurfaceEventArgs args)
{
SKImageInfo info = args.Info;
SKSurface surface = args.Surface;
SKCanvas canvas = surface.Canvas;
canvas.Clear();
string str = "Hello SkiaSharp!";
// Create an SKPaint object to display the text
SKPaint textPaint = new SKPaint
{
Color = SKColors.Chocolate
};
// Adjust TextSize property so text is 90% of screen width
float textWidth = textPaint.MeasureText(str);
textPaint.TextSize = 0.9f * info.Width * textPaint.TextSize / textWidth;
// Find the text bounds
SKRect textBounds = new SKRect();
textPaint.MeasureText(str, ref textBounds);
...
}
第二 MeasureText
個呼叫具有自 SKRect
變數,因此它會取得轉譯文字的寬度和高度。 Height
這個SKRect
值的 屬性取決於文字字串中大寫字母、遞增和子系的存在。 例如,會針對文字字串 「mom」、“cat” 和 “dog” 報告不同的 Height
值。
結構的 Left
和 Top
屬性 SKRect
會指出轉譯文字左上角的座標,如果文字是由 DrawText
具有 X 和 Y 位置 0 的呼叫所顯示。 例如,當此程式在 i 電話 7 模擬器上執行時,TextSize
會在第一次呼叫 MeasureText
之後,指派值 90.6254。 SKRect
從 第二個 呼叫MeasureText
取得的值具有下列屬性值:
Left
= 6Top
= –68Width
= 664.8214Height
= 88;
請記住,您傳遞給 DrawText
方法的 X 和 Y 座標會指定基準文字的左側。 值 Top
表示文字會擴充該基準的 68 圖元,並在基準下方減去 68 像素(從 88 減去 68 圖元)。 Left
6 的值表示文字會在呼叫中 DrawText
X 值的右邊開始六個圖元。 這允許一般字元間間距。 如果您想要在顯示左上角顯示文字,請將這些 Left
和 Top
值的負值當做 的 X 和 Y 座標 DrawText
傳遞,在此範例中為 –6 和 68。
結構 SKRect
會定義數個方便的屬性和方法,其中部分用於處理程序的 PaintSurface
其餘部分。 MidX
和 MidY
值表示矩形中央的座標。 (在 i 電話 7 範例中,這些值為 338.4107 和 –24。下列程式代碼會使用這些值來計算座標,以將顯示器上的文字置中:
void OnCanvasViewPaintSurface(object sender, SKPaintSurfaceEventArgs args)
{
...
// Calculate offsets to center the text on the screen
float xText = info.Width / 2 - textBounds.MidX;
float yText = info.Height / 2 - textBounds.MidY;
// And draw the text
canvas.DrawText(str, xText, yText, textPaint);
...
}
SKImageInfo
資訊結構也會定義 Rect
類型的SKRect
屬性,因此您也可以計算xText
並yText
如下所示:
float xText = info.Rect.MidX - textBounds.MidX;
float yText = info.Rect.MidY - textBounds.MidY;
處理程式最後 PaintSurface
會呼叫 DrawRoundRect
兩個 ,這兩個呼叫都需要 的 SKRect
自變數。 此值SKRect
是以從 MeasureText
方法取得的值為基礎SKRect
,但不能相同。 首先,它必須變大一點,讓圓角矩形不會繪製文字邊緣。 其次,它必須在空格中移位, Left
讓和 Top
值對應至矩形所在的左上角。 這兩個作業是由 所SKRect
定義的 和 Inflate
方法所完成Offset
:
void OnCanvasViewPaintSurface(object sender, SKPaintSurfaceEventArgs args)
{
...
// Create a new SKRect object for the frame around the text
SKRect frameRect = textBounds;
frameRect.Offset(xText, yText);
frameRect.Inflate(10, 10);
// Create an SKPaint object to display the frame
SKPaint framePaint = new SKPaint
{
Style = SKPaintStyle.Stroke,
StrokeWidth = 5,
Color = SKColors.Blue
};
// Draw one frame
canvas.DrawRoundRect(frameRect, 20, 20, framePaint);
// Inflate the frameRect and draw another
frameRect.Inflate(10, 10);
framePaint.Color = SKColors.DarkBlue;
canvas.DrawRoundRect(frameRect, 30, 30, framePaint);
}
接下來,方法的其餘部分是直接的。 它會為框線建立另一個 SKPaint
物件,並呼叫 DrawRoundRect
兩次。 第二個呼叫會使用另一個 10 像素擴充的矩形。 第一次呼叫會指定 20 像素的圓角半徑。 第二個角半徑為 30 像素,因此它們看起來是平行的:
您可以側邊轉手機或模擬器,以查看文字和畫面大小增加。
如果您只需要將畫面上的某些文字置中,您可以大致執行此動作,而不測量文字。 請改為將 TextAlign
的 SKPaint
屬性設定為 列舉成員 SKTextAlign.Center
。 您在 方法中指定的 DrawText
X 座標接著會指出文字的水準置中位置。 如果您將畫面 DrawText
的中間點傳遞給 方法,文字會水準置中, 而且幾乎 垂直置中,因為基準會垂直置中。
文字可以像任何其他圖形化對象一樣處理。 其中一個簡單的選項是顯示文字字元的外框:
只要將 物件的一般 Style
屬性 SKPaint
從其預設設定 SKPaintStyle.Fill
變更為 SKPaintStyle.Stroke
,並藉由指定筆劃寬度來完成。 [PaintSurface
大綱文字] 頁面的處理程序會顯示其完成方式:
void OnCanvasViewPaintSurface(object sender, SKPaintSurfaceEventArgs args)
{
SKImageInfo info = args.Info;
SKSurface surface = args.Surface;
SKCanvas canvas = surface.Canvas;
canvas.Clear();
string text = "OUTLINE";
// Create an SKPaint object to display the text
SKPaint textPaint = new SKPaint
{
Style = SKPaintStyle.Stroke,
StrokeWidth = 1,
FakeBoldText = true,
Color = SKColors.Blue
};
// Adjust TextSize property so text is 95% of screen width
float textWidth = textPaint.MeasureText(text);
textPaint.TextSize = 0.95f * info.Width * textPaint.TextSize / textWidth;
// Find the text bounds
SKRect textBounds = new SKRect();
textPaint.MeasureText(text, ref textBounds);
// Calculate offsets to center the text on the screen
float xText = info.Width / 2 - textBounds.MidX;
float yText = info.Height / 2 - textBounds.MidY;
// And draw the text
canvas.DrawText(text, xText, yText, textPaint);
}
另一個常見的圖形對像是位圖。 這是SkiaSharp位陣陣圖一節中深入討論的大型主題,但下一篇文章:SkiaSharp中的點陣圖基本概念提供更簡短的簡介。