001: /*******************************************************************************
002: * Copyright (c) 2000, 2007 IBM Corporation and others.
003: * All rights reserved. This program and the accompanying materials
004: * are made available under the terms of the Eclipse Public License v1.0
005: * which accompanies this distribution, and is available at
006: * http://www.eclipse.org/legal/epl-v10.html
007: *
008: * Contributors:
009: * IBM Corporation - initial API and implementation
010: *******************************************************************************/package org.eclipse.jdt.internal.ui.wizards.buildpaths;
011:
012: import java.util.ArrayList;
013: import java.util.Arrays;
014: import java.util.Iterator;
015: import java.util.List;
016:
017: import org.eclipse.core.runtime.Assert;
018: import org.eclipse.core.runtime.IPath;
019: import org.eclipse.core.runtime.IStatus;
020: import org.eclipse.core.runtime.Path;
021: import org.eclipse.core.runtime.Status;
022:
023: import org.eclipse.core.resources.IResource;
024: import org.eclipse.core.resources.IWorkspaceRoot;
025: import org.eclipse.core.resources.ResourcesPlugin;
026:
027: import org.eclipse.jdt.core.ClasspathContainerInitializer;
028: import org.eclipse.jdt.core.IAccessRule;
029: import org.eclipse.jdt.core.IClasspathAttribute;
030: import org.eclipse.jdt.core.IClasspathContainer;
031: import org.eclipse.jdt.core.IClasspathEntry;
032: import org.eclipse.jdt.core.IJavaProject;
033: import org.eclipse.jdt.core.JavaCore;
034: import org.eclipse.jdt.core.JavaModelException;
035:
036: import org.eclipse.jdt.internal.corext.util.JavaModelUtil;
037:
038: import org.eclipse.jdt.launching.JavaRuntime;
039:
040: import org.eclipse.jdt.ui.JavaUI;
041:
042: import org.eclipse.jdt.internal.ui.JavaPlugin;
043:
044: public class CPListElement {
045:
046: public static final String SOURCEATTACHMENT = "sourcepath"; //$NON-NLS-1$
047: public static final String OUTPUT = "output"; //$NON-NLS-1$
048: public static final String EXCLUSION = "exclusion"; //$NON-NLS-1$
049: public static final String INCLUSION = "inclusion"; //$NON-NLS-1$
050:
051: public static final String ACCESSRULES = "accessrules"; //$NON-NLS-1$
052: public static final String COMBINE_ACCESSRULES = "combineaccessrules"; //$NON-NLS-1$
053:
054: public static final String JAVADOC = IClasspathAttribute.JAVADOC_LOCATION_ATTRIBUTE_NAME;
055: public static final String NATIVE_LIB_PATH = JavaRuntime.CLASSPATH_ATTR_LIBRARY_PATH_ENTRY;
056:
057: private IJavaProject fProject;
058:
059: private int fEntryKind;
060: private IPath fPath, fOrginalPath;
061: private IResource fResource;
062: private boolean fIsExported;
063: private boolean fIsMissing;
064:
065: private Object fParentContainer;
066:
067: private IClasspathEntry fCachedEntry;
068: private ArrayList fChildren;
069: private IPath fLinkTarget, fOrginalLinkTarget;
070:
071: private CPListElement() {
072: }
073:
074: public CPListElement(IJavaProject project, int entryKind,
075: IPath path, IResource res) {
076: this (null, project, entryKind, path, res);
077: }
078:
079: public CPListElement(Object parent, IJavaProject project,
080: int entryKind, IPath path, IResource res) {
081: this (parent, project, entryKind, path, res, null);
082: }
083:
084: public CPListElement(IJavaProject project, int entryKind) {
085: this (null, project, entryKind, null, null);
086: }
087:
088: public CPListElement(Object parent, IJavaProject project,
089: int entryKind, IPath path, IResource res, IPath linkTarget) {
090: fProject = project;
091:
092: fEntryKind = entryKind;
093: fPath = path;
094: fOrginalPath = path;
095: fLinkTarget = linkTarget;
096: fOrginalLinkTarget = linkTarget;
097: fChildren = new ArrayList();
098: fResource = res;
099: fIsExported = false;
100:
101: fIsMissing = false;
102: fCachedEntry = null;
103: fParentContainer = parent;
104:
105: switch (entryKind) {
106: case IClasspathEntry.CPE_SOURCE:
107: createAttributeElement(OUTPUT, null, true);
108: createAttributeElement(INCLUSION, new Path[0], true);
109: createAttributeElement(EXCLUSION, new Path[0], true);
110: createAttributeElement(NATIVE_LIB_PATH, null, false);
111: break;
112: case IClasspathEntry.CPE_LIBRARY:
113: case IClasspathEntry.CPE_VARIABLE:
114: createAttributeElement(SOURCEATTACHMENT, null, true);
115: createAttributeElement(JAVADOC, null, false);
116: createAttributeElement(NATIVE_LIB_PATH, null, false);
117: createAttributeElement(ACCESSRULES, new IAccessRule[0],
118: true);
119: break;
120: case IClasspathEntry.CPE_PROJECT:
121: createAttributeElement(ACCESSRULES, new IAccessRule[0],
122: true);
123: createAttributeElement(COMBINE_ACCESSRULES, Boolean.FALSE,
124: true); // not rendered
125: createAttributeElement(NATIVE_LIB_PATH, null, false);
126: break;
127: case IClasspathEntry.CPE_CONTAINER:
128: createAttributeElement(ACCESSRULES, new IAccessRule[0],
129: true);
130: try {
131: IClasspathContainer container = JavaCore
132: .getClasspathContainer(fPath, fProject);
133: if (container != null) {
134: IClasspathEntry[] entries = container
135: .getClasspathEntries();
136: if (entries != null) { // invalid container implementation
137: for (int i = 0; i < entries.length; i++) {
138: IClasspathEntry entry = entries[i];
139: if (entry != null) {
140: CPListElement curr = createFromExisting(
141: this , entry, fProject);
142: fChildren.add(curr);
143: } else {
144: JavaPlugin
145: .logErrorMessage("Null entry in container '" + fPath + "'"); //$NON-NLS-1$//$NON-NLS-2$
146: }
147: }
148: } else {
149: JavaPlugin
150: .logErrorMessage("container returns null as entries: '" + fPath + "'"); //$NON-NLS-1$//$NON-NLS-2$
151: }
152: }
153: } catch (JavaModelException e) {
154: }
155: createAttributeElement(NATIVE_LIB_PATH, null, false);
156: break;
157: default:
158: }
159: }
160:
161: public IClasspathEntry getClasspathEntry() {
162: if (fCachedEntry == null) {
163: fCachedEntry = newClasspathEntry();
164: }
165: return fCachedEntry;
166: }
167:
168: private IClasspathAttribute[] getClasspathAttributes() {
169: ArrayList res = new ArrayList();
170: for (int i = 0; i < fChildren.size(); i++) {
171: Object curr = fChildren.get(i);
172: if (curr instanceof CPListElementAttribute) {
173: CPListElementAttribute elem = (CPListElementAttribute) curr;
174: if (!elem.isBuiltIn() && elem.getValue() != null) {
175: res.add(elem.getClasspathAttribute());
176: }
177: }
178: }
179: return (IClasspathAttribute[]) res
180: .toArray(new IClasspathAttribute[res.size()]);
181: }
182:
183: private IClasspathEntry newClasspathEntry() {
184:
185: IClasspathAttribute[] extraAttributes = getClasspathAttributes();
186: switch (fEntryKind) {
187: case IClasspathEntry.CPE_SOURCE:
188: IPath[] inclusionPattern = (IPath[]) getAttribute(INCLUSION);
189: IPath[] exclusionPattern = (IPath[]) getAttribute(EXCLUSION);
190: IPath outputLocation = (IPath) getAttribute(OUTPUT);
191: return JavaCore.newSourceEntry(fPath, inclusionPattern,
192: exclusionPattern, outputLocation, extraAttributes);
193: case IClasspathEntry.CPE_LIBRARY: {
194: IPath attach = (IPath) getAttribute(SOURCEATTACHMENT);
195: IAccessRule[] accesRules = (IAccessRule[]) getAttribute(ACCESSRULES);
196: return JavaCore.newLibraryEntry(fPath, attach, null,
197: accesRules, extraAttributes, isExported());
198: }
199: case IClasspathEntry.CPE_PROJECT: {
200: IAccessRule[] accesRules = (IAccessRule[]) getAttribute(ACCESSRULES);
201: boolean combineAccessRules = ((Boolean) getAttribute(COMBINE_ACCESSRULES))
202: .booleanValue();
203: return JavaCore.newProjectEntry(fPath, accesRules,
204: combineAccessRules, extraAttributes, isExported());
205: }
206: case IClasspathEntry.CPE_CONTAINER: {
207: IAccessRule[] accesRules = (IAccessRule[]) getAttribute(ACCESSRULES);
208: return JavaCore.newContainerEntry(fPath, accesRules,
209: extraAttributes, isExported());
210: }
211: case IClasspathEntry.CPE_VARIABLE: {
212: IPath varAttach = (IPath) getAttribute(SOURCEATTACHMENT);
213: IAccessRule[] accesRules = (IAccessRule[]) getAttribute(ACCESSRULES);
214: return JavaCore.newVariableEntry(fPath, varAttach, null,
215: accesRules, extraAttributes, isExported());
216: }
217: default:
218: return null;
219: }
220: }
221:
222: /**
223: * Gets the class path entry path.
224: * @return returns the path
225: * @see IClasspathEntry#getPath()
226: */
227: public IPath getPath() {
228: return fPath;
229: }
230:
231: /**
232: * Gets the class path entry kind.
233: * @return the entry kind
234: * @see IClasspathEntry#getEntryKind()
235: */
236: public int getEntryKind() {
237: return fEntryKind;
238: }
239:
240: /**
241: * Entries without resource are either non existing or a variable entry
242: * External jars do not have a resource
243: * @return returns the resource
244: */
245: public IResource getResource() {
246: return fResource;
247: }
248:
249: public CPListElementAttribute setAttribute(String key, Object value) {
250: CPListElementAttribute attribute = findAttributeElement(key);
251: if (attribute == null) {
252: return null;
253: }
254: if (key.equals(EXCLUSION) || key.equals(INCLUSION)) {
255: Assert.isTrue(value != null
256: || fEntryKind != IClasspathEntry.CPE_SOURCE);
257: }
258:
259: if (key.equals(ACCESSRULES)) {
260: Assert.isTrue(value != null
261: || fEntryKind == IClasspathEntry.CPE_SOURCE);
262: }
263: if (key.equals(COMBINE_ACCESSRULES)) {
264: Assert.isTrue(value instanceof Boolean);
265: }
266:
267: attribute.setValue(value);
268: return attribute;
269: }
270:
271: public boolean addToExclusions(IPath path) {
272: String key = CPListElement.EXCLUSION;
273: return addFilter(path, key);
274: }
275:
276: public boolean addToInclusion(IPath path) {
277: String key = CPListElement.INCLUSION;
278: return addFilter(path, key);
279: }
280:
281: public boolean removeFromExclusions(IPath path) {
282: String key = CPListElement.EXCLUSION;
283: return removeFilter(path, key);
284: }
285:
286: public boolean removeFromInclusion(IPath path) {
287: String key = CPListElement.INCLUSION;
288: return removeFilter(path, key);
289: }
290:
291: private boolean addFilter(IPath path, String key) {
292: IPath[] filters = (IPath[]) getAttribute(key);
293: if (filters == null)
294: return false;
295:
296: if (!JavaModelUtil.isExcludedPath(path, filters)) {
297: IPath toAdd = path.removeFirstSegments(
298: getPath().segmentCount()).addTrailingSeparator();
299: IPath[] newFilters = new IPath[filters.length + 1];
300: System.arraycopy(filters, 0, newFilters, 0, filters.length);
301: newFilters[filters.length] = toAdd;
302: setAttribute(key, newFilters);
303: return true;
304: }
305: return false;
306: }
307:
308: private boolean removeFilter(IPath path, String key) {
309: IPath[] filters = (IPath[]) getAttribute(key);
310: if (filters == null)
311: return false;
312:
313: IPath toRemove = path.removeFirstSegments(
314: getPath().segmentCount()).addTrailingSeparator();
315: if (JavaModelUtil.isExcludedPath(toRemove, filters)) {
316: List l = new ArrayList(Arrays.asList(filters));
317: l.remove(toRemove);
318: IPath[] newFilters = (IPath[]) l
319: .toArray(new IPath[l.size()]);
320: setAttribute(key, newFilters);
321: return true;
322: }
323: return false;
324: }
325:
326: public CPListElementAttribute findAttributeElement(String key) {
327: for (int i = 0; i < fChildren.size(); i++) {
328: Object curr = fChildren.get(i);
329: if (curr instanceof CPListElementAttribute) {
330: CPListElementAttribute elem = (CPListElementAttribute) curr;
331: if (key.equals(elem.getKey())) {
332: return elem;
333: }
334: }
335: }
336: return null;
337: }
338:
339: public Object getAttribute(String key) {
340: CPListElementAttribute attrib = findAttributeElement(key);
341: if (attrib != null) {
342: return attrib.getValue();
343: }
344: return null;
345: }
346:
347: public CPListElementAttribute[] getAllAttributes() {
348: ArrayList res = new ArrayList();
349: for (int i = 0; i < fChildren.size(); i++) {
350: Object curr = fChildren.get(i);
351: if (curr instanceof CPListElementAttribute) {
352: res.add(curr);
353: }
354: }
355: return (CPListElementAttribute[]) res
356: .toArray(new CPListElementAttribute[res.size()]);
357: }
358:
359: private void createAttributeElement(String key, Object value,
360: boolean builtIn) {
361: fChildren.add(new CPListElementAttribute(this , key, value,
362: builtIn));
363: }
364:
365: private static boolean isFiltered(Object entry,
366: String[] filteredKeys) {
367: if (entry instanceof CPListElementAttribute) {
368: CPListElementAttribute curr = (CPListElementAttribute) entry;
369: String key = curr.getKey();
370: for (int i = 0; i < filteredKeys.length; i++) {
371: if (key.equals(filteredKeys[i])) {
372: return true;
373: }
374: }
375: if (curr.isNotSupported()) {
376: return true;
377: }
378: if (!curr.isBuiltIn() && !key.equals(CPListElement.JAVADOC)
379: && !key.equals(CPListElement.NATIVE_LIB_PATH)) {
380: return !JavaPlugin
381: .getDefault()
382: .getClasspathAttributeConfigurationDescriptors()
383: .containsKey(key);
384: }
385: }
386: return false;
387: }
388:
389: private Object[] getFilteredChildren(String[] filteredKeys) {
390: int nChildren = fChildren.size();
391: ArrayList res = new ArrayList(nChildren);
392:
393: for (int i = 0; i < nChildren; i++) {
394: Object curr = fChildren.get(i);
395: if (!isFiltered(curr, filteredKeys)) {
396: res.add(curr);
397: }
398: }
399: return res.toArray();
400: }
401:
402: public Object[] getChildren(boolean hideOutputFolder) {
403: if (hideOutputFolder
404: && fEntryKind == IClasspathEntry.CPE_SOURCE) {
405: return getFilteredChildren(new String[] { OUTPUT });
406: }
407: /*if (isInContainer(JavaRuntime.JRE_CONTAINER)) {
408: return getFilteredChildren(new String[] { COMBINE_ACCESSRULES, NATIVE_LIB_PATH });
409: }*/
410: if (fEntryKind == IClasspathEntry.CPE_PROJECT) {
411: return getFilteredChildren(new String[] { COMBINE_ACCESSRULES });
412: }
413: return getFilteredChildren(new String[0]);
414: }
415:
416: public Object getParentContainer() {
417: return fParentContainer;
418: }
419:
420: protected void attributeChanged(String key) {
421: fCachedEntry = null;
422: }
423:
424: private IStatus evaluateContainerChildStatus(
425: CPListElementAttribute attrib) {
426: if (fProject != null) {
427: ClasspathContainerInitializer initializer = JavaCore
428: .getClasspathContainerInitializer(fPath.segment(0));
429: if (initializer != null
430: && initializer.canUpdateClasspathContainer(fPath,
431: fProject)) {
432: if (attrib.isBuiltIn()) {
433: if (CPListElement.SOURCEATTACHMENT.equals(attrib
434: .getKey())) {
435: return initializer.getSourceAttachmentStatus(
436: fPath, fProject);
437: } else if (CPListElement.ACCESSRULES.equals(attrib
438: .getKey())) {
439: return initializer.getAccessRulesStatus(fPath,
440: fProject);
441: }
442: } else {
443: return initializer.getAttributeStatus(fPath,
444: fProject, attrib.getKey());
445: }
446: }
447: return new Status(IStatus.ERROR, JavaUI.ID_PLUGIN,
448: ClasspathContainerInitializer.ATTRIBUTE_READ_ONLY,
449: "", null); //$NON-NLS-1$
450: }
451: return null;
452: }
453:
454: public IStatus getContainerChildStatus(CPListElementAttribute attrib) {
455: if (fParentContainer instanceof CPListElement) {
456: CPListElement parent = (CPListElement) fParentContainer;
457: if (parent.getEntryKind() == IClasspathEntry.CPE_CONTAINER) {
458: return parent.evaluateContainerChildStatus(attrib);
459: }
460: return ((CPListElement) fParentContainer)
461: .getContainerChildStatus(attrib);
462: }
463: return null;
464: }
465:
466: public boolean isInContainer(String containerName) {
467: if (fParentContainer instanceof CPListElement) {
468: CPListElement elem = (CPListElement) fParentContainer;
469: return new Path(containerName).isPrefixOf(elem.getPath());
470: }
471: return false;
472: }
473:
474: public boolean isDeprecated() {
475: if (fEntryKind != IClasspathEntry.CPE_VARIABLE) {
476: return false;
477: }
478: if (fPath.segmentCount() > 0) {
479: return JavaCore
480: .getClasspathVariableDeprecationMessage(fPath
481: .segment(0)) != null;
482: }
483: return false;
484: }
485:
486: public String getDeprecationMessage() {
487: if (fEntryKind != IClasspathEntry.CPE_VARIABLE) {
488: return null;
489: }
490: if (fPath.segmentCount() > 0) {
491: String varName = fPath.segment(0);
492: return BuildPathSupport.getDeprecationMessage(varName);
493: }
494: return null;
495: }
496:
497: /*
498: * @see Object#equals(java.lang.Object)
499: */
500: public boolean equals(Object other) {
501: if (other != null && other.getClass().equals(getClass())) {
502: CPListElement elem = (CPListElement) other;
503: return getClasspathEntry().equals(elem.getClasspathEntry());
504: }
505: return false;
506: }
507:
508: /*
509: * @see Object#hashCode()
510: */
511: public int hashCode() {
512: return fPath.hashCode() + fEntryKind;
513: }
514:
515: /* (non-Javadoc)
516: * @see java.lang.Object#toString()
517: */
518: public String toString() {
519: return getClasspathEntry().toString();
520: }
521:
522: /**
523: * Returns if a entry is missing.
524: * @return Returns a boolean
525: */
526: public boolean isMissing() {
527: return fIsMissing;
528: }
529:
530: /**
531: * Sets the 'missing' state of the entry.
532: * @param isMissing the new state
533: */
534: public void setIsMissing(boolean isMissing) {
535: fIsMissing = isMissing;
536: }
537:
538: /**
539: * Returns if a entry is exported (only applies to libraries)
540: * @return Returns a boolean
541: */
542: public boolean isExported() {
543: return fIsExported;
544: }
545:
546: /**
547: * Sets the export state of the entry.
548: * @param isExported the new state
549: */
550: public void setExported(boolean isExported) {
551: if (isExported != fIsExported) {
552: fIsExported = isExported;
553:
554: attributeChanged(null);
555: }
556: }
557:
558: /**
559: * Gets the project.
560: * @return Returns a IJavaProject
561: */
562: public IJavaProject getJavaProject() {
563: return fProject;
564: }
565:
566: public static CPListElement createFromExisting(
567: IClasspathEntry curr, IJavaProject project) {
568: return createFromExisting(null, curr, project);
569: }
570:
571: public static CPListElement createFromExisting(Object parent,
572: IClasspathEntry curr, IJavaProject project) {
573: IPath path = curr.getPath();
574: IWorkspaceRoot root = ResourcesPlugin.getWorkspace().getRoot();
575:
576: // get the resource
577: IResource res = null;
578: boolean isMissing = false;
579: IPath linkTarget = null;
580:
581: switch (curr.getEntryKind()) {
582: case IClasspathEntry.CPE_CONTAINER:
583: try {
584: isMissing = project != null
585: && (JavaCore.getClasspathContainer(path,
586: project) == null);
587: } catch (JavaModelException e) {
588: isMissing = true;
589: }
590: break;
591: case IClasspathEntry.CPE_VARIABLE:
592: IPath resolvedPath = JavaCore.getResolvedVariablePath(path);
593: isMissing = root.findMember(resolvedPath) == null
594: && !resolvedPath.toFile().isFile();
595: break;
596: case IClasspathEntry.CPE_LIBRARY:
597: res = root.findMember(path);
598: if (res == null) {
599: if (!ArchiveFileFilter.isArchivePath(path)) {
600: if (root.getWorkspace().validatePath(
601: path.toString(), IResource.FOLDER).isOK()
602: && root.getProject(path.segment(0))
603: .exists()) {
604: res = root.getFolder(path);
605: }
606: }
607: isMissing = !path.toFile().isFile(); // look for external JARs
608: } else if (res.isLinked()) {
609: linkTarget = res.getLocation();
610: }
611: break;
612: case IClasspathEntry.CPE_SOURCE:
613: path = path.removeTrailingSeparator();
614: res = root.findMember(path);
615: if (res == null) {
616: if (root.getWorkspace().validatePath(path.toString(),
617: IResource.FOLDER).isOK()) {
618: res = root.getFolder(path);
619: }
620: isMissing = true;
621: } else if (res.isLinked()) {
622: linkTarget = res.getLocation();
623: }
624: break;
625: case IClasspathEntry.CPE_PROJECT:
626: res = root.findMember(path);
627: isMissing = (res == null);
628: break;
629: }
630: CPListElement elem = new CPListElement(parent, project, curr
631: .getEntryKind(), path, res, linkTarget);
632: elem.setExported(curr.isExported());
633: elem.setAttribute(SOURCEATTACHMENT, curr
634: .getSourceAttachmentPath());
635: elem.setAttribute(OUTPUT, curr.getOutputLocation());
636: elem.setAttribute(EXCLUSION, curr.getExclusionPatterns());
637: elem.setAttribute(INCLUSION, curr.getInclusionPatterns());
638: elem.setAttribute(ACCESSRULES, curr.getAccessRules());
639: elem.setAttribute(COMBINE_ACCESSRULES, new Boolean(curr
640: .combineAccessRules()));
641:
642: IClasspathAttribute[] extraAttributes = curr
643: .getExtraAttributes();
644: for (int i = 0; i < extraAttributes.length; i++) {
645: IClasspathAttribute attrib = extraAttributes[i];
646: CPListElementAttribute attribElem = elem
647: .findAttributeElement(attrib.getName());
648: if (attribElem == null) {
649: elem.createAttributeElement(attrib.getName(), attrib
650: .getValue(), false);
651: } else {
652: attribElem.setValue(attrib.getValue());
653: }
654: }
655:
656: if (project != null && project.exists()) {
657: elem.setIsMissing(isMissing);
658: }
659: return elem;
660: }
661:
662: public static StringBuffer appendEncodePath(IPath path,
663: StringBuffer buf) {
664: if (path != null) {
665: String str = path.toString();
666: buf.append('[').append(str.length()).append(']')
667: .append(str);
668: } else {
669: buf.append('[').append(']');
670: }
671: return buf;
672: }
673:
674: public static StringBuffer appendEncodedString(String str,
675: StringBuffer buf) {
676: if (str != null) {
677: buf.append('[').append(str.length()).append(']')
678: .append(str);
679: } else {
680: buf.append('[').append(']');
681: }
682: return buf;
683: }
684:
685: public static StringBuffer appendEncodedFilter(IPath[] filters,
686: StringBuffer buf) {
687: if (filters != null) {
688: buf.append('[').append(filters.length).append(']');
689: for (int i = 0; i < filters.length; i++) {
690: appendEncodePath(filters[i], buf).append(';');
691: }
692: } else {
693: buf.append('[').append(']');
694: }
695: return buf;
696: }
697:
698: public static StringBuffer appendEncodedAccessRules(
699: IAccessRule[] rules, StringBuffer buf) {
700: if (rules != null) {
701: buf.append('[').append(rules.length).append(']');
702: for (int i = 0; i < rules.length; i++) {
703: appendEncodePath(rules[i].getPattern(), buf)
704: .append(';');
705: buf.append(rules[i].getKind()).append(';');
706: }
707: } else {
708: buf.append('[').append(']');
709: }
710: return buf;
711: }
712:
713: public StringBuffer appendEncodedSettings(StringBuffer buf) {
714: buf.append(fEntryKind).append(';');
715: if (getLinkTarget() == null) {
716: appendEncodePath(fPath, buf).append(';');
717: } else {
718: appendEncodePath(fPath, buf).append('-').append('>');
719: appendEncodePath(getLinkTarget(), buf).append(';');
720: }
721: buf.append(Boolean.valueOf(fIsExported)).append(';');
722: for (int i = 0; i < fChildren.size(); i++) {
723: Object curr = fChildren.get(i);
724: if (curr instanceof CPListElementAttribute) {
725: CPListElementAttribute elem = (CPListElementAttribute) curr;
726: if (elem.isBuiltIn()) {
727: String key = elem.getKey();
728: if (OUTPUT.equals(key)
729: || SOURCEATTACHMENT.equals(key)) {
730: appendEncodePath((IPath) elem.getValue(), buf)
731: .append(';');
732: } else if (EXCLUSION.equals(key)
733: || INCLUSION.equals(key)) {
734: appendEncodedFilter((IPath[]) elem.getValue(),
735: buf).append(';');
736: } else if (ACCESSRULES.equals(key)) {
737: appendEncodedAccessRules(
738: (IAccessRule[]) elem.getValue(), buf)
739: .append(';');
740: } else if (COMBINE_ACCESSRULES.equals(key)) {
741: buf.append(
742: ((Boolean) elem.getValue())
743: .booleanValue()).append(';');
744: }
745: } else {
746: appendEncodedString((String) elem.getValue(), buf);
747: }
748: }
749: }
750: return buf;
751: }
752:
753: public IPath getLinkTarget() {
754: return fLinkTarget;
755: }
756:
757: public void setPath(IPath path) {
758: fCachedEntry = null;
759: fPath = path;
760: }
761:
762: public void setLinkTarget(IPath linkTarget) {
763: fCachedEntry = null;
764: fLinkTarget = linkTarget;
765: }
766:
767: public static void insert(CPListElement element, List cpList) {
768: int length = cpList.size();
769: CPListElement[] elements = (CPListElement[]) cpList
770: .toArray(new CPListElement[length]);
771: int i = 0;
772: while (i < length
773: && elements[i].getEntryKind() != element.getEntryKind()) {
774: i++;
775: }
776: if (i < length) {
777: i++;
778: while (i < length
779: && elements[i].getEntryKind() == element
780: .getEntryKind()) {
781: i++;
782: }
783: cpList.add(i, element);
784: return;
785: }
786:
787: switch (element.getEntryKind()) {
788: case IClasspathEntry.CPE_SOURCE:
789: cpList.add(0, element);
790: break;
791: case IClasspathEntry.CPE_CONTAINER:
792: case IClasspathEntry.CPE_LIBRARY:
793: case IClasspathEntry.CPE_PROJECT:
794: case IClasspathEntry.CPE_VARIABLE:
795: default:
796: cpList.add(element);
797: break;
798: }
799: }
800:
801: public static IClasspathEntry[] convertToClasspathEntries(
802: List/*<CPListElement>*/cpList) {
803: IClasspathEntry[] result = new IClasspathEntry[cpList.size()];
804: int i = 0;
805: for (Iterator iter = cpList.iterator(); iter.hasNext();) {
806: CPListElement cur = (CPListElement) iter.next();
807: result[i] = cur.getClasspathEntry();
808: i++;
809: }
810: return result;
811: }
812:
813: public static CPListElement[] createFromExisting(
814: IJavaProject project) throws JavaModelException {
815: IClasspathEntry[] rawClasspath = project.getRawClasspath();
816: CPListElement[] result = new CPListElement[rawClasspath.length];
817: for (int i = 0; i < rawClasspath.length; i++) {
818: result[i] = CPListElement.createFromExisting(
819: rawClasspath[i], project);
820: }
821: return result;
822: }
823:
824: public static boolean isProjectSourceFolder(
825: CPListElement[] existing, IJavaProject project) {
826: IPath projPath = project.getProject().getFullPath();
827: for (int i = 0; i < existing.length; i++) {
828: IClasspathEntry curr = existing[i].getClasspathEntry();
829: if (curr.getEntryKind() == IClasspathEntry.CPE_SOURCE) {
830: if (projPath.equals(curr.getPath())) {
831: return true;
832: }
833: }
834: }
835: return false;
836: }
837:
838: public IPath getOrginalPath() {
839: return fOrginalPath;
840: }
841:
842: public IPath getOrginalLinkTarget() {
843: return fOrginalLinkTarget;
844: }
845:
846: public CPListElement copy() {
847: CPListElement result = new CPListElement();
848: result.fProject = fProject;
849: result.fEntryKind = fEntryKind;
850: result.fPath = fPath;
851: result.fOrginalPath = fOrginalPath;
852: result.fResource = fResource;
853: result.fIsExported = fIsExported;
854: result.fIsMissing = fIsMissing;
855: result.fParentContainer = fParentContainer;
856: result.fCachedEntry = null;
857: result.fChildren = new ArrayList(fChildren.size());
858: for (Iterator iterator = fChildren.iterator(); iterator
859: .hasNext();) {
860: Object child = iterator.next();
861: if (child instanceof CPListElement) {
862: result.fChildren.add(((CPListElement) child).copy());
863: } else {
864: result.fChildren.add(((CPListElementAttribute) child)
865: .copy());
866: }
867: }
868: result.fLinkTarget = fLinkTarget;
869: result.fOrginalLinkTarget = fOrginalLinkTarget;
870: return result;
871: }
872:
873: public void setAttributesFromExisting(CPListElement existing) {
874: Assert.isTrue(existing.getEntryKind() == getEntryKind());
875: CPListElementAttribute[] attributes = existing
876: .getAllAttributes();
877: for (int i = 0; i < attributes.length; i++) {
878: CPListElementAttribute curr = attributes[i];
879: CPListElementAttribute elem = findAttributeElement(curr
880: .getKey());
881: if (elem == null) {
882: createAttributeElement(curr.getKey(), curr.getValue(),
883: false);
884: } else {
885: elem.setValue(curr.getValue());
886: }
887: }
888: }
889:
890: }
|