鴻蒙元服務實戰-笑笑五子棋(2)
章節導讀
本章節主要講解如何創建元服務和使用 canvas 描繪圖形
目標
上一章最后講到了 笑笑五子棋 主要的技術棧如下:
- ArkTS API 12
- Canvas
- 元服務獨有的 AtomicServiceTabs
- 卡片開發
- 元服務的創建
- 元服務的上架
那么本章節就開始實現這個案例。
AGC 平臺上創建元服務
需要先在AGC平臺上項目,然后再新建元服務。一個項目可以對應多個元服務。
DevEco Studio 創建元服務工程
AGC 平臺上創建好了項目,我們可以在本地創建元服務。
- 新建元服務
- 選擇 笑笑五子棋
- 選擇工程位置
- 元服務創建成功
Canvas 入門
Canvas提供畫布組件,用于自定義繪制圖形,開發者使用 CanvasRenderingContext2D 對象和 OffscreenCanvasRenderingContext2D
對象在 Canvas 組件上進行繪制,繪制對象可以是基礎形狀、文本、圖片等。
基本使用
canvas 的基本使用分為 4 步:
- 設置是否抗鋸齒抗鋸齒(Anti - aliasing)是一種在數字圖形處理中使用的技術,主要用于減少圖像中因為像素有限而產生的鋸齒狀邊緣的現象
- 創建畫布上下文
- 渲染畫布組件
- 在畫布上描繪圖案
@Entry
@Component
struct Index {
// 1 用來配置CanvasRenderingContext2D對象的參數,包括是否開啟抗鋸齒,true表明開啟抗鋸齒。
private settings: RenderingContextSettings = new RenderingContextSettings(true)
// 2 用來創建CanvasRenderingContext2D對象,通過在canvas中調用CanvasRenderingContext2D對象來繪制。
private context: CanvasRenderingContext2D = new CanvasRenderingContext2D(this.settings)
build() {
// 3 在canvas中調用CanvasRenderingContext2D對象。
Column(){
Canvas(this.context)
.width('100%')
.height('100%')
.backgroundColor('#F5DC62')
.onReady(() = > {
// 4 可以在這里繪制內容。
this.context.strokeRect(50, 50, 200, 150);
})
}
.width('100%')
.height('100%')
.justifyContent(FlexAlign.Center)
}
}
- 效果
canvas 常見用法
canvas 的核心思想是將想要的圖形如,直線、圓圈、矩形等圖形描繪到畫布上。如果想要呈現出比較酷炫的效果,做法是:
- 描繪圖形
- 擦除畫布
- 計算數值-重新描繪圖形
- 擦除畫布
- 。。。
通過以上過程實現動畫效果
canvas 的坐標系
在 canvas 中畫圖形都是基于坐標系來進行的。 左上角為起點。
描繪圖形
canvas 中內置的常見的描繪圖形的方法有以下:
- 直線
- 矩形
- 弧形
- 文本
- 圖像
- ...
直線
描繪直線可以使用:
- 定起點
moveTo
- 定終點
lineTo
- 開始描繪
stroke
this.context.moveTo(10, 10);
this.context.lineTo(100, 100);
this.context.stroke();
矩形
可以使用直線lineTo
自己畫成一個矩形。也可以直接使用 strokeRect
直接生成矩形
lineTo 畫矩形
this.context.moveTo(10, 10);
this.context.lineTo(300, 10);
this.context.lineTo(300, 300);
this.context.lineTo(10, 300);
// 自動閉環
this.context.closePath();
// 開始描述 將路徑的當前點移回到路徑的起點,當前點到起點間畫一條直線
this.context.stroke();
strokeRect 畫矩形
// this.context.strokeRect(x, y, 寬度, 高度);
this.context.strokeRect(50, 50, 200, 150);
弧形
弧形可以使用 arc
和 arcTo
來描繪
arc
arc(x: number, y: number, radius: number, startAngle: number, endAngle: number, counterclockwise?: boolean)
參數名 | 類型 | 必填 | 說明 |
---|---|---|---|
x | number | 是 | 弧線圓心的 x 坐標值。默認單位:vp。 |
y | number | 是 | 弧線圓心的 y 坐標值。默認單位:vp。 |
radius | number | 是 | 弧線的圓半徑。默認單位:vp。 |
startAngle | number | 是 | 弧線的起始弧度。單位:弧度 |
endAngle | number | 是 | 弧線的終止弧度。單位:弧度 |
counterclockwise | boolean | 否 | 是否逆時針繪制圓弧。true:逆時針方向繪制橢圓。false:順時針方向繪制橢圓。默認值:false。 |
這里需要注意的是 arc 使用的單位是弧度不是角度
一圈 = 360角度 = 2 * Math.PI
半圈 = 180角度 = Math.PI ≈ 3.14
觀察以下效果
100,75 是圓心坐標
50 是半徑
0 是開始的弧度
6.28 ≈ 2 * Math.PI = 一圈
arc 是從正右方向開始旋轉的。
this.context.beginPath();
this.context.arc(100, 75, 50, 0, 3.14 / 2);
this.context.stroke();
arcTo
arcTo(x1: number, y1: number, x2: number, y2: number, radius: number)
參數名 | 類型 | 必填 | 說明 |
---|---|---|---|
x1 | number | 是 | 第一個控制點的 x 坐標值。默認單位:vp。 |
y1 | number | 是 | 第一個控制點的 y 坐標值。默認單位:vp。 |
x2 | number | 是 | 第二個控制點的 x 坐標值。默認單位:vp。 |
y2 | number | 是 | 第二個控制點的 y 坐標值。默認單位:vp。 |
radius | number | 是 | 圓弧的圓半徑值。默認單位:vp。 |
this.context.beginPath();
this.context.strokeStyle = "#000000";
this.context.lineWidth = 3;
this.context.moveTo(360, 20);
this.context.arcTo(360, 170, 110, 170, 150);
this.context.stroke();
輔助理解
想象一下,我們有一個起點(即當前路徑的最后一個點),然后有三個更多的點:兩個控制點 (x1, y1) 和 (x2, y2),以及由 radius
定義的一個圓心。arcTo
會創建一條從起點到第二個控制點 (x2, y2) 的圓弧,這條圓弧是位于以 radius
為半徑的圓周上的一部
分。該圓弧會在起點和第一個控制點 (x1, y1) 之間形成一個切線,并且也會在第二個控制點 (x2, y2) 和圓弧的終點之間形成一個切線。
文本
- strokeText表示描邊的圖形
- fillText 表示填充的圖形,還有其他 fill ,fillRect等也表示填充。
strokeText
this.context.font = '55px sans-serif'
this.context.strokeText("Hello World!", 20, 60)
fillText
this.context.font = '55px sans-serif'
this.context.fillText("Hello World!", 20, 60)
圖像
drawImage可以把圖像描繪到畫布上,很多的在線圖形合成效果都可以利用該功能實現
drawImage(image: ImageBitmap | PixelMap, dx: number, dy: number): void
drawImage(image: ImageBitmap | PixelMap, dx: number, dy: number, dw: number, dh: number): void
drawImage(image: ImageBitmap | PixelMap, sx: number, sy: number, sw: number, sh: number, dx: number, dy: number, dw: number, dh: number): void
參數名 | 類型 | 必填 | 說明 |
---|---|---|---|
image | ImageBitmap或PixelMap | 是 | 圖片資源,請參考 ImageBitmap 或 PixelMap。 |
sx | number | 是 | 裁切源圖像時距離源圖像左上角的 x 坐標值。image 類型為 ImageBitmap 時,默認單位:vp。image 類型為 PixelMap 時,單位:px。 |
sy | number | 是 | 裁切源圖像時距離源圖像左上角的 y 坐標值。image 類型為 ImageBitmap 時,默認單位:vp。image 類型為 PixelMap 時,單位:px。 |
sw | number | 是 | 裁切源圖像時需要裁切的寬度。image 類型為 ImageBitmap 時,默認單位:vp。image 類型為 PixelMap 時,單位:px。 |
sh | number | 是 | 裁切源圖像時需要裁切的高度。image 類型為 ImageBitmap 時,默認單位:vp。image 類型為 PixelMap 時,單位:px。 |
dx | number | 是 | 繪制區域左上角在 x 軸的位置。默認單位:vp。 |
dy | number | 是 | 繪制區域左上角在 y 軸的位置。默認單位:vp。 |
dw | number | 是 | 繪制區域的寬度。當繪制區域的寬度和裁剪圖像的寬度不一致時,將圖像寬度拉伸或壓縮為繪制區域的寬度。默認單位:vp。 |
dh | number | 是 | 繪制區域的高度。當繪制區域的高度和裁剪圖像的高度不一致時,將圖像高度拉伸或壓縮為繪制區域的高度。默認單位:vp。 |
@Entry
@Component
struct Index {
private settings: RenderingContextSettings = new RenderingContextSettings(true)
private context: CanvasRenderingContext2D = new CanvasRenderingContext2D(this.settings)
private img: ImageBitmap = new ImageBitmap("/images/example.jpg")
build() {
Flex({ direction: FlexDirection.Column, alignItems: ItemAlign.Center, justifyContent: FlexAlign.Center }) {
Canvas(this.context)
.width('100%')
.height('100%')
.backgroundColor('#ffff00')
.onReady(() = > {
this.context.drawImage(this.img, 0, 0)
this.context.drawImage(this.img, 0, 150, 300, 100)
this.context.drawImage(this.img, 0, 0, 500, 500, 0, 300, 400, 200)
})
}
.width('100%')
.height('100%')
}
}
canvas 淺嘗動態效果 1
const width = px2vp(display.getDefaultDisplaySync().availableWidth) * 0.9;
const height = width;
let x = 0;
let y = 0;
setInterval(() = > {
this.context.strokeRect(x, y, 100, 100);
x++;
y++;
}, 20);
canvas 淺嘗動態效果 2
const width = px2vp(display.getDefaultDisplaySync().availableWidth) * 0.9;
const height = width;
let x = 0;
let y = 0;
setInterval(() = > {
// 清理畫布
this.context.strokeRect(x, y, 100, 100);
x++;
y++;
}, 20);
canvas 屬性 一覽
名稱 | 說明 |
---|---|
fillStyle | 設置繪制的填充色,支持多種類型及對應創建方式,有默認值。 |
lineWidth | 設置繪制線條的寬度,有默認值及取值限制。 |
strokeStyle | 設置線條的顏色,支持多種類型及對應創建方式,有默認值。 |
lineCap | 指定線端點的樣式,有可選值及默認值。 |
lineJoin | 指定線段間相交的交點樣式,有可選值及默認值。 |
miterLimit | 設置斜接面限制值,有默認值及取值限制。 |
font | 設置文本繪制中的字體樣式,包含多種可選參數及默認值。 |
textAlign | 設置文本繪制中的文本對齊方式,有可選值及默認值。 |
textBaseline | 設置文本繪制中的水平對齊方式,有可選值及默認值。 |
globalAlpha | 設置透明度,有默認值。 |
lineDashOffset | 設置畫布的虛線偏移量,有默認值。 |
globalCompositeOperation | 設置合成操作的方式,有可選值及默認值。 |
shadowBlur | 設置繪制陰影時的模糊級別,有默認值及取值限制。 |
shadowColor | 設置繪制陰影時的陰影顏色,有默認值。 |
shadowOffsetX | 設置繪制陰影時和原有對象的水平偏移值,有默認值。 |
shadowOffsetY | 設置繪制陰影時和原有對象的垂直偏移值,有默認值。 |
imageSmoothingEnabled | 設置繪制圖片時是否進行圖像平滑度調整,有默認值。 |
height | 表示組件高度,有默認單位。 |
width | 表示組件寬度,有默認單位。 |
imageSmoothingQuality | 設置圖像平滑度,有默認值。 |
direction | 設置繪制文字時使用的文字方向,有默認值。 |
filter | 設置圖像的濾鏡,支持多種濾鏡效果,有默認值。 |
canvas | 獲取和 CanvasRenderingContext2D 關聯的 Canvas 組件的 FrameNode 實例,可監聽可見狀態,默認值為 null。 |
canvas 方法 一覽
名稱 | 說明 |
---|---|
fillRect | 推測用于進行圖形填充相關操作(通常是填充矩形區域) |
strokeRect | 推測用于繪制矩形邊框相關操作(通常是繪制矩形的輪廓) |
clearRect | 推測用于清除指定矩形區域的內容 |
fillText | 推測用于對文本進行填充操作(比如設置文本填充顏色等相關樣式填充) |
strokeText | 推測用于繪制文本的輪廓相關操作 |
measureText | 推測用于測量文本相關的尺寸等屬性 |
stroke | 一般用于繪制圖形的輪廓、線條等(按常規語義理解) |
beginPath | 通常用于開始定義一個新的路徑,后續可基于此路徑進行圖形繪制等操作 |
moveTo | 常用來將畫筆移動到指定坐標位置,作為繪制路徑的起始點等操作 |
lineTo | 一般用于從當前畫筆位置繪制直線到指定坐標位置,構建路徑內容 |
closePath | 通常用于閉合當前正在繪制的路徑,使路徑形成封閉圖形 |
createPattern | 可能用于創建某種圖案(比如重復平鋪的圖案等)用于繪制等 |
bezierCurveTo | 大概率用于繪制貝塞爾曲線,通過控制點來定義曲線形狀 |
quadraticCurveTo | 推測用于繪制二次貝塞爾曲線,指定控制點來確定曲線走向 |
arc | 一般用于繪制圓弧,通過圓心、半徑、起始角度、結束角度等參數來定義 |
arcTo | 常用來繪制與兩條切線相切的圓弧,按給定條件確定圓弧形狀 |
ellipse | 用于繪制橢圓圖形,需指定相關參數如圓心坐標、長半軸、短半軸等 |
rect | 可用于繪制矩形,指定矩形的左上角坐標、寬度、高度等參數 |
fill | 用于對已繪制的圖形或者指定區域進行填充操作 |
clip | 可能用于設置裁剪區域,后續繪制內容只在裁剪區域內顯示 |
reset12+ | 從名稱看可能是在特定版本(12+)中用于重置某些狀態或設置的操作 |
saveLayer12+ | 在特定版本(12+)里可能用于保存圖層相關狀態等操作 |
restoreLayer12+ | 在特定版本(12+)里對應于之前保存圖層狀態進行恢復的操作 |
resetTransform | 推測用于重置圖形變換相關的設置(比如旋轉、縮放等變換) |
rotate | 用于將圖形進行旋轉操作,需指定旋轉角度等參數 |
scale | 用于對圖形進行縮放操作,指定橫向和縱向的縮放比例 |
transform | 一般用于對圖形進行多種變換(如平移、旋轉、縮放等組合變換)的設置 |
setTransform | 可能用于設置圖形的變換矩陣,來確定圖形的變換情況 |
getTransform | 推測用于獲取當前圖形的變換相關信息(比如變換矩陣等) |
translate | 用于將圖形進行平移操作,指定在橫、縱坐標方向平移的距離 |
drawImage | 通常用于在畫布上繪制圖像,指定圖像源及繪制位置等參數 |
createImageData | 可能用于創建圖像數據對象(比如像素數據等相關內容) |
getPixelMap | 推測用于獲取像素映射相關的數據(比如圖像像素的分布等情況) |
setPixelMap | 大概是用于設置像素映射相關數據,改變圖像像素表現等 |
getImageData | 一般用于獲取圖像的像素數據等具體信息內容 |
putImageData | 通常是將獲取到的圖像數據(如像素數據)重新應用到畫布等位置 |
setLineDash | 可能用于設置線條的虛線樣式,指定虛線的長度、間隔等參數 |
getLineDash | 推測用于獲取當前線條所設置的虛線樣式相關參數 |
transferFromImageBitmap | 從名稱看可能是與從圖像位圖進行數據轉移相關操作 |
toDataURL | 通常用于將畫布等內容轉換為可以表示圖像數據的 URL 格式 |
restore | 一般用于恢復之前保存的某些狀態(如畫布狀態等) |
save | 常用來保存當前畫布等相關的狀態,以便后續恢復使用 |
createLinearGradient | 用于創建線性漸變對象,可用于圖形的漸變填充等操作 |
createRadialGradient | 用于創建徑向漸變對象,定義從中心向外擴散的漸變效果 |
createConicGradient | 用于創建圓錐漸變對象,實現類似圓錐形狀的漸變效果 |
總結
這篇文章主要是介紹了元服務的創建和基本 canvas 的使用
如果你興趣想要了解更多的鴻蒙應用開發細節和最新資訊,歡迎在評論區留言或者私信或者看我個人信息,可以加入技術交流群。
審核編輯 黃宇
-
AGC
+關注
關注
0文章
164瀏覽量
52083 -
Canvas
+關注
關注
0文章
20瀏覽量
11105 -
鴻蒙
+關注
關注
57文章
2457瀏覽量
43447
發布評論請先 登錄
相關推薦
評論