// Copyright (C) 2025 The Android Open Source Project
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//      http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

import m from 'mithril';

import {classNames} from '../../../../base/classnames';
import {PopupMenu, MenuDivider, MenuTitle} from '../../../../widgets/menu';
import type {QueryNode} from '../../query_node';
import {Icon} from '../../../../widgets/icon';
import {buildMenuItems} from './menu_utils';
import {nodeRegistry} from '../node_registry';
import type {NodeDetailsAttrs} from '../../node_types';
import {NodeDetailsContent} from '../node_styling_widgets';

export interface NodeBoxAttrs {
  readonly node: QueryNode;
  readonly onAddOperationNode: (id: string, node: QueryNode) => void;
}

export function renderWarningIcon(node: QueryNode): m.Child {
  if (!node.context.issues || !node.context.issues.hasIssues()) return null;

  const iconClasses = classNames('pf-exp-node-box__warning-icon');

  return m(Icon, {
    className: iconClasses,
    icon: 'warning',
    title: node.context.issues.getTitle(),
  });
}

export function renderAddButton(attrs: NodeBoxAttrs): m.Child {
  const {node, onAddOperationNode} = attrs;

  const allowedChildren = nodeRegistry.getAllowedChildrenFor(node.type);
  if (allowedChildren.length === 0) {
    return null;
  }

  const addCb = (id: string) => onAddOperationNode(id, node);
  const multisourceMenuItems = buildMenuItems(
    'multisource',
    addCb,
    allowedChildren,
  );
  const modificationMenuItems = buildMenuItems(
    'modification',
    addCb,
    allowedChildren,
  );
  const exportMenuItems = buildMenuItems('export', addCb, allowedChildren);

  const sections: {title: string; items: m.Children[]}[] = [
    {title: 'Modifications', items: modificationMenuItems},
    {title: 'Operations', items: multisourceMenuItems},
    {title: 'Export', items: exportMenuItems},
  ].filter((s) => s.items.length > 0);

  if (sections.length === 0) {
    return null;
  }

  const menuItems: m.Children[] = [];
  for (let i = 0; i < sections.length; i++) {
    if (i > 0) {
      menuItems.push(m(MenuDivider));
    }
    menuItems.push(m(MenuTitle, {label: sections[i].title}));
    menuItems.push(...sections[i].items);
  }

  return m(
    PopupMenu,
    {
      trigger: m(Icon, {
        className: 'pf-exp-node-box-add-button',
        icon: 'add',
      }),
    },
    ...menuItems,
  );
}

function renderDetailsView(node: QueryNode): m.Child {
  const attrs: NodeDetailsAttrs = node.nodeDetails();
  return NodeDetailsContent(attrs.content);
}

export const NodeBox: m.Component<NodeBoxAttrs> = {
  view({attrs}) {
    const {node} = attrs;

    return [
      m(
        '.pf-exp-node-box__content',
        {
          class: classNames(node.type),
        },
        m('.pf-exp-node-box__details', renderDetailsView(node)),
      ),
      m(
        '.pf-exp-node-box__actions',
        renderAddButton(attrs),
        renderWarningIcon(node),
      ),
    ];
  },
};
