bit-condition:红点该不该显示,交给条件系统自动算

它解决什么问题

红点系统看着简单,做起来烦。一个红点的显示条件可能是”有未读邮件”,另一个可能是”背包里有新装备 或者 有可升级的装备”,条件组合一多,代码里到处散落着 if (hasNewMail() || hasUpgradableItem()) 这种判断,而且数据一变还要记得手动去刷新对应的红点节点,漏刷新是最常见的红点 bug 来源。

bit-condition 把”判断条件”和”通知 UI 更新”这两件事拆开管理:你只管写条件类怎么判断,节点怎么显示交给框架,数据变化时通知框架重新算一遍,该显示的自动显示,该隐藏的自动隐藏。

安装

bit-core@gongxh/fairygui-cc 是 peer 依赖:

npm install @gongxh/bit-condition @gongxh/bit-core @gongxh/fairygui-cc

核心用法

1. 加条件模块

场景根节点或者一个常驻的管理节点上挂 ConditionModule 组件,它负责定时批量重算所有待更新的条件(默认 0.3 秒一次),不是每次数据变化就立刻算,攒一批一起处理,性能更友好:

// 挂在场景管理节点上,updateDeltaTime 可以在 Inspector 里调

2. 定义条件类型和条件类

先用枚举定义好有哪些条件类型,再继承 ConditionBase 实现判断逻辑:

import { _conditionDecorator, ConditionBase } from '@gongxh/bit-condition';

enum ConditionType {
    NewMail,
    UpgradableItem,
}

@_conditionDecorator.conditionClass(ConditionType.NewMail)
export class NewMailCondition extends ConditionBase {
    protected onInit(): void {
        // 这里可以注册数据变化的监听
    }

    protected evaluate(): boolean {
        return MailSystem.hasUnreadMail();
    }
}

evaluate() 只管返回布尔值,什么时候调用、调用完怎么通知节点,都不用你操心。

3. 数据变化时喊一声

邮件系统收到新邮件时,找到条件实例调用 tryUpdate(),告诉框架”我这个条件可能变了,下个周期重新算一下”:

newMailCondition.tryUpdate();

4. 挂红点节点

ConditionAnyNodeConditionAllNode 是内置的两种组合模式,分别对应”任一条件满足就显示”和”所有条件都满足才显示”:

import { ConditionAnyNode } from '@gongxh/bit-condition';

// 邮件红点:有未读邮件 或者 有可升级装备,任一满足就亮红点
const redDot = new ConditionAnyNode(redDotNode, ConditionType.NewMail, ConditionType.UpgradableItem);

节点销毁前记得调用 destroy() 解绑;如果是挂在 FairyGUI 对象上的 ConditionFGUINodeGObject.removeFromParent() 的时候会自动帮你解绑,不用手动处理。

条件组合模式

ConditionMode 只有两种:

  • Any(0)—— 任意一个条件满足就算满足,红点、提示类场景最常用
  • All(1)—— 所有条件都要满足,比如某个功能同时要求”等级达到10级”和”完成新手引导”才解锁

如果 Any/All 都不够表达你的逻辑(比如条件之间还要加权重、或者要 A 且非 B),直接继承 ConditionBase 自己写一个组合条件类,evaluate() 里调用其他条件实例的结果自己拼逻辑就行,框架没有限制你必须用内置的两种模式。

避坑提醒

  • evaluate() 不会自动被高频调用,只有调用过 tryUpdate() 之后,才会在下一个更新周期被重新计算。如果条件判断依赖的数据变了但忘了调 tryUpdate(),红点状态就会一直停留在旧值,这是最容易踩的坑。
  • ConditionModule 只能挂一份在场景里生效,别指望多挂几个能加速刷新——批量定时更新本身就是为了避免频繁计算,加实例只会重复算,不会更快。
  • 条件类型枚举建议一次性统一定义好,散落在各个业务模块里定义容易和其他系统的枚举撞值。

项目信息

bit-ui 的窗口系统配合起来用效果最好,红点挂在窗口内的 FairyGUI 节点上,窗口关闭时节点自动跟着销毁解绑。