/******************************************************************************* * Copyright (c) 2007-2012 Red Hat, Inc. * Distributed under license by Red Hat, Inc. All rights reserved. * This program is 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: * Red Hat, Inc. - initial API and implementation ******************************************************************************/ package org.jboss.tools.cdi.seam.text.ext.hyperlink; import java.text.MessageFormat; import java.util.Map; import org.eclipse.core.resources.IFile; import org.eclipse.core.resources.IProject; import org.eclipse.core.runtime.CoreException; import org.eclipse.jdt.core.IField; import org.eclipse.jdt.core.IJavaElement; import org.eclipse.jdt.core.IJavaProject; import org.eclipse.jdt.core.IMethod; import org.eclipse.jdt.core.IType; import org.eclipse.jdt.core.JavaModelException; import org.eclipse.jdt.ui.JavaUI; import org.eclipse.jface.text.IDocument; import org.eclipse.jface.text.IRegion; import org.eclipse.ui.PartInitException; import org.jboss.tools.cdi.core.CDICoreNature; import org.jboss.tools.cdi.core.CDICorePlugin; import org.jboss.tools.cdi.seam.config.core.CDISeamConfigExtension; import org.jboss.tools.cdi.seam.config.core.definition.SeamBeansDefinition; import org.jboss.tools.cdi.seam.config.core.definition.SeamFieldDefinition; import org.jboss.tools.cdi.seam.config.core.definition.SeamMemberDefinition; import org.jboss.tools.cdi.seam.config.core.definition.SeamMethodDefinition; import org.jboss.tools.cdi.seam.config.core.util.Util; import org.jboss.tools.cdi.seam.text.ext.CDISeamExtMessages; import org.jboss.tools.common.text.ext.hyperlink.AbstractHyperlink; import org.jboss.tools.common.text.ext.util.StructuredModelWrapper; import org.jboss.tools.common.text.ext.util.Utils; import org.jboss.tools.jst.web.ui.internal.text.ext.hyperlink.jsp.JSPRootHyperlinkPartitioner; import org.w3c.dom.Attr; import org.w3c.dom.Document; import org.w3c.dom.Element; import org.w3c.dom.Node; /** * @author Jeremy */ public class SeamConfigTagNameHyperlink extends AbstractHyperlink { /** * @see com.ibm.sse.editor.AbstractHyperlink#doHyperlink(org.eclipse.jface.text.IRegion) */ protected void doHyperlink(IRegion region) { IFile documentFile = getFile(); if(documentFile == null) return; IProject project = documentFile.getProject(); CDICoreNature cdi = CDICorePlugin.getCDI(project, true); if(cdi == null) return; String tagName = getTagName(region); if(tagName == null) return; int at = tagName.indexOf('@'); String attrName = null; if(at >= 0) { attrName = tagName.substring(at + 1); tagName = tagName.substring(0, at); } String uri = getURI(region); IJavaElement element = null; IType type = Util.resolveType(tagName, uri, cdi); if(type != null) { element = type; if(attrName != null) { try { if(type.isAnnotation()) { IMethod m = type.getMethod(attrName, new String[0]); if(m != null && m.exists()) element = m; } else { IField f = type.getField(attrName); if(f != null && f.exists()) { element = f; } } } catch (CoreException e) { } } } else { SeamMemberDefinition def = find(cdi, region, documentFile); if(def instanceof SeamFieldDefinition) { element = ((SeamFieldDefinition)def).getField(); } else if(def instanceof SeamMethodDefinition) { element = ((SeamMethodDefinition)def).getMethod(); } } if(element != null) { try { JavaUI.openInEditor(element); } catch (JavaModelException e) { } catch (PartInitException e) { } } } SeamMemberDefinition find(CDICoreNature cdi, IRegion region, IFile documentFile) { CDISeamConfigExtension ext = CDISeamConfigExtension.getExtension(cdi); if(ext == null) return null; SeamBeansDefinition def = ext.getContext().getDefinition(documentFile.getFullPath()); if(def == null) return null; return def.findExactly(region.getOffset()); } private IType resolve(IJavaProject jp, String tagName, String uri) { return null; } private String getURI(IRegion region) { return getURI(region, getDocument()); } public static String getURI(IRegion region, IDocument document) { StructuredModelWrapper smw = new StructuredModelWrapper(); smw.init(document); try { Document xmlDocument = smw.getDocument(); if (xmlDocument == null) return null; Node n = Utils.findNodeForOffset(xmlDocument, region.getOffset()); if(n instanceof Attr) { n = ((Attr)n).getOwnerElement(); } if (!(n instanceof Element)) return null; return getURI(n, document, region.getOffset()); } finally { smw.dispose(); } } public static String getURI(Node node, IDocument document, int offset) { String nodeName = node.getNodeName(); if (nodeName.indexOf(':') == -1) return null; String nodePrefix = nodeName.substring(0, nodeName.indexOf(":")); //$NON-NLS-1$ if (nodePrefix == null || nodePrefix.length() == 0) return null; Map trackers = JSPRootHyperlinkPartitioner.getTrackersMap(document, offset); return (String)(trackers == null ? null : trackers.get(nodePrefix)); } private String getTagName(IRegion region) { StructuredModelWrapper smw = new StructuredModelWrapper(); smw.init(getDocument()); try { Document xmlDocument = smw.getDocument(); if (xmlDocument == null) return null; Node node = Utils.findNodeForOffset(xmlDocument, region.getOffset()); Attr attr = null; Element elem = null; if (node instanceof Element) { elem = (Element)node; } else if(node instanceof Attr) { attr = (Attr)node; elem = attr.getOwnerElement(); } if(elem == null) return null; String tagName = elem.getNodeName(); if (tagName.indexOf(':') == -1) return null; tagName = tagName.substring(tagName.indexOf(':') + 1); if(attr != null) { tagName += "@" + attr.getName(); } return tagName; } finally { smw.dispose(); } } /* * (non-Javadoc) * * @see IHyperlink#getHyperlinkText() */ public String getHyperlinkText() { String tagName = getTagName(getHyperlinkRegion()); if (tagName == null) return CDISeamExtMessages.CDI_SEAM_CONFIG_OPEN_TAG; return MessageFormat.format(CDISeamExtMessages.CDI_SEAM_CONFIG_OPEN_TAG, tagName); } }