/*
 * Copyright 2000-2014 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 org.jetbrains.plugins.groovy.annotator.intentions.dynamic;

import com.intellij.openapi.project.Project;
import com.intellij.openapi.wm.ToolWindowManager;
import com.intellij.psi.*;
import com.intellij.psi.javadoc.PsiDocComment;
import com.intellij.psi.search.GlobalSearchScope;
import com.intellij.psi.search.ProjectScope;
import com.intellij.psi.search.SearchScope;
import com.intellij.ui.treeStructure.treetable.ListTreeTableModelOnColumns;
import com.intellij.ui.treeStructure.treetable.TreeTable;
import com.intellij.util.IncorrectOperationException;
import com.intellij.util.ui.tree.TreeUtil;
import icons.JetgroovyIcons;
import org.jetbrains.annotations.NonNls;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.plugins.groovy.annotator.intentions.dynamic.elements.DClassElement;
import org.jetbrains.plugins.groovy.annotator.intentions.dynamic.elements.DPropertyElement;
import org.jetbrains.plugins.groovy.lang.psi.impl.synthetic.GrDynamicImplicitElement;
import org.jetbrains.plugins.groovy.lang.psi.impl.synthetic.GrImplicitVariableImpl;
import org.jetbrains.plugins.groovy.lang.psi.impl.statements.expressions.TypesUtil;
import org.jetbrains.plugins.groovy.lang.psi.util.PsiUtil;

import javax.swing.*;
import javax.swing.tree.DefaultMutableTreeNode;
import javax.swing.tree.TreePath;

/**
 * @author ilyas
 */
public class GrDynamicImplicitProperty extends GrImplicitVariableImpl implements GrDynamicImplicitElement, PsiField {
  private final String myContainingClassName;
  private final Project myProject;

  public GrDynamicImplicitProperty(PsiManager manager, @NonNls String name, @NonNls @NotNull String type, String containingClassName) {
    super(manager, name, type, null);
    myContainingClassName = containingClassName;
    myProject = manager.getProject();
    setOriginInfo("dynamic property");
  }

  @Override
  @Nullable
  public PsiClass getContainingClassElement() {
    final PsiClassType containingClassType = JavaPsiFacade.getInstance(getProject()).getElementFactory().
        createTypeByFQClassName(myContainingClassName, ProjectScope.getAllScope(getProject()));

    return containingClassType.resolve();
  }

  @Override
  public String getContainingClassName() {
    return myContainingClassName;
  }

  @Override
  public PsiFile getContainingFile() {
    final PsiClass psiClass = getContainingClassElement();
    if (psiClass == null) return null;

    return psiClass.getContainingFile();
  }

  @Override
  public PsiElement setName(@NotNull String name) throws IncorrectOperationException {
    DynamicManager.getInstance(getProject()).replaceDynamicPropertyName(myContainingClassName, getName(), name);
    return super.setName(name);
  }

  @Override
  public String getPresentableText() {
    return getName();
  }

  @Override
  @Nullable
  public String getLocationString() {
    return null;
  }

  @Override
  @NotNull
  public SearchScope getUseScope() {
    return GlobalSearchScope.projectScope(myProject);
  }

  @Override
  public void navigate(boolean requestFocus) {
    if (canNavigateToSource()) {
      super.navigate(requestFocus);
      return;
    }
    DynamicToolWindowWrapper.getInstance(myProject).getToolWindow().activate(new Runnable() {
      @Override
      public void run() {
        DynamicToolWindowWrapper toolWindowWrapper = DynamicToolWindowWrapper.getInstance(myProject);
        final TreeTable treeTable = toolWindowWrapper.getTreeTable();
        final ListTreeTableModelOnColumns model = toolWindowWrapper.getTreeTableModel();

        Object root = model.getRoot();

        if (root == null || !(root instanceof DefaultMutableTreeNode)) return;

        DefaultMutableTreeNode treeRoot = ((DefaultMutableTreeNode) root);
        final PsiClass psiClass = getContainingClassElement();
        if (psiClass == null) return;

        final DefaultMutableTreeNode desiredNode;
        DPropertyElement dynamicProperty = null;
        PsiClass trueSuper = null;
        for (PsiClass aSuper : PsiUtil.iterateSupers(psiClass, true)) {
          dynamicProperty = DynamicManager.getInstance(myProject).findConcreteDynamicProperty(aSuper.getQualifiedName(), getName());

          if (dynamicProperty != null) {
            trueSuper = aSuper;
            break;
          }
        }

        if (trueSuper == null) return;

        final DefaultMutableTreeNode classNode = TreeUtil.findNodeWithObject(treeRoot, new DClassElement(myProject, trueSuper.getQualifiedName()));
        if (classNode == null) return;

        desiredNode = TreeUtil.findNodeWithObject(classNode, dynamicProperty);

        if (desiredNode == null) return;
        final TreePath path = TreeUtil.getPathFromRoot(desiredNode);

        treeTable.getTree().expandPath(path);
        treeTable.getTree().setSelectionPath(path);
        treeTable.getTree().fireTreeExpanded(path);

        ToolWindowManager.getInstance(myProject).getFocusManager().requestFocus(treeTable, true);
        treeTable.revalidate();
        treeTable.repaint();

      }
    }, true);
  }

  @Override
  public boolean canNavigateToSource() {
    return false;
  }

  @Override
  public boolean canNavigate() {
    return true;
  }

  @Override
  public boolean isWritable() {
    return true;
  }

  @Override
  @Nullable
  public Icon getIcon(boolean open) {
    return JetgroovyIcons.Groovy.Property;
  }

  @Override
  public boolean isValid() {
    return true;
  }

  @Override
  public PsiClass getContainingClass() {
    return getContainingClassElement();
  }

    @Override
    public PsiDocComment getDocComment() {
        return null;
    }

    @Override
    public boolean isDeprecated() {
        return false;
    }

  @Override
  public void setInitializer(@Nullable PsiExpression initializer) throws IncorrectOperationException {
    throw new IncorrectOperationException();
  }

  @NotNull
  @Override
  public PsiType getType() {
    PsiType type = super.getType();
    if (type instanceof PsiClassType && ((PsiClassType)type).resolve() == null) {
      return TypesUtil.getJavaLangObject(this);
    }
    return type;
  }
}
