resolveTree static method

RenderObjectElement? resolveTree(
  1. Offset buttonOffset,
  2. BuildContext context
)

Implementation

static RenderObjectElement? resolveTree(
    Offset buttonOffset, BuildContext context) {
  Element? currentPage;
  final List<RenderObjectElement> inBounds = <RenderObjectElement>[];
  final Rect focus =
      Rect.fromLTWH(buttonOffset.dx, buttonOffset.dy, diameter, diameter);
  // 记录根路由,用以过滤overlay
  final ModalRoute<dynamic>? rootRoute = ModalRoute.of<dynamic>(context);

  void filter(Element element) {
    // 兼容IOS,IOS的MaterialApp会在Navigator后再插入一个PositionedDirectional控件,用以处理右滑关闭手势,遍历的时候跳过该控件
    // ignore:
    if (element.widget is! PositionedDirectional) {
      if (element is RenderObjectElement &&
          element.renderObject is RenderBox) {
        final ModalRoute<dynamic>? route = ModalRoute.of<dynamic>(element);
        // overlay不包含route信息,通过ModalRoute.of会获取到当前所在materialapp在其父节点内的route,此处对overlay做过滤。只能过滤掉直接添加在根MaterialApp的overlay,
        // 并且该overlay的子widget不能包含materialApp或navigator
        if (route != null && route != rootRoute) {
          currentPage = element;
          final RenderBox renderBox = element.renderObject as RenderBox;
          if (renderBox.hasSize && renderBox.attached) {
            final Offset offset = renderBox.localToGlobal(Offset.zero);
            if (isOverlap(
                focus,
                Rect.fromLTWH(offset.dx, offset.dy, element.size!.width,
                    element.size!.height))) {
              inBounds.add(element);
            }
          }
        }
      }
      element.visitChildren(filter);
    }
  }

  context.visitChildElements(filter);
  RenderObjectElement? topElement;
  final ModalRoute<dynamic>? route =
      currentPage != null ? ModalRoute.of<dynamic>(currentPage!) : null;
  for (final RenderObjectElement element in inBounds) {
    if ((route == null || ModalRoute.of(element) == route) &&
        checkSelected(topElement, element, buttonOffset)) {
      topElement = element;
    }
  }
  return topElement;
}