在HarmonyOS中,ArkTS提供了建立自定義元件的能力,允許開發者封裝和複用UI程式碼。以下是關於自定義元件的詳細介紹,包括建立自定義元件、頁面和自定義元件的生命週期、自定義元件的自定義佈局、凍結功能,以及程式碼案例分析。
建立自定義元件
自定義元件是基於struct
實現的,使用@Component
裝飾器來標識。每個自定義元件都必須實現build()
方法,用於描述元件的UI結構。
@Component
struct HelloComponent {
@State message: string = 'Hello, World!';
build() {
Row() {
Text(this.message)
.onClick(() => {
this.message = 'Hello, ArkUI!';
})
}
}
}
在其他檔案中使用該自定義元件時,需要使用export
關鍵字匯出,並在頁面中使用import
匯入該元件 。
頁面和自定義元件生命週期
頁面生命週期僅限於被@Entry
裝飾的元件,而自定義元件的生命週期僅限於被@Component
裝飾的元件。
onPageShow
:頁面每次顯示時觸發。onPageHide
:頁面每次隱藏時觸發。onBackPress
:當使用者點選返回按鈕時觸發。aboutToAppear
:元件即將出現時觸發。aboutToDisappear
:元件即將銷燬時觸發 。
自定義元件的自定義佈局
如果需要透過測算的方式佈局自定義元件內子元件的位置,可以使用onMeasureSize
和onPlaceChildren
介面。
@Component
struct CustomLayout {
@Builder doNothingBuilder() {};
@BuilderParam builder: () => void = this.doNothingBuilder;
@State startSize: number = 100;
result: SizeResult = { width: 0, height: 0 };
onMeasureSize(selfLayoutInfo: GeometryInfo, children: Array<Measurable>, constraint: ConstraintSizeOptions) {
let size = 100;
children.forEach((child) => {
let result: MeasureResult = child.measure({ minHeight: size, minWidth: size, maxWidth: size, maxHeight: size });
size += result.width / 2;
});
this.result.width = 100;
this.result.height = 400;
return this.result;
}
onPlaceChildren(selfLayoutInfo: GeometryInfo, children: Array<Layoutable>, constraint: ConstraintSizeOptions) {
let startPos = 300;
children.forEach((child) => {
let pos = startPos - child.measureResult.height;
child.layout({ x: pos, y: pos });
});
}
build() {
this.builder();
}
}
在這個例子中,CustomLayout
元件透過onMeasureSize
和onPlaceChildren
設定了子元件的大小和位置 。
自定義元件凍結功能
從API version 12開始,@ComponentV2
裝飾的自定義元件支援凍結功能。當元件處於非啟用狀態時,狀態變數將不響應更新。
@Entry@ComponentV2({ freezeWhenInactive: true })
struct FirstTest {
build() {
Column() {
Text(`From first Page ${book.page}`).fontSize(50)
Button('first page + 1').fontSize(30)
.onClick(() => {
book.page += 1;
})
Button('go to next page').fontSize(30)
.onClick(() => {
router.pushUrl({ url: 'pages/Page' });
})
}
}
}
在這個例子中,當頁面A跳轉到頁面B時,頁面A的狀態變為非啟用,元件的更新將被凍結 。
透過這些功能,開發者可以建立可複用、響應式且具有複雜佈局的自定義元件,從而提升HarmonyOS應用的開發效率和使用者體驗。
自定義元件案例:訂單列表頁面
假設我們需要開發一個HarmonyOS應用,其中包含一個訂單列表頁面。這個頁面將顯示一個訂單項的自定義元件,每個訂單項包含訂單編號、日期和訂單狀態。我們希望這個自定義元件是可重用的,以便在應用的其他部分也可以使用它。
步驟 1: 建立自定義元件
首先,我們建立一個名為OrderItem
的自定義元件,它將顯示單個訂單項的詳細資訊。
// OrderItem.ets
@Component
export struct OrderItem {
@Prop orderId: string;
@Prop orderDate: string;
@Prop status: string;
build() {
Row() {
Text(this.orderId).width(200).height(60).fontSize(16).alignItems(HorizontalAlign.Start);
Text(this.orderDate).width(150).height(60).fontSize(14).alignItems(HorizontalAlign.Center);
Text(this.status).width(100).height(60).fontSize(14).alignItems(HorizontalAlign.End);
}.padding(10).backgroundColor(Color.White).border({ width: 1, color: Color.Grey });
}
}
在這個元件中,我們使用了@Prop
裝飾器來定義屬性,這些屬性將由父元件傳遞。build()
方法定義了訂單項的UI結構,使用了Row
佈局來水平排列訂單編號、日期和狀態。
步驟 2: 使用自定義元件
接下來,我們在訂單列表頁面中使用OrderItem
元件來顯示訂單資料。
// OrderList.ets
import { OrderItem } from './OrderItem';
@Entry
@Component
struct OrderList {
@State orders: Array<{ orderId: string; orderDate: string; status: string }> = [
{ orderId: '001', orderDate: '2024-04-01', status: 'Completed' },
{ orderId: '002', orderDate: '2024-04-02', status: 'Shipped' },
// 更多訂單...
];
build() {
Column() {
ForEach(this.orders, (order) => {
OrderItem({
orderId: order.orderId,
orderDate: order.orderDate,
status: order.status,
});
});
}.spacing(10).padding(10);
}
}
在OrderList
元件中,我們定義了一個狀態變數orders
來儲存訂單資料。在build()
方法中,我們使用ForEach
迴圈來遍歷訂單陣列,併為每個訂單建立一個OrderItem
元件例項,傳遞相應的屬性。
詳細解釋
-
自定義元件的定義:
OrderItem
元件透過@Component
裝飾器定義,使其成為一個自定義元件。它接受三個屬性:orderId
、orderDate
和status
。 -
UI佈局:在
OrderItem
的build()
方法中,我們使用Row
佈局來水平排列三個Text
元件,分別顯示訂單編號、日期和狀態。每個Text
元件都設定了寬度、高度、字型大小和對齊方式,以確保佈局的整潔和一致性。 -
屬性傳遞:
OrderItem
元件的屬性是透過@Prop
裝飾器定義的,這允許父元件OrderList
在建立OrderItem
例項時傳遞這些屬性的值。 -
資料驅動:
OrderList
元件的狀態變數orders
包含了訂單資料。使用ForEach
迴圈,我們為每個訂單項建立一個OrderItem
元件例項,並將訂單資料作為屬性傳遞給它。 -
重用性:
OrderItem
元件是可重用的,因為它封裝了訂單項的UI和邏輯,可以在OrderList
頁面之外的其他部分使用,只需傳遞相應的屬性即可。
好了,這個案例展示瞭如何建立和使用自定義元件來構建HarmonyOS應用的UI,以及如何透過屬性傳遞和狀態管理來實現資料驅動的UI更新。關注威哥愛程式設計,你會發現他的世界裡,咖啡是燃料,鍵盤是樂器,而程式碼就是他的交響樂。每當夜深人靜,別人數羊,威哥數的是程式碼行數。🌙👨💻🎶