r1356 - in guix/trunk/guix-compiler/src/main/java/org/nuiton/guix: . compiler css model parser tags
Author: kmorin Date: 2009-04-24 15:37:46 +0000 (Fri, 24 Apr 2009) New Revision: 1356 Added: guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/GuixInitializer.java Modified: guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/GuixLauncher.java guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/compiler/GuixCompiler.java guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/css/CSS.jj guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/css/CSS.jjt guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/model/GuixModelObject.java guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/parser/Java1.5.jjt guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/tags/ScriptHandler.java guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/tags/StyleHandler.java guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/tags/TagManager.java Log: Parsing des fichiers CSS et des fichiers scripts Added: guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/GuixInitializer.java =================================================================== --- guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/GuixInitializer.java (rev 0) +++ guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/GuixInitializer.java 2009-04-24 15:37:46 UTC (rev 1356) @@ -0,0 +1,24 @@ +/* + * To change this template, choose Tools | Templates + * and open the template in the editor. + */ + +package org.nuiton.guix; + +import org.nuiton.guix.tags.TagManager; + +/** + * + * @author morin + */ +public class GuixInitializer { + + public static void initialize() { + TagManager.registerGuixClasse("Button"); + TagManager.registerGuixClasse("Panel"); + TagManager.registerGuixClasse("Label"); + TagManager.registerGuixClasse("CheckBox"); + TagManager.registerGuixClasse("ComboBox"); + TagManager.registerGuixClasse("Application"); + } +} Modified: guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/GuixLauncher.java =================================================================== --- guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/GuixLauncher.java 2009-04-21 15:57:24 UTC (rev 1355) +++ guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/GuixLauncher.java 2009-04-24 15:37:46 UTC (rev 1356) @@ -58,8 +58,8 @@ private File targetDirectory = new File("destination"); public GuixLauncher() { - files = new File[]{new File("/home/morin/NetBeansProjects/jaxx-gwt/trunk/jaxx-example/src/main/java/jaxx/demo/CalculatorDemo.jaxx")}; - classNames = new String[]{"CalculatorDemo"}; + files = new File[]{new File("/home/morin/NetBeansProjects/guix/trunk/guix-test/src/main/java/org/nuiton/guix/demo/GuixDemo.guix")}; + classNames = new String[]{"GuixDemo"}; compile(); } @@ -140,7 +140,7 @@ for (GuixModelObject mo : rootModelObjects) { - File f = new File(mo.getClassDescriptor().getName() + "ModelTree.xml"); + File f = new File(targetDirectory,mo.getClassDescriptor().getName() + "ModelTree.xml"); if (!f.exists()) { f.createNewFile(); } @@ -261,8 +261,9 @@ private void writeModelTree(XmlSerializer serializer, GuixModelObject mo, XmlSerializer cssSerializer) throws IOException { if(!mo.getStyleSheets().isEmpty()) { + int i = 0; for(StyleSheet styleSheet : mo.getStyleSheets()) { - File ss = new File(mo.getClassDescriptor().getName() + "SS"); + File ss = new File(targetDirectory,mo.getClassDescriptor().getName() + i++ + "SS.xml"); cssSerializer.setOutput(new FileWriter(ss)); cssSerializer.startTag("", "rules"); for(Rule rule : styleSheet.getRules()) { Modified: guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/compiler/GuixCompiler.java =================================================================== --- guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/compiler/GuixCompiler.java 2009-04-21 15:57:24 UTC (rev 1355) +++ guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/compiler/GuixCompiler.java 2009-04-24 15:37:46 UTC (rev 1356) @@ -1,17 +1,14 @@ -/* - * To change this template, choose Tools | Templates - * and open the template in the editor. - */ + package org.nuiton.guix.compiler; +import java.util.logging.Level; +import java.util.logging.Logger; import org.nuiton.guix.GuixLauncher; import java.io.File; -import java.io.FileNotFoundException; import java.io.FileReader; import java.io.IOException; import java.util.ArrayList; import java.util.List; -import java.util.Stack; import org.nuiton.guix.model.AttributeDescriptor; import org.nuiton.guix.model.ClassDescriptor; import org.nuiton.guix.model.GuixModelObject; @@ -24,174 +21,257 @@ import org.xmlpull.v1.XmlPullParserFactory; /** - * Compiles Guix files into Java classes + * Compiles Guix files into model tree * * @author morin */ public class GuixCompiler { - /** flag to detec if an error occurs while compiling jaxx file */ + /** Flag to detec if an error occurs while compiling guix file */ protected boolean failed; - /** Used for error reporting purposes, - * so we can report the right source file. */ - protected Stack<File> sourceFiles = new Stack<File>(); - /** XML parser of src file. */ + /** Directory containing the guix files */ private File baseDir; + /** Guix file to compile */ private File src; + /** Name of the class to produce */ private String outputClassName; - private GuixLauncher launchor; + /** GuixLauncher instance which launched this compiler */ + private GuixLauncher launcher; private StyleHandler styleHandler = new StyleHandler(); private ScriptHandler scriptHandler = new ScriptHandler(); - + /** Root of the model */ + private GuixModelObject rootMO; + /*------------------------------------------------------------------------*/ /*-- Constructor methods -------------------------------------------------*/ /*------------------------------------------------------------------------*/ /** * Creates a new GuixCompiler. * - * @param baseDir classpath location - * @param src location of file to compile - * @param outputClassName the out file name + * @param baseDir classpath location + * @param src location of file to compile + * @param outputClassName the out file name + * @param launcher the launcher of the compiler */ public GuixCompiler(File baseDir, File src, String outputClassName, - GuixLauncher launchor) { + GuixLauncher launcher) { this.baseDir = baseDir; this.src = src; - sourceFiles.push(src); this.outputClassName = outputClassName; - this.launchor = launchor; + this.launcher = launcher; } - public GuixModelObject compile() - throws FileNotFoundException, IOException, XmlPullParserException { - //try { - XmlPullParserFactory factory = XmlPullParserFactory.newInstance( - System.getProperty(XmlPullParserFactory.PROPERTY_NAME), null); - factory.setNamespaceAware(true); - XmlPullParser xpp = factory.newPullParser(); - xpp.setInput(new FileReader(src)); - - if (xpp.getEventType() == XmlPullParser.START_DOCUMENT) { - StringBuffer doc = new StringBuffer(); - do { - xpp.nextToken(); - if(xpp.getEventType() == XmlPullParser.COMMENT) - doc.append(xpp.getText()); - } while(xpp.getEventType() != XmlPullParser.START_TAG); - - String nameSpace = xpp.getNamespace(); - String localName = xpp.getName(); - String packageName = - resolvePackageName(nameSpace, localName); - - GuixModelObject root = new GuixModelObject(xpp.getAttributeValue("", "id"), - doc.toString(),xpp.getAttributeValue("", "styleClass")); - String className = src.getName().substring(0, src.getName().lastIndexOf('.')); - String classPackageName = src.getPath().replace('/', '.') - .substring(src.getPath().lastIndexOf("src/main/java/") + 14, - src.getPath().lastIndexOf('/')); - root.setClassDescriptor(new ClassDescriptor(className,classPackageName)); - root.getClassDescriptor().setSuperClass(new ClassDescriptor( - localName, packageName)); - root.setAttributeDescriptors(getAttributes(xpp)); - root.setChildren(new ArrayList<GuixModelObject>()); - - do { - xpp.nextToken(); - } while(xpp.getEventType() != XmlPullParser.START_TAG); - - while(xpp.getName().equals("script") - ||xpp.getName().equals("style")) { - if(xpp.getName().equals("script")) { - root.getClassDescriptor().setScript( - scriptHandler.compileScript(xpp)); + /** + * Compiles the guix file + * + * @return the root of the model + */ + public GuixModelObject compile() { + try { + //Creation of the Xml parser + XmlPullParserFactory factory = XmlPullParserFactory.newInstance(System.getProperty(XmlPullParserFactory.PROPERTY_NAME), null); + factory.setNamespaceAware(true); + XmlPullParser xpp = factory.newPullParser(); + xpp.setInput(new FileReader(src)); + //Start parsing + if (xpp.getEventType() == XmlPullParser.START_DOCUMENT) { + //javaDoc of the class to create + StringBuffer doc = new StringBuffer(); + do { + xpp.nextToken(); + if (xpp.getEventType() == XmlPullParser.COMMENT) { + doc.append(xpp.getText()); + } + } while (xpp.getEventType() != XmlPullParser.START_TAG); + //resolve the package of teh superclass + String tagNameSpace = xpp.getNamespace(); + String tagName = xpp.getName(); + String tagPackageName = resolvePackageName(tagNameSpace, tagName); + //creation of the root GuixModelObject + rootMO = new GuixModelObject(xpp.getAttributeValue("", "id"), doc.toString(), xpp.getAttributeValue("", "styleClass")); + //the class name is the name of the file minus the extension + String className = src.getName().substring(0, src.getName().lastIndexOf('.')); + String classPackageName = src.getPath().replace('/', '.').substring(src.getPath().lastIndexOf("src/main/java/") + 14, src.getPath().lastIndexOf('/')); + rootMO.setClassDescriptor(new ClassDescriptor(className, classPackageName)); + rootMO.getClassDescriptor().setSuperClass(new ClassDescriptor(tagName, tagPackageName)); + rootMO.setAttributeDescriptors(getAttributes(xpp)); + rootMO.setChildren(new ArrayList<GuixModelObject>()); + //add the stylesheet of the CSS file with the same name as the Guix file + StyleSheet ss = styleHandler.autoDetectStyleFile(baseDir.getPath(), outputClassName); + rootMO.getStyleSheets().add(ss); + StringBuffer script = new StringBuffer(); + //add the script in the .script file with the same name as the Guix file + script.append(scriptHandler.autoDetectScriptFile(baseDir.getPath(), outputClassName)); + //reach the next START_TAG + do { + xpp.nextToken(); + } while (xpp.getEventType() != XmlPullParser.START_TAG && xpp.getEventType() != XmlPullParser.END_DOCUMENT); + //if not eof + if (xpp.getEventType() == XmlPullParser.START_TAG) { + //compile the rest of the file + script.append(compile(xpp, rootMO, doc.toString())); } - - if(xpp.getName().equals("style")) { - StyleSheet ss = styleHandler.compileStyle(xpp, baseDir.getPath()); - root.getStyleSheets().add(ss); - } + //all the script tags have been recorded + rootMO.getClassDescriptor().setScript(script.toString()); + //register the root ClassDescriptor + failed = !launcher.registerClassDescriptor(rootMO.getClassDescriptor()); + return rootMO; } - failed = launchor.registerClassDescriptor(root.getClassDescriptor()); - - if (xpp.getEventType() == XmlPullParser.START_TAG) { - compile(xpp,root,doc.toString()); - } - - return root; + failed = true; + } catch (XmlPullParserException ex) { + Logger.getLogger(GuixCompiler.class.getName()).log(Level.SEVERE, null, ex); + } catch (IOException ex) { + Logger.getLogger(GuixCompiler.class.getName()).log(Level.SEVERE, null, ex); } - failed = true; return null; - //} } /*------------------------------------------------------------------------*/ /*-- Compile methods -----------------------------------------------------*/ /*------------------------------------------------------------------------*/ - private void compile(final XmlPullParser xpp, GuixModelObject previousMO, - String javaDoc) throws IOException, XmlPullParserException { + /** + * + * @param xpp the parser referencing the tag + * @param previousMO the <code>GuixModelObject</code> parent of the tag + * @param javaDoc the comments above the tag, to add to its javaDoc + * @return the scripts already discovered while parsing the file + */ + private StringBuffer compile(final XmlPullParser xpp, GuixModelObject previousMO, + String javaDoc) { - String nameSpace = xpp.getNamespace(); - String localName = xpp.getName(); - String packageName = resolvePackageName(nameSpace, localName); + StringBuffer result = new StringBuffer(); + StringBuffer doc = new StringBuffer(); + GuixModelObject prev; - nameSpace = packageName + ".*"; - GuixModelObject mo = new GuixModelObject(xpp.getAttributeValue("","id"), - javaDoc,xpp.getAttributeValue("", "styleClass")); - mo.setParent(previousMO); - mo.setClassDescriptor(new ClassDescriptor(localName, packageName)); - previousMO.getChildren().add(mo); - mo.setChildren(new ArrayList<GuixModelObject>()); - - failed = !launchor.registerClassDescriptor(mo.getClassDescriptor()); - - if(!failed) { - GuixModelObject prev = mo; - StringBuffer doc = new StringBuffer(); - do { - xpp.nextToken(); - - if (xpp.getEventType() == XmlPullParser.END_TAG) { - prev = prev.getParent(); + try { + //if the tag is a style tag + if (xpp.getName() != null && xpp.getName().equals("style")) { + //creates a new stylesheet + StyleSheet ss = styleHandler.compileStyle(xpp, baseDir.getPath()); + rootMO.getStyleSheets().add(ss); + //the parent is still the same + + prev = previousMO; + } + //if the tag is a script tag + else if (xpp.getName() != null && xpp.getName().equals("script")) { + //add the script to the result + result.append(scriptHandler.compileScript(xpp, baseDir.getPath())); + //the parent is still the same + prev = previousMO; + } + //if the tag is a class tag + else { + String tagNameSpace = xpp.getNamespace(); + String tagPackageName = resolvePackageName(tagNameSpace, xpp.getName()); + String tagName; + //if the name of the tag is the fully-qualified class name + if(xpp.getName().lastIndexOf('.') >= 0) { + tagName = xpp.getName().substring(xpp.getName().lastIndexOf('.') + 1); } - else if(xpp.getEventType() == XmlPullParser.COMMENT) - doc.append(xpp.getText()); - else if(xpp.getName() != null && xpp.getName().equals("style")) { - StyleSheet ss = styleHandler.compileStyle(xpp, baseDir.getPath()); - prev.getStyleSheets().add(ss); + else { + tagName = xpp.getName(); } - } while (xpp.getEventType() != XmlPullParser.START_TAG - && xpp.getEventType() != XmlPullParser.END_DOCUMENT); + tagNameSpace = tagPackageName + ".*"; + //create the GuixModelObject representing the tag + GuixModelObject mo = new GuixModelObject(xpp.getAttributeValue("", "id"), + javaDoc, xpp.getAttributeValue("", "styleClass")); + mo.setParent(previousMO); + mo.setClassDescriptor(new ClassDescriptor(tagName, tagPackageName)); + mo.setChildren(new ArrayList<GuixModelObject>()); + //add this GuixModelObject to the children of the parent + previousMO.getChildren().add(mo); + + //register the ClassDescriptor + failed = !launcher.registerClassDescriptor(mo.getClassDescriptor()); + + if (!failed) { + //parse the children of the tag + prev = mo; + do { + xpp.nextToken(); + //if the tag has no children + if (xpp.getEventType() == XmlPullParser.END_TAG) { + prev = prev.getParent(); + } else if (xpp.getEventType() == XmlPullParser.COMMENT) { + //add the comment to the doc of the next tag + doc.append(xpp.getText()); + } + } while (xpp.getEventType() != XmlPullParser.START_TAG + && xpp.getEventType() != XmlPullParser.END_DOCUMENT); + } + else + return null; + } + //if not eof if (xpp.getEventType() == XmlPullParser.START_TAG) { - compile(xpp, prev,doc.toString()); + //compile the rest of the document + result.append(compile(xpp, prev, doc.toString())); } + } catch (XmlPullParserException ex) { + Logger.getLogger(GuixCompiler.class.getName()).log(Level.SEVERE, null, ex); + } catch (IOException ex) { + Logger.getLogger(GuixCompiler.class.getName()).log(Level.SEVERE, null, ex); } + return result; } - private String resolvePackageName(String nameSpace, String localName) { - // resolve class tags into fully-qualified class name - String packageName; - if (nameSpace != null && nameSpace.endsWith("*")) { - packageName = nameSpace.substring(0, nameSpace.length() - 2); - } else { - String fullClassName = TagManager.resolveClassName(localName); - packageName = (fullClassName == null) ? null : fullClassName - .substring(0, fullClassName.lastIndexOf('.')); + /** + * Resolve the package name of the tag using the namespace + * and the name of the tag. + * + * @param tagNameSpace namespace of the tag + * @param tagName name of the tag + * @return the name of the package of the tag + */ + private String resolvePackageName(String tagNameSpace, String tagName) { + String packageName = null; + //if there is a namespace + if (tagNameSpace != null && tagNameSpace.endsWith("*")) { + packageName = tagNameSpace.substring(0, tagNameSpace.length() - 2); } + //if the name of the tag is the fully qualified class name + if(tagName.lastIndexOf('.') >= 0) { + if(packageName == null) { + packageName = tagName.substring(0, tagName.lastIndexOf('.')); + } + else { + packageName += tagName.substring(0, tagName.lastIndexOf('.')); + } + } + //if nor the namespace nor the fully qualified class name is defined + if(packageName == null) { + String fullClassName = TagManager.resolveClassName(tagName); + packageName = (fullClassName == null) ? null : fullClassName.substring(0, fullClassName.lastIndexOf('.')); + } return packageName; } + /** + * Transforms the attributes of a tag + * into a list of <code>AttributeDescriptor</code>s. + * + * @param xpp the parser referencing a tag. + * @return the list of <code>AttributeDescriptor</code>s corresponding + * to the attributes of the tag. + */ private List<AttributeDescriptor> getAttributes(XmlPullParser xpp) { List<AttributeDescriptor> result = new ArrayList<AttributeDescriptor>(); - for(int i = 0 ; i < xpp.getAttributeCount() ; i++) { - if(!xpp.getAttributeName(i).equals("id")) + for (int i = 0; i < xpp.getAttributeCount(); i++) { + if (!xpp.getAttributeName(i).equals("id")) { result.add(new AttributeDescriptor( - xpp.getAttributeName(i),xpp.getAttributeValue(i))); + xpp.getAttributeName(i), xpp.getAttributeValue(i))); + } } return result; } + /** + * Return if the compilation failed. + * + * @return true if the compilation failed + */ public boolean isFailed() { return failed; } Modified: guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/css/CSS.jj =================================================================== --- guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/css/CSS.jj 2009-04-21 15:57:24 UTC (rev 1355) +++ guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/css/CSS.jj 2009-04-24 15:37:46 UTC (rev 1356) @@ -9,11 +9,11 @@ // fan of the LGPL, unfortunately that won't work. options { STATIC = false; - JDK_VERSION = "1.4"; + JDK_VERSION = "1.6"; } PARSER_BEGIN(CSSParser) -package jaxx.css; +package org.nuiton.guix.css; public class CSSParser/*@bgen(jjtree)*/implements CSSParserTreeConstants/*@egen*/ {/*@bgen(jjtree)*/ protected JJTCSSParserState jjtree = new JJTCSSParserState(); Modified: guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/css/CSS.jjt =================================================================== --- guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/css/CSS.jjt 2009-04-21 15:57:24 UTC (rev 1355) +++ guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/css/CSS.jjt 2009-04-24 15:37:46 UTC (rev 1356) @@ -8,12 +8,12 @@ // fan of the LGPL, unfortunately that won't work. options { STATIC = false; - JDK_VERSION = "1.4"; + JDK_VERSION = "1.6"; NODE_SCOPE_HOOK = true; } PARSER_BEGIN(CSSParser) -package jaxx.css; +package org.nuiton.guix.css; public class CSSParser { public SimpleNode popNode() { Modified: guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/model/GuixModelObject.java =================================================================== --- guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/model/GuixModelObject.java 2009-04-21 15:57:24 UTC (rev 1355) +++ guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/model/GuixModelObject.java 2009-04-24 15:37:46 UTC (rev 1356) @@ -1,7 +1,3 @@ -/* - * To change this template, choose Tools | Templates - * and open the template in the editor. - */ package org.nuiton.guix.model; @@ -9,20 +5,38 @@ import java.util.List; /** + * Base object to represent the model of the guix files * * @author morin */ public class GuixModelObject { + /** The id of the object */ private String id; + /** The component containing the object */ private GuixModelObject parent; + /** The children that the object contains */ private List<GuixModelObject> children = new ArrayList<GuixModelObject>(); + /** The descriptor the class of the object */ private ClassDescriptor classDescriptor; - private List<AttributeDescriptor> attributeDescriptors = new ArrayList<AttributeDescriptor>(); + /** The descriptor of the attributes of the object */ + private List<AttributeDescriptor> attributeDescriptors + = new ArrayList<AttributeDescriptor>(); + /** The stylesheets associated to the object + * (in case the object is a root model object) */ private List<StyleSheet> styleSheets = new ArrayList<StyleSheet>(); + /** The javaDoc of the object */ private String javadoc; + /** The style class of the object */ private String styleClass; + /** + * Constructor + * + * @param id the id of the object + * @param javadoc the javadoc of the object + * @param styleClass the styleclass of the object + */ public GuixModelObject(String id, String javadoc, String styleClass) { this.id = id; this.javadoc = javadoc; Modified: guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/parser/Java1.5.jjt =================================================================== --- guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/parser/Java1.5.jjt 2009-04-21 15:57:24 UTC (rev 1355) +++ guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/parser/Java1.5.jjt 2009-04-24 15:37:46 UTC (rev 1356) @@ -33,7 +33,7 @@ JAVA_UNICODE_ESCAPE = true; ERROR_REPORTING = false; STATIC = false; - JDK_VERSION = "1.4"; + JDK_VERSION = "1.6"; NODE_SCOPE_HOOK=true; } @@ -1083,27 +1083,27 @@ <EOF> { return true; } -| +| LOOKAHEAD(BlockStatement()) BlockStatement() { return false; - } -| - LOOKAHEAD(Modifiers() [ TypeParameters() ] [ ResultType() ] <IDENTIFIER> FormalParameters() [ "throws" NameList() ] "{") + } +| + LOOKAHEAD(Modifiers() [ TypeParameters() ] [ ResultType() ] <IDENTIFIER> FormalParameters() [ "throws" NameList() ] "{") ClassOrInterfaceBodyDeclaration(false) { return false; } -| - LOOKAHEAD(ClassOrInterfaceBodyDeclaration(false)) +| + LOOKAHEAD(ClassOrInterfaceBodyDeclaration(false)) ClassOrInterfaceBodyDeclaration(false) { return false; } | - LOOKAHEAD(Expression()) - Expression() { - return false; - } -| + LOOKAHEAD(Expression()) + Expression() { + return false; + } +| ImportDeclaration() { return false; } Modified: guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/tags/ScriptHandler.java =================================================================== --- guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/tags/ScriptHandler.java 2009-04-21 15:57:24 UTC (rev 1355) +++ guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/tags/ScriptHandler.java 2009-04-24 15:37:46 UTC (rev 1356) @@ -1,10 +1,10 @@ -/* - * Copyright 2006 Ethan Nicholas. All rights reserved. - * Use is subject to license terms. - */ package org.nuiton.guix.tags; +import java.io.File; +import java.io.FileNotFoundException; +import java.io.FileReader; import java.io.IOException; +import java.io.StringWriter; import java.util.logging.Level; import java.util.logging.Logger; import org.xmlpull.v1.XmlPullParser; @@ -13,31 +13,82 @@ /** * Handles the <code><script></code> tag. * - * @author Ethan Nicholas + * @author morin */ public class ScriptHandler { - public String compileScript(XmlPullParser xpp) { - try { - String script = null; + /** + * Loads the content of a script file + * + * @param scriptFile the file to load + * @return the content of the script file + * @throws java.io.IOException if an error occurs while reading scriptFile + */ + private String loadScriptFile(File scriptFile) throws IOException { + StringWriter scriptBuffer = new StringWriter(); + FileReader in = new FileReader(scriptFile); + char[] readBuffer = new char[2048]; + int c; + while ((c = in.read(readBuffer)) > 0) { + scriptBuffer.write(readBuffer, 0, c); + } + return scriptBuffer.toString(); + } + + /** + * Loads the file with the name of the class + * and get the content of the file. + * + * @param baseDir the directory of the compiled guix file + * @param className the name of the file to load + * @return the content of the file + * @throws IOException if an error occurs while reading the file + * with the same name as the class + */ + public String autoDetectScriptFile(String baseDir, String className) + throws IOException { + File scriptFile = null; + scriptFile = new File(baseDir, className + ".script"); + return loadScriptFile(scriptFile); + } + + /** + * Parse the <code>script</code> tag. + * + * @param xpp the parser referencing the style tag + * @param baseDir the directory of the compiled guix file + * @return the content of the file specified by the <code>source</code> attribute + * or the script between the script tags + * @throws IOException + * @throws XmlPullParserException + */ + public String compileScript(XmlPullParser xpp, String baseDir) + throws IOException, XmlPullParserException { + + StringBuffer script = new StringBuffer(); + File scriptFile = null; + //the name of the file to load + String source = xpp.getAttributeValue("", "source"); + + //if the source attribute is specified + if (source != null) { + scriptFile = new File(baseDir, source.replace('/', File.separatorChar)); + } + if (scriptFile != null && scriptFile.exists()) { + script.append(loadScriptFile(scriptFile)); + } + + xpp.nextToken(); + if (xpp.getEventType() == XmlPullParser.CDSECT) { + script.append(xpp.getText()); + } + while ((xpp.getEventType() != XmlPullParser.END_TAG) || (!xpp.getName().equals("script"))) { xpp.nextToken(); - if (xpp.getEventType() == XmlPullParser.CDSECT) { - script = xpp.getText(); - } - while ((xpp.getEventType() != XmlPullParser.END_TAG) || (!xpp.getName().equals("script"))) { - xpp.nextToken(); - } - do { - xpp.nextToken(); - } while (xpp.getEventType() != XmlPullParser.START_TAG && xpp.getEventType() != XmlPullParser.END_DOCUMENT); - return script; - } catch (XmlPullParserException ex) { - Logger.getLogger(ScriptHandler.class.getName()).log(Level.SEVERE, null, ex); - } catch (IOException ex) { - Logger.getLogger(ScriptHandler.class.getName()).log(Level.SEVERE, null, ex); } - finally { - return null; - } + do { + xpp.nextToken(); + } while (xpp.getEventType() != XmlPullParser.START_TAG && xpp.getEventType() != XmlPullParser.END_DOCUMENT); + + return script.toString(); } } Modified: guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/tags/StyleHandler.java =================================================================== --- guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/tags/StyleHandler.java 2009-04-21 15:57:24 UTC (rev 1355) +++ guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/tags/StyleHandler.java 2009-04-24 15:37:46 UTC (rev 1356) @@ -1,7 +1,4 @@ -/* - * Copyright 2006 Ethan Nicholas. All rights reserved. - * Use is subject to license terms. - */ + package org.nuiton.guix.tags; import java.io.File; @@ -14,6 +11,8 @@ import java.util.HashMap; import java.util.List; import java.util.Map; +import java.util.logging.Level; +import java.util.logging.Logger; import org.nuiton.guix.css.CSSParser; import org.nuiton.guix.css.CSSParserConstants; import org.nuiton.guix.css.CSSParserTreeConstants; @@ -28,74 +27,113 @@ /** * Handles the <code><style></code> tag. * - * @author Ethan Nicholas + * @author morin */ public class StyleHandler { + /** List of the selectors */ private List<Selector> selectors = new ArrayList<Selector>(); + /** + * Loads the content of a file. + * + * @param styleFile the file to load + * @return the content of the file + * @throws java.io.FileNotFoundException if styleFile does not exist + * @throws java.io.IOException if an error occurs while reading styleFile + */ + private String loadStyleFile(File styleFile) throws FileNotFoundException, IOException { + StringWriter styleBuffer = new StringWriter(); + FileReader in = new FileReader(styleFile); + char[] readBuffer = new char[2048]; + int c; + while ((c = in.read(readBuffer)) > 0) { + styleBuffer.write(readBuffer, 0, c); + } + return styleBuffer.toString(); + } + + /** + * Load the file with the name of the class + * and creates a <code>StyleSheet</code> with the content of the file. + * + * @param baseDir the directory of the compiled guix file + * @param className the name of the file to load + * @return a <code>StyleSheet</code> containing the content of the file + * @throws FileNotFoundException if the file with the same name as the class + * does not exist + * @throws IOException if an error occurs while reading the file + * with the same name as the class + */ + public StyleSheet autoDetectStyleFile(String baseDir, String className) throws FileNotFoundException, IOException { + File styleFile = null; + styleFile = new File(baseDir, className + ".css"); + return processStylesheet(loadStyleFile(styleFile)); + } + + /** + * Load the file specified by the <code>source</code> attribute + * or the code between the style tags + * and creates a <code>StyleSheet</code> with this content. + * + * @param xpp the parser referencing the style tag + * @param baseDir the directory of the compiled guix file + * @return a <code>StyleSheet</code> containing the content of the file + * @throws java.io.IOException if an error occurs while reading + * the file specified by the <code>source</code> attribute + * @throws org.xmlpull.v1.XmlPullParserException if an error occurs + * while parsing the guix file + */ public StyleSheet compileStyle(XmlPullParser xpp, String baseDir) throws IOException, XmlPullParserException { - boolean source = false; + File styleFile = null; StyleSheet result = null; - for (int i = 0; i < xpp.getAttributeCount(); i++) { - String name = xpp.getAttributeName(i); - String attrValue = xpp.getAttributeValue(i); - if (name.equals("source")) { - source = true; - File styleFile = new File(baseDir, attrValue.replace('/', File.separatorChar)); - StringWriter styleBuffer = new StringWriter(); - try { - FileReader in = new FileReader(styleFile); - char[] readBuffer = new char[2048]; - int c; - while ((c = in.read(readBuffer)) > 0) - styleBuffer.write(readBuffer, 0, c); - } - catch (FileNotFoundException e) { - //compiler.reportError( - System.out.println("stylesheet file not found: " + styleFile); - } - result = processStylesheet(styleBuffer.toString()); - /*compiler.getSourceFiles().push(styleFile); - compiler.registerStylesheet(processStylesheet(styleBuffer.toString())); - compiler.getSourceFiles().pop();*/ - }/* else - if (!name.startsWith("xmlns") && !JAXXCompiler.JAXX_INTERNAL_NAMESPACE.equals(attribute.getNamespaceURI())) - throw new UnsupportedAttributeException(name);*/ + //the name of the file to load + String source = xpp.getAttributeValue("", "source"); + + //if a file is specified + if (source != null) { + styleFile = new File(baseDir, source.replace('/', File.separatorChar)); } + StringBuffer style = new StringBuffer(); - StringBuffer style = new StringBuffer(); + if (styleFile != null && styleFile.exists()) { + style.append(loadStyleFile(styleFile)); + } + + xpp.nextToken(); do { - xpp.nextToken(); switch (xpp.getEventType()) { case XmlPullParser.START_TAG: - /*compiler.reportError*/System.out.println("<style> tag may not contain child elements: ");// + tag); + Logger.getLogger(StyleHandler.class.getName()).log(Level.WARNING, + "<style> tag may not contain child elements: " + xpp.getName()); break; - case XmlPullParser.TEXT: break;// fall through + case XmlPullParser.TEXT: + break;// fall through case XmlPullParser.CDSECT: + style.append(xpp.getText()); xpp.nextToken(); - style.append(xpp.getText()); break; } - } while((xpp.getEventType() != XmlPullParser.END_TAG) - && (!xpp.getName().equals("style"))); - - String styleString = style.toString().trim(); - if (styleString.length() > 0) { - if (source) - /*compiler.reportError*/System.out.println("<style> tag has both a source attribute and an inline stylesheet"); - //compiler.registerStylesheet(processStylesheet(style.toString())); - } + } while ((xpp.getEventType() != XmlPullParser.END_TAG) && (!xpp.getName().equals("style"))); + result = processStylesheet(style.toString()); + do { xpp.nextToken(); - } while(xpp.getEventType() != XmlPullParser.START_TAG - && xpp.getEventType() != XmlPullParser.END_DOCUMENT); + } while (xpp.getEventType() != XmlPullParser.START_TAG && xpp.getEventType() != XmlPullParser.END_DOCUMENT); + return result; + } + /** + * + * @param selector + * @return + */ protected Selector processSelector(SimpleNode selector) { - if (selector.getId() != CSSParserTreeConstants.JJTSELECTOR) + if (selector.getId() != CSSParserTreeConstants.JJTSELECTOR) { throw new IllegalArgumentException("argument node is not a Selector"); + } String javaClassName = null; String styleClass = null; String pseudoClass = null; @@ -105,8 +143,9 @@ SimpleNode child = selector.getChild(i); switch (child.getId()) { case CSSParserTreeConstants.JJTJAVACLASS: - if (!child.getText().trim().equals("*")) + if (!child.getText().trim().equals("*")) { javaClassName = child.getText(); + } break; case CSSParserTreeConstants.JJTCLASS: styleClass = child.getText().substring(1); @@ -122,11 +161,15 @@ throw new IllegalStateException("unexpected child of Selector node, type=" + child.getId()); } } - + return new Selector(javaClassName, styleClass, pseudoClass, id); } - + /** + * + * @param ruleNode + * @return + */ protected Rule processRule(SimpleNode ruleNode) { if (ruleNode.getId() != CSSParserTreeConstants.JJTRULE) { @@ -140,11 +183,12 @@ SimpleNode selectorNode = selectorsNode.getChild(i); Selector selector = processSelector(selectorNode); ruleSelectors.add(selector); - if(!selectorRecorded(selector)) + if (!selectorRecorded(selector)) { selectors.add(selector); + } } - Map<String,String> properties = new HashMap<String,String>(); + Map<String, String> properties = new HashMap<String, String>(); for (int i = 1; i < ruleNode.jjtGetNumChildren(); i++) { SimpleNode declarationNode = ruleNode.getChild(i); if (declarationNode.getId() == CSSParserTreeConstants.JJTDECLARATION) { @@ -160,14 +204,18 @@ Rule rule; rule = new Rule(); rule.setSelectors(ruleSelectors); - for(Selector selector : ruleSelectors) { + for (Selector selector : ruleSelectors) { selector.getRules().add(rule); } rule.setProperties(properties); return rule; } - + /** + * + * @param stylesheetText + * @return + */ protected StyleSheet processStylesheet(String stylesheetText) { CSSParser p = new CSSParser(new StringReader(stylesheetText)); SimpleNode node; @@ -189,8 +237,13 @@ return styleSheet; } + /** + * + * @param newSelector + * @return + */ private boolean selectorRecorded(Selector newSelector) { - for(Selector selector : selectors) { + for (Selector selector : selectors) { boolean areJavaClassNamesNull = newSelector.getJavaClassName() == null && selector.getJavaClassName() == null; boolean areJavaClassNamesNotNull = newSelector.getJavaClassName() != null && selector.getJavaClassName() != null; boolean areStyleClassesNull = newSelector.getStyleClass() == null && selector.getStyleClass() == null; @@ -199,14 +252,8 @@ boolean arePseudoClassesNotNull = newSelector.getPseudoClass() != null && selector.getPseudoClass() != null; boolean areIdsNull = newSelector.getId() == null && selector.getId() == null; boolean areIdsNotNull = newSelector.getId() != null && selector.getId() != null; - if((areJavaClassNamesNull || (areJavaClassNamesNotNull - && newSelector.getJavaClassName().equals(selector.getJavaClassName()))) - && (areStyleClassesNull || (areStyleClassesNotNull - && newSelector.getStyleClass().equals(selector.getStyleClass()))) - && (arePseudoClassesNull || (arePseudoClassesNotNull - && newSelector.getPseudoClass().equals(selector.getPseudoClass()))) - && (areIdsNull || (areIdsNotNull && newSelector.getId().equals(selector.getId())))) { - return true; + if ((areJavaClassNamesNull || (areJavaClassNamesNotNull && newSelector.getJavaClassName().equals(selector.getJavaClassName()))) && (areStyleClassesNull || (areStyleClassesNotNull && newSelector.getStyleClass().equals(selector.getStyleClass()))) && (arePseudoClassesNull || (arePseudoClassesNotNull && newSelector.getPseudoClass().equals(selector.getPseudoClass()))) && (areIdsNull || (areIdsNotNull && newSelector.getId().equals(selector.getId())))) { + return true; } } return false; Modified: guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/tags/TagManager.java =================================================================== --- guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/tags/TagManager.java 2009-04-21 15:57:24 UTC (rev 1355) +++ guix/trunk/guix-compiler/src/main/java/org/nuiton/guix/tags/TagManager.java 2009-04-24 15:37:46 UTC (rev 1356) @@ -13,7 +13,9 @@ import java.lang.reflect.Constructor; import java.lang.reflect.InvocationTargetException; import java.net.URL; +import java.util.ArrayList; import java.util.HashMap; +import java.util.List; import java.util.Map; import java.util.Set; @@ -26,7 +28,7 @@ * Namespace for JAXX's non-class tags, such as <script;>. The namespace normally does not * need to be specified but can be used to resolve ambiguities. */ - public static final String JAXX_NAMESPACE = "http://www.jaxxframework.org/"; + public static final String GUIX_NAMESPACE = "org.nuiton.guix.*"; /** Maps simple tag names to their default namespaces (package names). */ private static Map<String, String> defaultNamespaces = new HashMap<String, String>(); @@ -37,6 +39,9 @@ /** Keeps track of whether or not named classes exist. */ private static Map<String, Boolean> classExistenceCache = new HashMap<String, Boolean>(); + /** */ + private static List<String> guixClasses = new ArrayList<String>(); + /** * Maps bean classes to their TagHandler classes. The mapping is to TagHandler classes, rather than to * TagHandler instances, because subclasses of the bean class should be handled by the same TagHandler @@ -142,6 +147,13 @@ } } + /** + * + * @param className + */ + public static void registerGuixClasse(String className) { + guixClasses.add(className); + } /** * Registers a <code>TagHandler</code> for a tag. When a tag with the given name and namespace @@ -319,82 +331,11 @@ if (name.equals("boolean") || name.equals("byte") || name.equals("short") || name.equals("int") || name.equals("long") || name.equals("float") || name.equals("double") || name.equals("char")) return name; - - String result = null; - String originalName = name; - String defaultNamespace = null; - if (defaultNamespaces.containsKey(name)) { - defaultNamespace = defaultNamespaces.get(name); - if (defaultNamespace == null) { // defaultNamespaces map contains a null value, which is put there to indicate ambiguity - //compiler.reportError("class '" + name + "' is ambiguous; specify fully-qualified name (package and class) to disambiguate"); - return null; - } + + if (guixClasses.contains(name)) { + return GUIX_NAMESPACE.substring(0, GUIX_NAMESPACE.lastIndexOf('*')) + name; } - if (defaultNamespace != null && defaultNamespace.endsWith("*")) { - result = defaultNamespace.substring(0, defaultNamespace.length() - 1) + name; - } - - /*if (result == null) { - // Inner class names (like JPopupMenu.Separator) present a special challenge. The name before the dot might be - // a package name, or it might be a class name. If it's a class name, it might be fully qualified, or it might - // not. And it's also not actually the correct name of the class, as far as the JVM is concerned -- the correct - // name uses a dollar sign instead of a dot (javax.swing.JPopupMenu$Separator). And there could be more than - // one inner class -- it's possible to have com.mycompany.Outer$Inner$Innerer$Innerest. - // - // The basic strategy is to start by treating the part before the last dot as a package name, as that is by far - // the most likely case. If we don't find the class there, change the last dot to a dollar sign and try again. - // Suppose we have the tag <com.mycompany.Outer.Inner.Innerer.Innerest/>, matching the class above. Resolution - // proceeds like this: - // com.mycompany.Outer.Inner.Innerer.* : Innerest - // com.mycompany.Outer.Inner.* : Innerer$Innerest - // com.mycompany.Outer.* : Inner$Innerer$Innerest - // com.mycompany.* : Outer$Inner$Innerer$Innerest - // And at this point we have a match with the class Outer$Inner$Innerer$Innerest in package com.mycompany. - int dotPos = originalName.lastIndexOf('.'); - for (; ;) { - String namespace = dotPos != -1 ? originalName.substring(0, dotPos) + ".*" : "*"; - name = originalName.substring(dotPos + 1).replace('.', '$'); - String packageName = determinePackage(name, namespace); - if (packageName != null) { - assert packageName.endsWith("*"); - if (packageName.equals(namespace) || namespace.equals("*")) { - // check for an alias (like javax.swing.JComboBox actually being jaxx.runtime.swing.JAXXComboBox) - TagHandler handler = registeredTags.get(new QName(namespace, name)); - if (handler != null) { // determine alias by looking at handler - ClassDescriptor alias = ((DefaultObjectHandler) handler).getBeanClass(); - // make sure the same handler is used for both the aliased and non-aliased names, in order to avoid "no CompiledObject has been registered" error - // the line below doesn't bother to handle the case where the aliased class name doesn't have a package, since it's a pretty safe assumption that - // that will never happen - assert alias.getPackageName() != null && alias.getPackageName().length() > 0 : "aliasing with no package name has not been implemented"; - registeredTags.put(new QName(alias.getPackageName() + ".*", alias.getName().substring(alias.getPackageName().length() + 1)), handler); - result = alias.getName(); - break; - } else { // no alias - result = packageName.substring(0, packageName.length() - 1) + name; - break; - } - } - // else we found a class by the same name, but in the wrong package - } - - if (dotPos <= 0) - break; - dotPos = originalName.lastIndexOf('.', dotPos - 1); - } - }*/ - - //if (result != null && !result.equals(originalName)) - //result = resolveClassName(result); // check for aliases against the new name as well - - Class clazz; - try { - clazz = Class.forName(name); - result = clazz.getCanonicalName(); - } catch (ClassNotFoundException ex) { - result = null; - } - - return result; + return null; }
participants (1)
-
kmorin@users.labs.libre-entreprise.org