車牌號智能填充快人一步,告別繁瑣輸入
在汽車出行場景中,車主時常在停車繳費口因記不住車牌而堵成長龍;在車險理賠過程中需要輸入車牌號時,也要通過翻照片或行駛證才能找到車牌號信息;尤其在車主名下有多輛車的情況下,車牌號信息記憶難度倍增,輸入環節便成了效率瓶頸。
為解決這一難題,HarmonyOS SDK融合場景服務(Scenario Fusion Kit)智能填充服務的推薦車牌號場景能力基于本地安全沙箱,實時比對登錄設備的賬號信息,實名姓名+手機號或郵箱信息,與歷史表單輸入中的車牌號信息做匹配。匹配成功即在用戶填寫車牌號表單時提供輸入建議,點擊即可一鍵填入,無需聯網查詢,也無需第三方授權。

使用智能填充服務能力填寫車牌號信息
能力優勢
● 一鍵速填
自動匹配車主實名賬號下的歷史車牌,無需手動輸入,停車繳費、理賠申報秒級完成。
● 零記憶成本
本地加密存儲,換車、增車自動同步,徹底告別翻照片、查行駛證。
● 零誤差保障
只呈現與登錄身份一致的專屬車牌候選項,杜絕輸錯或他人車牌混入。
開發步驟
import { display } from '@kit.ArkUI';
const NEW_ENERGY_TEXT = '新能源';
@Extend(Text)
function extendStyles(value: string, width: number, height: number, active: boolean) {
.fontSize(value === NEW_ENERGY_TEXT ? 10 : 18)
.fontWeight(FontWeight.Medium)
.textAlign(TextAlign.Center)
.width(width)
.height(height)
.borderWidth('3px')
.borderColor(active ? Color.Blue : '#ccc')
.borderRadius(5)
}
@Entry
@Component
struct LicensePlate {
// 車牌號輸入框的數量。
private length = 8;
private licenseItemId = '_license_item';
@State licensePlateVal: string[] = [];
@State activeIndex: number = -1;
@State itemWidth: number = 30;
@State itemHeight: number = 30;
@State inputText: string = '';
// 用戶是否已經觸發輸入。
@State isUserInput: boolean = false;
// 匹配歷史輸入的上一個輸入框的值
private beforeValue: string = '';
aboutToAppear(): void {
this.licensePlateVal = new Array(this.length).fill('');
let displayClass = display.getDefaultDisplaySync();
let width = displayClass.width;
// 每個框的寬度根據屏幕寬度計算。
this.itemWidth = this.getUIContext().px2vp(width) / (this.length + 1) - 4;
this.itemHeight = this.itemWidth * 1.2;
}
setValue(val: string): void {
if (!this.isUserInput) {
// 根據SmartFill填寫車牌號輸入框。
this.handleAutoFill(val);
this.beforeValue = val;
return;
}
if (!val || val.length === 0 || this.beforeValue.length > val.length) {
let licensePlate = this.getLicensePlate();
if (licensePlate.length > 0) {
this.inputText = licensePlate;
}
this.beforeValue = this.inputText;
return;
}
let inputData = val.substring(this.beforeValue.length);
if (inputData.length > this.length) {
inputData = inputData.substring(0, this.length);
}
// 用戶輸入僅替換選定的輸入框,而SmartFill則替換所有輸入框中的所有值。
this.handleUserInput(inputData);
this.beforeValue = val;
}
getLicensePlate(): string {
return this.licensePlateVal.join('');
}
handleUserInput(val: string): void {
if (val.length > this.length - this.activeIndex) {
val = val.substring(0, this.length - this.activeIndex);
}
for (let i = 0; i < val.length; i++) {
this.licensePlateVal[this.activeIndex] = val[i];
this.activeIndex = Math.min(this.activeIndex + 1, this.length - 1);
}
}
handleAutoFill(val: string): void {
let value = val.split('');
this.licensePlateVal.fill('');
for (let i = 0; i < this.length; i++) {
this.licensePlateVal[i] = i < value.length ? value[i] : this.licensePlateVal[i];
}
this.activeIndex = Math.min(value.length + 1, this.length - 1);
}
handleDelete() {
if (!this.licensePlateVal[this.activeIndex]) {
this.licensePlateVal[this.activeIndex - 1] = '';
} else {
this.licensePlateVal[this.activeIndex] = '';
}
this.activeIndex = Math.max(0, this.activeIndex - 1);
}
getValue(index: number): string {
return (index === this.length - 1 && !this.licensePlateVal[index]) ? NEW_ENERGY_TEXT : this.licensePlateVal[index];
}
handleLicenseClick(screenX: number) {
for(let index = 0; index <= 7; index++) {
let id = index + this.licenseItemId;
let position = this.getUIContext().getComponentUtils().getRectangleById(id);
// 相對于屏幕的位置信息,單位px
let left = position?.screenOffset?.x ?? 0;
let right = left + (position?.size?.width ?? 0);
if (screenX >= left && screenX <= right) {
this.activeIndex = index;
}
}
}
@Builder
displayItem(index: number) {
Column() {
Text(this.getValue(index))
.extendStyles(this.getValue(index), this.itemWidth, this.itemHeight, this.activeIndex === index)
}
.id(index + this.licenseItemId)
.padding({
left: 2,
right: 2
})
}
@Builder
buildLicensePlateNumber() {
Flex({
direction: FlexDirection.Row,
alignItems: ItemAlign.Center,
justifyContent: FlexAlign.SpaceBetween
}) {
Column() {
Row() {
Text("車牌號碼")
}.height(30)
Stack({ alignContent: Alignment.BottomStart }) {
Row() {
this.displayItem(0)
this.displayItem(1)
Text('·')
.fontSize(22)
.fontWeight(600)
.height(this.itemHeight)
this.displayItem(2)
this.displayItem(3)
this.displayItem(4)
this.displayItem(5)
this.displayItem(6)
this.displayItem(7)
}
TextInput({ text: $$this.inputText })
.width('100%')
.height('100%')
.opacity(0)
.contentType(ContentType.LICENSE_PLATE)
.onClick((event) => {
// 相對于屏幕的X軸坐標,單位px
let displayX = this.getUIContext().vp2px(event.displayX);
this.handleLicenseClick(displayX);
if (this.activeIndex < 0) {
this.activeIndex = 0;
}
})
.onChange((val: string) => {
if (val === this.beforeValue) {
return;
}
this.setValue(val);
this.isUserInput = false;
})
.onDidInsert(() => {
// 當使用輸入法輸入數據時觸發。如果輸入法是自定義的,則在用戶輸入數據時將isUserInput設置為true。
this.isUserInput = true;
})
.onDidDelete((val: DeleteValue) => {
// 當使用輸入方法刪除數據時觸發。如果輸入方法是自定義的,當用戶刪除數據時,將`isUserInput`設置為`true`,并調用相應的處理函數。
if (val?.deleteValue?.length > 0) {
this.isUserInput = true;
}
this.handleDelete();
})
}
.height(this.itemHeight)
.margin({ top: 20 })
}
}
.backgroundColor(Color.White)
.height(50)
.margin({ left: 15, right: 15 })
.id("customInput")
.defaultFocus(false)
}
build() {
Column() {
this.buildLicensePlateNumber()
}
}
}
了解更多詳情>>
浙公網安備 33010602011771號