HarmonyOS鸿蒙Next中mpchart如何自定义Y轴标签字体?
HarmonyOS鸿蒙Next中mpchart如何自定义Y轴标签字体? 我在使用mpchart绘制图表,现在需要对于Y轴标签使用自定义字体,
我想用setTypeFace()这个接口,但是他只接受FontFamily类型,
我已经全局注册了自定义字体,在Text组件中可以正常使用,但是setTypeFace()不能直接接受注册的自定义字体名字。请问该怎么实现Y轴标签能使用自定义字体?
尊敬的开发者,您好,
mpchart的setTypeFace的入参FontFamily限制字体类型为’sans-serif’、‘serif’ 、‘monospace’、’’ 这几种,不支持通过此方式加载自定义字体。mpchart标签底层逻辑是通过Canvas fillText 绘制的,开发者可以通过继承YAxisRenderer类,重写drawYLabels方法的内部逻辑,将自定义字体直接绘制在Canvas上。
若是开发者需要通过setTypeFace设置或者由其他方案实现,还请开发者详细描述下您的场景以及期望实现的方式,感谢:
请问您是在什么样的业务场景中使用该能力,交互流程是怎样的,在哪一个环节遇到了问题?方便说明能力不满足可能带来的影响:什么时间用到?是否高频?有无三方库可以做到?若提供该能力,是否会造成大工作量返工?请您注意提供的内容不要包含您或第三方的非公开信息,如给您带来不便,敬请谅解。
更多关于HarmonyOS鸿蒙Next中mpchart如何自定义Y轴标签字体?的实战系列教程也可以访问 https://www.itying.com/category-93-b0.html
你好,尝试以下方式解决问题:
1、到官方仓库提 issues , 等待官方支持。
2、直接修改源码, FontFamily 类型增加 string,这样就支持传自定义字体。
export type FontFamily = 'sans-serif' | 'serif' | 'monospace' | '';
// 改为
export type FontFamily = 'sans-serif' | 'serif' | 'monospace' | string;
3、如果不想改源码,可以定制渲染类 YAxisRenderer。参考 README

上面官方例子是自定义 XAxisRenderer,下面来自定义我们的 YAxisRenderer:
import { YAxisRenderer, YAxis, ViewPortHandler, Transformer, Paint } from
'@ohos/mpchart';
class CustomYAxisRenderer extends YAxisRenderer {
private customFont: string;
constructor(viewPortHandler: ViewPortHandler, yAxis: YAxis, transformer: Transformer,
customFont: string) {
super(viewPortHandler, yAxis, transformer);
this.customFont = customFont;
}
// 重写 drawYLabels,在绘制前覆写 font 字符串
public drawYLabels(c: CanvasRenderingContext2D, fixedPosition: number, positions:
number[], offset: number, isHorizontalFlip: boolean, isLeftAxis: boolean): void {
if (this.mAxisLabelPaint) {
// 参考 this.mAxisLabelPaint.setFontFamily(this.mYAxis.getTypeface()); 拼接得到font
this.mAxisLabelPaint.font =
this.mAxisLabelPaint.fontStyle + " " + this.mAxisLabelPaint.fontWeight + " " + this.mAxisLabelPaint.fontSize +
this.mAxisLabelPaint.fontSizeUnit + " " + this.customFont;
}
super.drawYLabels(c, fixedPosition, positions, offset, isHorizontalFlip, isLeftAxis);
}
}
使用自定义 CustomYAxisRenderer:
// 在 aboutToAppear 中
this.model.setRendererLeftYAxis(
new CustomYAxisRenderer(
this.model.getViewPortHandler(),
this.model.getAxisLeft(),
this.model.getTransformer(AxisDependency.LEFT),
'你的字体名' // font 字符串
)
);
官方仓库半年回一次issue
HarmonyOS的流畅动画和过渡效果让操作更加顺畅,体验极佳。
尊敬的开发者,您好,
mpchart的setTypeFace的入参FontFamily限制字体类型为’sans-serif’、‘serif’ 、‘monospace’、’’ 这几种,不支持通过此方式加载自定义字体。mpchart标签底层逻辑是通过Canvas fillText 绘制的,开发者可以通过继承YAxisRenderer类,重写drawYLabels方法的内部逻辑,将自定义字体直接绘制在Canvas上。
若是开发者需要通过setTypeFace设置或者由其他方案实现,还请开发者详细描述下您的场景以及期望实现的方式,感谢:
请问您是在什么样的业务场景中使用该能力,交互流程是怎样的,在哪一个环节遇到了问题?方便说明能力不满足可能带来的影响:什么时间用到?是否高频?有无三方库可以做到?若提供该能力,是否会造成大工作量返工?请您注意提供的内容不要包含您或第三方的非公开信息,如给您带来不便,敬请谅解。
HarmonyOS 版 mpchart 和 Android 原版不太一样。
核心问题在于:
setTypeFace() 要的不是字符串字体名,而是 FontFamily 对象。
所以即使你已经在系统里全局注册了字体,Text 能直接 "xxx.ttf" 使用,mpchart 这里也不能直接传字符串。
正确做法是:
先创建 FontFamily,再传给 setTypeFace()。
示例:
import { FontFamily } from '@kit.ArkUI'
// 创建字体族
let customFont = new FontFamily('HarmonyOS_Sans_SC')
// 设置给Y轴
yAxis.setTypeFace(customFont)
如果你是通过 Resource 注册字体,例如:
.fontFamily('myFont')
那这里不能直接:
yAxis.setTypeFace('myFont') // ❌ 不行
而是需要:
let font = new FontFamily('myFont')
yAxis.setTypeFace(font)
另外还有一个坑:
有些 mpchart HarmonyOS 移植版本,其实内部并没有真正把 FontFamily 应用到 Canvas/TextPainter 上,所以你即使设置成功,也可能完全不生效。
这个你可以验证:
- X轴字体是否生效
- Legend 字体是否生效
- Description 字体是否生效
如果全部不生效,大概率是库本身没适配完整。
目前 HarmonyOS 上很多 mpchart 三方移植库都存在:
- 字体不生效
- 富文本不支持
- Canvas 字体 fallback
- 自定义字体渲染丢失
这种问题。
如果确认库本身不支持,通常只有两种方案:
-
修改 mpchart 源码
找到 YAxisRenderer / Renderer 中实际 drawText 的地方,把:paint.setTypeface(...)真正接到 ArkUI 的字体系统。
-
放弃 mpchart 默认轴文字
自己覆盖绘制 Y 轴标签(custom renderer)。
目前这是 HarmonyOS 图表库里比较常见的处理方式。
同问
在HarmonyOS Next中,使用mpchart时,通过YAxis对象的setTextSize()和setTypeface()方法可自定义Y轴标签字体。示例:leftAxis.setTextSize(14f); leftAxis.setTypeface(Typeface.DEFAULT_BOLD);。需要预先加载自定义字体文件,再通过Typeface.createFromAsset(context, "font.ttf")设置。
在 mpchart 中自定义 Y 轴字体,直接使用字体名称或资源构造 FontFamily 对象传入即可。
// 方式一:使用全局注册的字体名称(必须与 font.registerFont 时的 family 名称一致)
yAxis.setTypeface(new FontFamily("myCustomFont"));
// 方式二:使用资源引用(fonts 目录下的资源)
yAxis.setTypeface(new FontFamily($r('app.font.my_custom_font')));
确保字体文件已放在 src/main/resources/base/font/ 目录,或通过 font.registerFont() 注册并指定了 familyName。FontFamily 的构造器可直接接收 string 或 Resource,不必再通过其他手段转换。


