/*
 * 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.pom.wrappers;

import com.intellij.lang.ASTNode;
import com.intellij.pom.PomModel;
import com.intellij.pom.PomModelAspect;
import com.intellij.pom.event.PomModelEvent;
import com.intellij.pom.tree.TreeAspect;
import com.intellij.pom.tree.events.ChangeInfo;
import com.intellij.pom.tree.events.ReplaceChangeInfo;
import com.intellij.pom.tree.events.TreeChange;
import com.intellij.pom.tree.events.TreeChangeEvent;
import com.intellij.pom.tree.events.impl.ChangeInfoImpl;
import com.intellij.pom.tree.events.impl.TreeChangeImpl;
import com.intellij.psi.PsiElement;
import com.intellij.psi.PsiFile;
import com.intellij.psi.impl.PsiManagerImpl;
import com.intellij.psi.impl.PsiTreeChangeEventImpl;
import com.intellij.psi.impl.source.SourceTreeToPsiMap;

import java.util.Collections;

public class PsiEventWrapperAspect implements PomModelAspect{
  private final TreeAspect myTreeAspect;

  public PsiEventWrapperAspect(PomModel model, TreeAspect aspect) {
    myTreeAspect = aspect;
    model.registerAspect(PsiEventWrapperAspect.class, this, Collections.singleton((PomModelAspect)aspect));
  }

  @Override
  public void update(PomModelEvent event) {
    final TreeChangeEvent changeSet = (TreeChangeEvent)event.getChangeSet(myTreeAspect);
    if(changeSet == null) return;
    sendAfterEvents(changeSet);
  }

  private static void sendAfterEvents(TreeChangeEvent changeSet) {
    ASTNode rootElement = changeSet.getRootElement();
    final PsiFile file = (PsiFile)SourceTreeToPsiMap.treeElementToPsi(rootElement);
    final PsiManagerImpl manager = (PsiManagerImpl)file.getManager();
    if(manager == null) return;

    if (!file.isPhysical()) {
      manager.afterChange(false);
      return;
    }
    final ASTNode[] changedElements = changeSet.getChangedElements();
    for (ASTNode changedElement : changedElements) {
      TreeChange changesByElement = changeSet.getChangesByElement(changedElement);
      PsiElement psiParent = null;

      while (changedElement != null &&
             ((psiParent = changedElement.getPsi()) == null || !checkPsiForChildren(changesByElement.getAffectedChildren()))) {
        final ASTNode parent = changedElement.getTreeParent();
        final ChangeInfoImpl changeInfo = ChangeInfoImpl.create(ChangeInfo.CONTENTS_CHANGED, changedElement);
        changeInfo.compactChange(changesByElement);
        changesByElement = new TreeChangeImpl(parent);
        changesByElement.addChange(changedElement, changeInfo);
        changedElement = parent;
      }
      if (changedElement == null) continue;

      final ASTNode[] affectedChildren = changesByElement.getAffectedChildren();

      for (final ASTNode treeElement : affectedChildren) {
        PsiTreeChangeEventImpl psiEvent = new PsiTreeChangeEventImpl(manager);
        psiEvent.setParent(psiParent);
        psiEvent.setFile(file);

        final PsiElement psiChild = treeElement.getPsi();
        psiEvent.setChild(psiChild);

        final ChangeInfo changeByChild = changesByElement.getChangeByChild(treeElement);
        switch (changeByChild.getChangeType()) {
          case ChangeInfo.ADD:
            psiEvent.setOffset(treeElement.getStartOffset());
            psiEvent.setOldLength(0);
            manager.childAdded(psiEvent);
            break;
          case ChangeInfo.REPLACE:
            final ReplaceChangeInfo change = (ReplaceChangeInfo)changeByChild;
            psiEvent.setOffset(treeElement.getStartOffset());
            final ASTNode replaced = change.getReplaced();
            psiEvent.setOldChild(replaced.getPsi());
            psiEvent.setNewChild(psiChild);
            psiEvent.setOldLength(replaced.getTextLength());
            manager.childReplaced(psiEvent);
            break;
          case ChangeInfo.CONTENTS_CHANGED:
            psiEvent.setOffset(treeElement.getStartOffset());
            psiEvent.setParent(psiChild);
            psiEvent.setOldLength(changeByChild.getOldLength());
            manager.childrenChanged(psiEvent);
            break;
          case ChangeInfo.REMOVED:
            psiEvent.setOffset(changesByElement.getChildOffsetInNewTree(treeElement));
            psiEvent.setOldParent(psiParent);
            psiEvent.setOldChild(psiChild);
            psiEvent.setOldLength(changeByChild.getOldLength());
            manager.childRemoved(psiEvent);
            break;
        }
      }
    }
  }

  private static boolean checkPsiForChildren(final ASTNode[] affectedChildren) {
    for (final ASTNode astNode : affectedChildren) {
      //if (TreeUtil.isCollapsedChameleon(astNode)) return false;
      if (astNode.getPsi() == null) return false;
    }
    return true;
  }
}
