Skip to content
导航栏

Amis 内部组件查找逻辑

当在动作组件 action 里配置 target 时,会调用方法getComponentByName, 而在这个方法的内部其实会查找组件名名称或是组件的 id,单看方法名会有误解。

比如在测试示例里,配置了 target:组件 ID 也能找到对应的组件。

https://aisuda.bce.baidu.com/amis/zh-CN/components/form/formula#手动应用

  • 使用getComponentByName时,组件的 name 属性可以使用模板语法。
  • 使用getComponentById时,组件的 id 属性可以使用模板语法。
js
// \amis\packages\amis-core\src\Scoped.tsx
    getComponentByName(name: string) {
      if (~name.indexOf('.')) {
        const paths = name.split('.');
        const len = paths.length;

        return paths.reduce((scope, name, idx) => {
          if (scope && scope.getComponentByName) {
            const result: ScopedComponentType = scope.getComponentByName(name);
            return result && idx < len - 1 ? result.context : result;
          }

          return null;
        }, this);
      }

      const resolved = find(
        components,
        component =>
        //组件的name属性可以使用模板语法。
          filter(component.props.name, component.props.data) === name ||
          component.props.id === name
      );
      return resolved || (parent && parent.getComponentByName(name));
    },

    getComponentById(id: string) {
      let root: AliasIScopedContext = this;
      // 找到顶端scoped
      while (root.parent && root.parent !== rootScopedContext) {
        root = root.parent;
      }

      // 向下查找
      let component = undefined;
      findTree([root], (item: TreeItem) =>
        item.getComponents().find((cmpt: ScopedComponentType) => {
            //组件的id属性可以使用模板语法。
          if (filter(cmpt.props.id, cmpt.props.data) === id) {
            component = cmpt;
            return true;
          }
          return false;
        })
      ) as ScopedComponentType | undefined;

      return component;
    }