All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.openscience.cdk.io.cml.CMLHandler Maven / Gradle / Ivy

There is a newer version: 2.10
Show newest version
/* Copyright (C) 1997-2007  Egon Willighagen 
 *
 * Contact: [email protected]
 *
 *  This library is free software; you can redistribute it and/or
 *  modify it under the terms of the GNU Lesser General Public
 *  License as published by the Free Software Foundation; either
 *  version 2.1 of the License, or (at your option) any later version.
 *
 *  This library is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 *  Lesser General Public License for more details.
 *
 *  You should have received a copy of the GNU Lesser General Public
 *  License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 *
 */
package org.openscience.cdk.io.cml;

import java.util.Hashtable;
import java.util.Map;

import org.openscience.cdk.interfaces.IChemFile;
import org.openscience.cdk.tools.ILoggingTool;
import org.openscience.cdk.tools.LoggingToolFactory;
import org.xml.sax.Attributes;
import org.xml.sax.helpers.DefaultHandler;

/**
 * SAX2 implementation for CML XML fragment reading. CML Core is supported
 * as well is the CRML module.
 *
 * 

Data is stored into the Chemical Document Object which is passed when * instantiating this class. This makes it possible that programs that do not * use CDK for internal data storage, use this CML library. * * @cdk.module io * @cdk.githash * * @author Egon Willighagen **/ public class CMLHandler extends DefaultHandler { private ICMLModule conv; private static ILoggingTool logger = LoggingToolFactory.createLoggingTool(CMLHandler.class); private boolean debug = true; private Map userConventions; private CMLStack xpath; private CMLStack conventionStack; private CMLModuleStack moduleStack; /** * Constructor for the CMLHandler. * * @param chemFile The document in which data is stored **/ public CMLHandler(IChemFile chemFile) { conv = new CMLCoreModule(chemFile); userConventions = new Hashtable(); xpath = new CMLStack(); conventionStack = new CMLStack(); moduleStack = new CMLModuleStack(); } public void registerConvention(String convention, ICMLModule conv) { userConventions.put(convention, conv); } /** * Implementation of the characters() procedure overwriting the DefaultHandler interface. * * @param ch characters to handle */ @Override public void characters(char ch[], int start, int length) { if (debug) logger.debug(new String(ch, start, length)); conv.characterData(xpath, ch, start, length); } public void doctypeDecl(String name, String publicId, String systemId) throws Exception {} /** * Calling this procedure signals the end of the XML document. */ @Override public void endDocument() { conv.endDocument(); } @Override public void endElement(String uri, String local, String raw) { if (debug) logger.debug(""); conv.endElement(xpath, uri, local, raw); xpath.pop(); conventionStack.pop(); moduleStack.pop(); conv = moduleStack.current(); } @Override public void startDocument() { conv.startDocument(); conventionStack.push("CML"); moduleStack.push(conv); } @Override public void startElement(String uri, String local, String raw, Attributes atts) { xpath.push(local); if (debug) logger.debug("<", raw, "> -> ", xpath); // Detect CML modules, like CRML and CCML if (local.startsWith("reaction")) { // e.g. reactionList, reaction -> CRML module logger.info("Detected CRML module"); if (!conventionStack.current().equals("CMLR")) { conv = new CMLReactionModule(conv); } conventionStack.push("CMLR"); } else if (uri == null || uri.length() == 0 || uri.startsWith("http://www.xml-cml.org/")) { // assume CML Core // Detect conventions String convName = ""; for (int i = 0; i < atts.getLength(); i++) { if (atts.getQName(i).equals("convention")) { convName = atts.getValue(i); } } if (convName.length() > 0) { if (convName.equals(conventionStack.current())) { logger.debug("Same convention as parent"); } else { logger.info("New Convention: ", convName); if (convName.equals("CML")) { /* * Don't reset the convention handler to CMLCore, * becuase all handlers should extend this handler, and * use it for any content other then specifically put * into the specific convention */ } else if (convName.equals("PDB")) { conv = new PDBConvention(conv); } else if (convName.equals("PMP")) { conv = new PMPConvention(conv); } else if (convName.equals("MDLMol")) { if (debug) logger.debug("MDLMolConvention instantiated..."); conv = new MDLMolConvention(conv); } else if (convName.equals("JMOL-ANIMATION")) { conv = new JMOLANIMATIONConvention(conv); } else if (convName.equals("qsar:DescriptorValue")) { conv = new QSARConvention(conv); } else if (userConventions.containsKey(convName)) { //unknown convention. userConvention? ICMLModule newconv = (ICMLModule) userConventions.get(convName); newconv.inherit(conv); conv = newconv; } else { logger.warn("Detected unknown convention: ", convName); } } conventionStack.push(convName); } else { // no convention set/reset: take convention of parent conventionStack.push(conventionStack.current()); } } else { conv = new OtherNamespace(); conventionStack.push("Other"); } moduleStack.push(conv); if (debug) logger.debug("ConventionStack: ", conventionStack); conv.startElement(xpath, uri, local, raw, atts); } }





© 2015 - 2025 Weber Informatics LLC | Privacy Policy