108 lines
3.3 KiB
TypeScript
108 lines
3.3 KiB
TypeScript
import { _decorator, Component, Label, UITransform } from 'cc';
|
|
import { I18nManager } from '../managers/I18nManager';
|
|
|
|
const { ccclass, property } = _decorator;
|
|
|
|
@ccclass('LocalizedLabel')
|
|
export class LocalizedLabel extends Component {
|
|
private label: Label | null = null;
|
|
|
|
@property({ tooltip: '翻译键值' })
|
|
private key: string = '';
|
|
|
|
private originalText: string = '';
|
|
private minWidth: number = 800;
|
|
private maxWidth: number = 850;
|
|
|
|
start() {
|
|
this.label = this.getComponent(Label);
|
|
this.updateLabel();
|
|
}
|
|
|
|
public setKey(key: string) {
|
|
if (this.key !== key) {
|
|
this.key = key;
|
|
this.updateLabel();
|
|
}
|
|
}
|
|
|
|
public updateLabel() {
|
|
if (!this.label || !this.key) return;
|
|
if (!I18nManager.instance.ready) return;
|
|
|
|
this.label.string = I18nManager.instance.t(this.key);
|
|
this.label.updateRenderData();
|
|
|
|
// this.label.cacheMode = Label.CacheMode.NONE;
|
|
// this.label.overflow = Label.Overflow.NONE;
|
|
// this.label.enableWrapText = false;
|
|
// // this.label.string = I18nManager.instance.t(this.key);
|
|
// this.originalText = I18nManager.instance.t(this.key);
|
|
// this.updateLayout();
|
|
}
|
|
|
|
public updateLayout() {
|
|
if (!this.originalText) return;
|
|
this.label.string = '';
|
|
this.label.updateRenderData();
|
|
let wrappedText = this.wrapTextByWidth(this.originalText);
|
|
this.label.string = wrappedText;
|
|
}
|
|
|
|
public wrapTextByWidth(text: string): string {
|
|
// 按空格分割单词(保留空格)
|
|
const words = text.split(/\s+/);
|
|
const lines: string[] = [];
|
|
let currentLine = '';
|
|
|
|
for (const word of words) {
|
|
const testLine = currentLine ? currentLine + ' ' + word : word;
|
|
|
|
// 直接设置到 Label 并测量宽度
|
|
this.label.string = testLine;
|
|
this.label.updateRenderData();
|
|
const currentWidth = this.getLabelWidth();
|
|
|
|
if (currentWidth <= this.maxWidth) {
|
|
// 在最大宽度内,继续添加
|
|
currentLine = testLine;
|
|
} else {
|
|
// 超过最大宽度
|
|
if (currentLine) {
|
|
// 检查当前行是否满足最小宽度
|
|
this.label.string = currentLine;
|
|
this.label.updateRenderData();
|
|
const lineWidth = this.getLabelWidth();
|
|
|
|
if (lineWidth >= this.minWidth || lines.length === 0) {
|
|
lines.push(currentLine.trim());
|
|
currentLine = word.trim();
|
|
} else {
|
|
// 当前行太短,继续添加
|
|
currentLine = testLine;
|
|
}
|
|
} else {
|
|
// 单词太长,强制使用
|
|
currentLine = word;
|
|
}
|
|
}
|
|
}
|
|
|
|
// 添加最后一行
|
|
if (currentLine) {
|
|
lines.push(currentLine.trim());
|
|
}
|
|
|
|
return lines.join('\n');
|
|
}
|
|
|
|
/**
|
|
* 获取当前 Label 的实际宽度
|
|
*/
|
|
private getLabelWidth(): number {
|
|
const transform = this.label.getComponent(UITransform)!;
|
|
return transform.width;
|
|
}
|
|
|
|
|
|
} |