package com.jetbrains.edu.coursecreator.projectView;

import com.intellij.ide.projectView.ViewSettings;
import com.intellij.ide.util.treeView.AbstractTreeNode;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.psi.PsiDirectory;
import com.intellij.psi.PsiElement;
import com.intellij.psi.PsiFile;
import com.jetbrains.edu.coursecreator.CCUtils;
import com.jetbrains.edu.learning.StudyLanguageManager;
import com.jetbrains.edu.learning.StudyTaskManager;
import com.jetbrains.edu.learning.StudyUtils;
import com.jetbrains.edu.learning.core.EduNames;
import com.jetbrains.edu.learning.courseFormat.Course;
import com.jetbrains.edu.learning.courseFormat.Task;
import com.jetbrains.edu.learning.projectView.TaskDirectoryNode;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;

public class CCTaskDirectoryNode extends TaskDirectoryNode {
  public CCTaskDirectoryNode(@NotNull Project project,
                             PsiDirectory value,
                             ViewSettings viewSettings,
                             @NotNull Task task) {
    super(project, value, viewSettings, task);
  }

  @Nullable
  @Override
  public AbstractTreeNode modifyChildNode(AbstractTreeNode childNode) {
    AbstractTreeNode node = super.modifyChildNode(childNode);
    if (node != null) {
      return node;
    }
    Object value = childNode.getValue();
    if (value instanceof PsiElement) {
      PsiFile psiFile = ((PsiElement)value).getContainingFile();
      VirtualFile virtualFile = psiFile.getVirtualFile();
      if (virtualFile == null) {
        return null;
      }
      if (StudyUtils.isTaskDescriptionFile(virtualFile.getName())) {
        return null;
      }
      if (!CCUtils.isTestsFile(myProject, virtualFile) || !myTask.hasSubtasks()) {
        return new CCStudentInvisibleFileNode(myProject, psiFile, myViewSettings);
      }

      Course course = StudyTaskManager.getInstance(myProject).getCourse();
      if (course == null) {
        return null;
      }
      StudyLanguageManager manager = StudyUtils.getLanguageManager(course);
      if (manager == null) {
        return new CCStudentInvisibleFileNode(myProject, psiFile, myViewSettings);
      }
      String testFileName = manager.getTestFileName();
      return isActiveSubtaskTest(virtualFile) ? new CCStudentInvisibleFileNode(myProject, psiFile, myViewSettings, testFileName) : null;
    }
    return null;
  }

  private boolean isActiveSubtaskTest(VirtualFile virtualFile) {
    if (!myTask.hasSubtasks()) {
      return true;
    }

    boolean isSubtaskTestFile = virtualFile.getName().contains(EduNames.SUBTASK_MARKER);
    if (myTask.getActiveSubtaskIndex() == 0) {
      return !isSubtaskTestFile;
    }
    if (!isSubtaskTestFile) {
      return false;
    }
    String nameWithoutExtension = virtualFile.getNameWithoutExtension();
    int stepMarkerStart = nameWithoutExtension.indexOf(EduNames.SUBTASK_MARKER);
    int stepIndex = Integer.valueOf(nameWithoutExtension.substring(EduNames.SUBTASK_MARKER.length() + stepMarkerStart));
    return stepIndex == myTask.getActiveSubtaskIndex();
  }
}

@@ -346,24 +346,65 @@
 si.PsiFile;%0A
+import com.intellij.psi.PsiNamedElement;%0A
 import com.j
@@ -1525,24 +1525,29 @@
  Psi
-File psiFile
+Element psiElement
  = 
-(
 (Psi
@@ -1558,14 +1558,50 @@
 ent)
+ 
 value
-)
+;%0A      PsiFile psiFile = psiElement
 .get
@@ -1840,183 +1840,8 @@
   %7D%0A
-      if (!CCUtils.isTestsFile(myProject, virtualFile) %7C%7C !myTask.hasSubtasks()) %7B%0A        return new CCStudentInvisibleFileNode(myProject, psiFile, myViewSettings);%0A      %7D%0A%0A
     
@@ -2174,215 +2174,979 @@
     
-String testFileName = manager.getTestFileName();%0A      return isActiveSubtaskTest(virtualFile) ? new CCStudentInvisibleFileNode(myProject, psiFile, myViewSettings, testFileName) : null;%0A    %7D%0A    return null
+if (!CCUtils.isTestsFile(myProject, virtualFile)) %7B%0A        return new CCStudentInvisibleFileNode(myProject, psiFile, myViewSettings);%0A      %7D%0A      if (!myTask.hasSubtasks()) %7B%0A        return new CCStudentInvisibleFileNode(myProject, psiFile, myViewSettings, getTestNodeName(manager, psiElement));%0A      %7D%0A      String testFileName = getTestNodeName(manager, psiElement);%0A      return isActiveSubtaskTest(virtualFile) ? new CCStudentInvisibleFileNode(myProject, psiFile, myViewSettings, testFileName) : null;%0A    %7D%0A    return null;%0A  %7D%0A%0A  @NotNull%0A  private static String getTestNodeName(StudyLanguageManager manager, PsiElement psiElement) %7B%0A    String defaultTestName = manager.getTestFileName();%0A    if (psiElement instanceof PsiFile) %7B%0A      return defaultTestName;%0A    %7D%0A    if (psiElement instanceof PsiNamedElement) %7B%0A      String name = ((PsiNamedElement)psiElement).getName();%0A      return name != null ? name : defaultTestName;%0A    %7D%0A    return defaultTestName
 ;%0A  

support for correct presentation of Class Nodes