/*
 * Copyright 2000-2009 JetBrains s.r.o.
 *
 * 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.
 */

package com.intellij.uiDesigner.designSurface;

import com.intellij.ide.DataManager;
import com.intellij.openapi.actionSystem.AnAction;
import com.intellij.openapi.actionSystem.AnActionEvent;
import com.intellij.openapi.actionSystem.DataContext;
import com.intellij.openapi.actionSystem.DefaultActionGroup;
import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.ui.popup.JBPopupFactory;
import com.intellij.openapi.ui.popup.ListPopup;
import com.intellij.openapi.util.Comparing;
import com.intellij.pom.Navigatable;
import com.intellij.psi.*;
import com.intellij.psi.controlFlow.DefUseUtil;
import com.intellij.psi.presentation.java.ClassPresentationUtil;
import com.intellij.psi.search.LocalSearchScope;
import com.intellij.psi.search.searches.ReferencesSearch;
import com.intellij.psi.util.PsiTreeUtil;
import com.intellij.uiDesigner.FormEditingUtil;
import com.intellij.uiDesigner.UIDesignerBundle;
import com.intellij.uiDesigner.lw.IRootContainer;
import com.intellij.uiDesigner.radComponents.RadComponent;
import com.intellij.util.Processor;
import icons.UIDesignerIcons;
import org.jetbrains.annotations.Nullable;

import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.beans.BeanInfo;
import java.beans.EventSetDescriptor;
import java.beans.IntrospectionException;
import java.beans.Introspector;

/**
 * @author yole
 */
public class ListenerNavigateButton extends JButton implements ActionListener {
  private static final Logger LOG = Logger.getInstance("#com.intellij.uiDesigner.designSurface.ListenerNavigateButton");

  private final RadComponent myComponent;

  public ListenerNavigateButton(RadComponent component) {
    myComponent = component;
    setIcon(UIDesignerIcons.Listener);
    setOpaque(false);
    setFocusable(false);
    setBorderPainted(false);
    setSize(new Dimension(getIcon().getIconWidth(), getIcon().getIconHeight()));
    addActionListener(this);
  }

  public void actionPerformed(ActionEvent e) {
    showNavigatePopup(myComponent, false);
  }

  public static void showNavigatePopup(final RadComponent component, final boolean showIfEmpty) {
    final DefaultActionGroup actionGroup = prepareActionGroup(component);
    if (actionGroup != null && actionGroup.getChildrenCount() == 0 && showIfEmpty) {
      actionGroup.add(new MyNavigateAction(UIDesignerBundle.message("navigate.to.listener.empty"), null));
    }
    if (actionGroup != null && actionGroup.getChildrenCount() > 0) {
      final DataContext context = DataManager.getInstance().getDataContext(component.getDelegee());
      final JBPopupFactory factory = JBPopupFactory.getInstance();
      final ListPopup popup = factory.createActionGroupPopup(UIDesignerBundle.message("navigate.to.listener.title"), actionGroup, context,
                                                             JBPopupFactory.ActionSelectionAid.NUMBERING, true);
      FormEditingUtil.showPopupUnderComponent(popup, component);
    }
  }

  @Nullable
  public static DefaultActionGroup prepareActionGroup(final RadComponent component) {
    final IRootContainer root = FormEditingUtil.getRoot(component);
    final String classToBind = root == null ? null : root.getClassToBind();
    if (classToBind != null) {
      final PsiClass aClass = FormEditingUtil.findClassToBind(component.getModule(), classToBind);
      if (aClass != null) {
        final PsiField boundField = aClass.findFieldByName(component.getBinding(), false);
        if (boundField != null) {
          return buildNavigateActionGroup(component, boundField);
        }
      }
    }
    return null;
  }

  private static DefaultActionGroup buildNavigateActionGroup(RadComponent component, final PsiField boundField) {
    final DefaultActionGroup actionGroup = new DefaultActionGroup();
    final EventSetDescriptor[] eventSetDescriptors;
    try {
      BeanInfo beanInfo = Introspector.getBeanInfo(component.getComponentClass());
      eventSetDescriptors = beanInfo.getEventSetDescriptors();
    }
    catch (IntrospectionException e) {
      LOG.error(e);
      return null;
    }
    final LocalSearchScope scope = new LocalSearchScope(boundField.getContainingFile());
    ReferencesSearch.search(boundField, scope).forEach(new Processor<PsiReference>() {
      public boolean process(final PsiReference ref) {
        final PsiElement element = ref.getElement();
        if (element.getParent() instanceof PsiReferenceExpression) {
          PsiReferenceExpression refExpr = (PsiReferenceExpression) element.getParent();
          if (refExpr.getParent() instanceof PsiMethodCallExpression) {
            PsiMethodCallExpression methodCall = (PsiMethodCallExpression) refExpr.getParent();
            final PsiElement psiElement = refExpr.resolve();
            if (psiElement instanceof PsiMethod) {
              PsiMethod method = (PsiMethod) psiElement;
              for(EventSetDescriptor eventSetDescriptor: eventSetDescriptors) {
                if (Comparing.equal(eventSetDescriptor.getAddListenerMethod().getName(), method.getName())) {
                  final String eventName = eventSetDescriptor.getName();
                  final PsiExpression[] args = methodCall.getArgumentList().getExpressions();
                  if (args.length > 0) {
                    addListenerRef(actionGroup, eventName, args[0]);
                  }
                }
              }
            }
          }
        }
        return true;
      }
    });

    return actionGroup;
  }

  private static void addListenerRef(final DefaultActionGroup actionGroup, final String eventName, final PsiExpression listenerArg) {
    final PsiType type = listenerArg.getType();
    if (type instanceof PsiClassType) {
      PsiClass listenerClass = ((PsiClassType) type).resolve();
      if (listenerClass != null) {
        if (!isAbstractOrInterface(listenerClass)) {
          actionGroup.add(new MyNavigateAction(eventName + ": " + ClassPresentationUtil.getNameForClass(listenerClass, false),
                                               listenerClass));
          return;
        }
        else if (listenerArg instanceof PsiReferenceExpression) {
          final PsiElement psiElement = ((PsiReferenceExpression)listenerArg).resolve();
          if (psiElement instanceof PsiVariable) {
            PsiCodeBlock codeBlock = PsiTreeUtil.getParentOfType(listenerArg, PsiCodeBlock.class);
            final PsiElement[] defs = DefUseUtil.getDefs(codeBlock, (PsiVariable)psiElement, listenerArg);
            if (defs.length == 1) {
              final PsiElement def = defs[0];
              if (def instanceof PsiVariable) {
                PsiVariable var = (PsiVariable) def;
                if (var.getInitializer() != listenerArg) {
                  addListenerRef(actionGroup, eventName, var.getInitializer());
                  return;
                }
              }
              else if (def.getParent() instanceof PsiAssignmentExpression) {
                final PsiAssignmentExpression assignmentExpr = (PsiAssignmentExpression)def.getParent();
                if (def.equals(assignmentExpr.getLExpression())) {
                  addListenerRef(actionGroup, eventName, assignmentExpr.getRExpression());
                  return;
                }
              }
            }
          }
        }
      }
    }
    actionGroup.add(new MyNavigateAction(eventName + ": " + listenerArg.getText(), listenerArg));
  }

  private static boolean isAbstractOrInterface(final PsiClass element) {
    return element.isInterface() ||
           element.hasModifierProperty(PsiModifier.ABSTRACT);
  }

  private static class MyNavigateAction extends AnAction {
    private final PsiElement myElement;

    public MyNavigateAction(final String name, PsiElement element) {
      super(name);
      myElement = element;
    }

    public void actionPerformed(AnActionEvent e) {
      if (myElement instanceof Navigatable) {
        ((Navigatable) myElement).navigate(true);
      }
    }

    @Override public void update(AnActionEvent e) {
      e.getPresentation().setEnabled(myElement != null &&
                                     (!(myElement instanceof PsiClass) || !isAbstractOrInterface((PsiClass)myElement)));
    }
  }
}
