Java tutorial
/******************************************************************************* * Copyright (c) 2005, 2006 IBM Corporation and others. All rights reserved. This * program and the accompanying materials are made available under the terms of * the Eclipse Public License v1.0 which accompanies this distribution, and is * available at http://www.eclipse.org/legal/epl-v10.html * * Contributors: Sian January - initial version ******************************************************************************/ package org.eclipse.ajdt.internal.ui.visualiser; import java.util.ArrayList; import java.util.List; import java.util.Set; import org.eclipse.ajdt.core.AJLog; import org.eclipse.ajdt.core.BuildConfig; import org.eclipse.ajdt.core.javaelements.AJCompilationUnit; import org.eclipse.contribution.jdt.IsWovenTester; import org.eclipse.contribution.visualiser.VisualiserPlugin; import org.eclipse.contribution.visualiser.core.ProviderManager; import org.eclipse.contribution.visualiser.interfaces.IGroup; import org.eclipse.contribution.visualiser.interfaces.IMember; import org.eclipse.contribution.visualiser.jdtImpl.JDTContentProvider; import org.eclipse.contribution.visualiser.jdtImpl.JDTGroup; import org.eclipse.contribution.visualiser.jdtImpl.JDTMember; import org.eclipse.contribution.visualiser.simpleImpl.SimpleMember; import org.eclipse.contribution.visualiser.utils.JDTUtils; import org.eclipse.core.resources.IFile; import org.eclipse.core.resources.IProject; import org.eclipse.jdt.core.ICompilationUnit; import org.eclipse.jdt.core.IJavaElement; import org.eclipse.jdt.core.IJavaProject; import org.eclipse.jdt.core.IPackageFragment; import org.eclipse.jdt.core.JavaModelException; import org.eclipse.jface.viewers.ISelection; import org.eclipse.jface.viewers.IStructuredSelection; import org.eclipse.ui.IWorkbenchPart; /** * AJDT Content Provider for the Visualiser. */ public class AJDTContentProvider extends JDTContentProvider { List<IGroup> currentGroups; List<IMember> currentMembers; // Access this variable via its getter method, which handles initialisation private Set<IFile> includedFiles; /** * Get all the groups to display. * * @see org.eclipse.contribution.visualiser.interfaces.IContentProvider#getAllGroups() */ public List<IGroup> getAllGroups() { synchronized (this) { if (currentGroups == null) { updateData(); } } return currentGroups; } /** * Get all the members to display. * * @see org.eclipse.contribution.visualiser.interfaces.IContentProvider#getAllMembers() */ public List<IMember> getAllMembers() { synchronized (this) { if (currentMembers == null) { updateData(); } } return currentMembers; } /** * Keeps the currentJavaElement and currentProject information up to date in * this class, as this method is called whenever a user changes their * selection in the workspace. */ public void selectionChanged(IWorkbenchPart workbenchPart, ISelection selection) { /* * What is the significance of this check? * * 'If we are not the current content provider, we don't need to bother * updating to reflect the new selection'? * * Yes, but what does it meant to be the current content provider? It's * not analagous to being the curerntly selected perspective. * * Also, this code still gets called, even when the Visualiser * perspective has been closed. Guess it's still loaded. * * -spyoung */ if (!(ProviderManager.getContentProvider().equals(this))) { return; } boolean updateRequired = false; if (selection instanceof IStructuredSelection) { IStructuredSelection structuredSelection = (IStructuredSelection) selection; Object firstElement = structuredSelection.getFirstElement(); if (firstElement != null) { if (firstElement instanceof IJavaElement) { IJavaElement javaElement = (IJavaElement) firstElement; if (currentlySelectedJE == javaElement) { return; } currentlySelectedJE = javaElement; updateRequired = true; if (javaElement.getJavaProject() != null) { setCurrentProject(javaElement.getJavaProject()); } } } } if (updateRequired) { reset(); VisualiserPlugin.refresh(); } } /** * Get the data for the current selection. * * @param members - * add members to the List being returned if true, otherwise add * groups * @return data */ private void updateData() { if (ProviderManager.getMarkupProvider() instanceof AJDTMarkupProvider) { ((AJDTMarkupProvider) ProviderManager.getMarkupProvider()).resetMarkupsAndKinds(); } long stime = System.currentTimeMillis(); List<IGroup> newGroups = new ArrayList<IGroup>(); List<IMember> newMembers = new ArrayList<IMember>(); if (currentProject != null) { try { if (currentlySelectedJE.getElementType() == IJavaElement.JAVA_PROJECT) { // Process contents of a Java project IPackageFragment[] packageFragments = ((IJavaProject) currentlySelectedJE) .getPackageFragments(); for (int i = 0; i < packageFragments.length; i++) { if (!(packageFragments[i].isReadOnly())) { addMembersAndGroups(newGroups, newMembers, packageFragments[i]); } } } else if (currentlySelectedJE.getElementType() == IJavaElement.PACKAGE_FRAGMENT) { // Process contents of a Java package(fragment) IPackageFragment packageFragment = (IPackageFragment) currentlySelectedJE; addMembersAndGroups(newGroups, newMembers, packageFragment); } else if (currentlySelectedJE.getElementType() == IJavaElement.COMPILATION_UNIT) { // Process individually selected compilation units JDTMember member = null; if (getIncludedFiles(currentProject.getProject()).contains(currentlySelectedJE.getResource())) { String memberName = currentlySelectedJE.getElementName(); if (memberName.endsWith(".java")) { //$NON-NLS-1$ memberName = memberName.substring(0, memberName.length() - 5); } else if (memberName.endsWith(".aj")) { //$NON-NLS-1$ memberName = memberName.substring(0, memberName.length() - 3); } member = new JDTMember(memberName, currentlySelectedJE); member.setSize(getLength((ICompilationUnit) currentlySelectedJE)); newMembers.add(member); } if (member != null) { IPackageFragment packageFrag = (IPackageFragment) ((ICompilationUnit) currentlySelectedJE) .getParent(); boolean defaultPackage = packageFrag.isDefaultPackage(); // ?!? Need to confirm a group for the pkg frag is OK in // the case of a selection like thiss IGroup group = new JDTGroup(packageFrag.getElementName()); if (defaultPackage) { group.setName("(default package)"); //$NON-NLS-1$ group.setTooltip("(default package)"); //$NON-NLS-1$ } if (defaultPackage) { member.setFullName(member.getName()); } group.add(member); newGroups.add(group); } } } catch (JavaModelException jme) { } long etime = System.currentTimeMillis(); AJLog.log("AJDTContentProvider.updateData() executed - took " + (etime - stime) + "ms"); //$NON-NLS-1$ //$NON-NLS-2$ } currentMembers = newMembers; currentGroups = newGroups; } private void addMembersAndGroups(List<IGroup> newGroups, List<IMember> newMembers, IPackageFragment packageFragment) { List<IMember> classes = getMembersForPackage(packageFragment); if (classes.size() > 0) { boolean defaultPackage = packageFragment.isDefaultPackage(); IGroup group = new JDTGroup(packageFragment.getElementName()); if (defaultPackage) { group.setName("(default package)"); //$NON-NLS-1$ group.setTooltip("(default package)"); //$NON-NLS-1$ } for (IMember jdtMember : classes) { group.add(jdtMember); newMembers.add(jdtMember); if (defaultPackage) { ((SimpleMember) jdtMember).setFullName(jdtMember.getName()); } } newGroups.add(group); } } /** * Override super to reset the colour list when the project changes. * * @see org.eclipse.contribution.visualiser.jdtImpl.JDTContentProvider#setCurrentProject(org.eclipse.jdt.core.IJavaProject) */ protected void setCurrentProject(IJavaProject newProject) { if (currentProject == null || !currentProject.equals(newProject)) { if (ProviderManager.getMarkupProvider() instanceof AJDTMarkupProvider) { ((AJDTMarkupProvider) ProviderManager.getMarkupProvider()).resetColours(); } currentProject = newProject; } } /** * Clear current cached project/package/file selections. */ public void reset() { currentGroups = null; currentMembers = null; // clear currently included files includedFiles = null; } /** * Process a mouse click on a member * * @see org.eclipse.contribution.visualiser.interfaces.IContentProvider#processMouseclick(IMember, * boolean, int) */ public boolean processMouseclick(IMember member, boolean markupWasClicked, int buttonClicked) { if (buttonClicked != 1) { return true; } if (markupWasClicked) { return false; } if (member instanceof JDTMember) { IJavaElement jEl = ((JDTMember) member).getResource(); if (jEl != null) { JDTUtils.openInEditor(jEl.getResource(), JDTUtils.getClassDeclLineNum(jEl)); } } return false; } /** * Get all JDT members for the given IPackageFragment (Java package) * * @param packageFragment * @return List of JDTMembers */ public List<IMember> getMembersForPackage(IPackageFragment packageFragment) { List<IMember> returningClasses = new ArrayList<IMember>(); try { if (containsUsefulStuff(packageFragment)) { IJavaElement[] javaElements = packageFragment.getChildren(); for (int j = 0; j < javaElements.length; j++) { if (javaElements[j].getElementType() == IJavaElement.COMPILATION_UNIT) { if (getIncludedFiles(packageFragment.getJavaProject().getProject()) .contains(javaElements[j].getResource())) { // Bug 157776: Filter out duplicate compilation units here, not in calling methods if (!IsWovenTester.isWeavingActive() && !(javaElements[j] instanceof AJCompilationUnit) && javaElements[j].getElementName() != null && javaElements[j].getElementName().endsWith(".aj")) { //$NON-NLS-1$ // Do nothing } else { String memberName = javaElements[j].getElementName(); if (!shouldIgnore(memberName)) { if (memberName.endsWith(".java")) { //$NON-NLS-1$ memberName = memberName.substring(0, memberName.length() - 5); } else if (memberName.endsWith(".aj")) { //$NON-NLS-1$ memberName = memberName.substring(0, memberName.length() - 3); } JDTMember member = new JDTMember(memberName, javaElements[j]); member.setSize(getLength((ICompilationUnit) javaElements[j])); returningClasses.add(member); } } } } } } } catch (JavaModelException jme) { } return returningClasses; } /** * Ignore package-info files * @param memberName * @return */ protected boolean shouldIgnore(String memberName) { return memberName.equals("package-info.java"); } /* * Lazy initialisation method added to avoid null pointer problem(s!) which * were occurring due to assumed state of includedFiles variable which was * then compounded by the assumed state of the currentProject variable (!). * * -spyoung */ private Set<IFile> getIncludedFiles(IProject project) { if (includedFiles == null) { includedFiles = BuildConfig.getIncludedSourceFiles(project); } return includedFiles; } }