You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@flex.apache.org by cd...@apache.org on 2016/04/14 09:46:30 UTC
[01/18] git commit: [flex-falcon]
[refs/heads/feature/maven-migration-test] - handle multiline XML literals
Repository: flex-falcon
Updated Branches:
refs/heads/feature/maven-migration-test c3dce49fd -> de0706362
handle multiline XML literals
Project: http://git-wip-us.apache.org/repos/asf/flex-falcon/repo
Commit: http://git-wip-us.apache.org/repos/asf/flex-falcon/commit/11e53909
Tree: http://git-wip-us.apache.org/repos/asf/flex-falcon/tree/11e53909
Diff: http://git-wip-us.apache.org/repos/asf/flex-falcon/diff/11e53909
Branch: refs/heads/feature/maven-migration-test
Commit: 11e53909863d82632c362d67aa37aab3d6631623
Parents: b0cd32c
Author: Alex Harui <ah...@apache.org>
Authored: Tue Apr 12 09:36:25 2016 -0700
Committer: Alex Harui <ah...@apache.org>
Committed: Tue Apr 12 09:36:35 2016 -0700
----------------------------------------------------------------------
.../js/flexjs/TestFlexJSGlobalClasses.java | 16 +++++++++---
.../internal/codegen/js/jx/LiteralEmitter.java | 26 +++++++++++---------
2 files changed, 26 insertions(+), 16 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/11e53909/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
----------------------------------------------------------------------
diff --git a/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java b/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
index 638f71b..d219506 100644
--- a/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
+++ b/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
@@ -321,7 +321,15 @@ public class TestFlexJSGlobalClasses extends TestGoogGlobalClasses
{
IVariableNode node = getVariable("var a:XML = <top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>");
asBlockWalker.visitVariable(node);
- assertOut("var /** @type {XML} */ a = new XML( \"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\") ");
+ assertOut("var /** @type {XML} */ a = new XML( \"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\")");
+ }
+
+ @Test
+ public void testXMLLiteralMultiline()
+ {
+ IVariableNode node = getVariable("var a:XML = <top attr1='cat'>\n<child attr2='dog'>\n<grandchild attr3='fish'>text</grandchild>\n</child>\n</top>");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {XML} */ a = new XML( \"<top attr1='cat'>\\\n<child attr2='dog'>\\\n<grandchild attr3='fish'>text</grandchild>\\\n</child>\\\n</top>\")");
}
@Test
@@ -334,7 +342,7 @@ public class TestFlexJSGlobalClasses extends TestGoogGlobalClasses
"private function test() { var a:XML = <{tagname} {attributename}={attributevalue}>{content}</{tagname}>;}",
VariableNode.class, WRAP_LEVEL_CLASS);
asBlockWalker.visitVariable(node);
- assertOut("var /** @type {XML} */ a = new XML( '<' + this.tagname + ' ' + this.attributename + '=' + this.attributevalue + '>' + this.content + '</' + this.tagname + '>') ");
+ assertOut("var /** @type {XML} */ a = new XML( '<' + this.tagname + ' ' + this.attributename + '=' + this.attributevalue + '>' + this.content + '</' + this.tagname + '>')");
}
@Test
@@ -343,7 +351,7 @@ public class TestFlexJSGlobalClasses extends TestGoogGlobalClasses
IFunctionCallNode node = (IFunctionCallNode)getNode("var a:XML; a.appendChild(<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>)",
IFunctionCallNode.class);
asBlockWalker.visitFunctionCall(node);
- assertOut("a.appendChild(new XML( \"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\") )");
+ assertOut("a.appendChild(new XML( \"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\"))");
}
@Test
@@ -351,7 +359,7 @@ public class TestFlexJSGlobalClasses extends TestGoogGlobalClasses
{
IBinaryOperatorNode node = getBinaryNode("var a:XML = <foo />; a = <top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>)");
asBlockWalker.visitBinaryOperator(node);
- assertOut("a = new XML( \"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\") ");
+ assertOut("a = new XML( \"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\")");
}
@Test
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/11e53909/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/LiteralEmitter.java
----------------------------------------------------------------------
diff --git a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/LiteralEmitter.java b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/LiteralEmitter.java
index 70d2c48..068d870 100644
--- a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/LiteralEmitter.java
+++ b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/LiteralEmitter.java
@@ -45,48 +45,50 @@ public class LiteralEmitter extends JSSubEmitter implements
{
boolean isWritten = false;
+ String newlineReplacement = "\\\\n";
String s = node.getValue(true);
if (!(node instanceof RegExpLiteralNode))
{
if (node.getLiteralType() == LiteralType.XML)
{
- write("new XML");
- writeToken(ASEmitterTokens.PAREN_OPEN);
+ newlineReplacement = "\\\\\n";
XMLLiteralNode xmlNode = (XMLLiteralNode)node;
if (xmlNode.getContentsNode().getChildCount() == 1)
{
if (s.contains("'"))
- write("\"" + s + "\"");
+ s = "\"" + s + "\"";
else
- write("'" + s + "'");
- isWritten = true;
+ s = "'" + s + "'";
+ s = "new XML( " + s + ")";
}
else
{
+ StringBuilder sb = new StringBuilder();
+ sb.append("new XML( ");
// probably contains {initializers}
int n = xmlNode.getContentsNode().getChildCount();
for (int i = 0; i < n; i++)
{
if (i > 0)
- write(" + ");
+ sb.append(" + ");
IASNode child = xmlNode.getContentsNode().getChild(i);
if (child instanceof LiteralNode)
{
s = ((LiteralNode)child).getValue(true);
if (s.contains("'"))
- write("\"" + s + "\"");
+ sb.append("\"" + s + "\"");
else
- write("'" + s + "'");
- isWritten = true;
+ sb.append("'" + s + "'");
}
else if (child instanceof IdentifierNode)
{
s = getEmitter().stringifyNode(child);
- write(s);
+ sb.append(s);
}
}
+ sb.append(")");
+ s = sb.toString();
}
- writeToken(ASEmitterTokens.PAREN_CLOSE);
}
s = s.replaceAll("\n", "__NEWLINE_PLACEHOLDER__");
s = s.replaceAll("\r", "__CR_PLACEHOLDER__");
@@ -102,7 +104,7 @@ public class LiteralEmitter extends JSSubEmitter implements
s = s.replaceAll("__FORMFEED_PLACEHOLDER__", "\\\\f");
s = s.replaceAll("__TAB_PLACEHOLDER__", "\\\\t");
s = s.replaceAll("__CR_PLACEHOLDER__", "\\\\r");
- s = s.replaceAll("__NEWLINE_PLACEHOLDER__", "\\\\n");
+ s = s.replaceAll("__NEWLINE_PLACEHOLDER__", newlineReplacement);
if (node.getLiteralType() == LiteralType.STRING)
{
char c = s.charAt(0);
[07/18] git commit: [flex-falcon]
[refs/heads/feature/maven-migration-test] - FLEX-35077 handle more XML in
assignments
Posted by cd...@apache.org.
FLEX-35077 handle more XML in assignments
Project: http://git-wip-us.apache.org/repos/asf/flex-falcon/repo
Commit: http://git-wip-us.apache.org/repos/asf/flex-falcon/commit/0b74b6a3
Tree: http://git-wip-us.apache.org/repos/asf/flex-falcon/tree/0b74b6a3
Diff: http://git-wip-us.apache.org/repos/asf/flex-falcon/diff/0b74b6a3
Branch: refs/heads/feature/maven-migration-test
Commit: 0b74b6a3514bf68ab67016aa5aed5c40943f4139
Parents: 395863b
Author: Alex Harui <ah...@apache.org>
Authored: Tue Apr 12 16:34:04 2016 -0700
Committer: Alex Harui <ah...@apache.org>
Committed: Tue Apr 12 16:34:04 2016 -0700
----------------------------------------------------------------------
.../internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java | 8 ++++++++
.../compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java | 2 ++
2 files changed, 10 insertions(+)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/0b74b6a3/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
----------------------------------------------------------------------
diff --git a/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java b/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
index 3fb8e67..de10f74 100644
--- a/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
+++ b/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
@@ -549,6 +549,14 @@ public class TestFlexJSGlobalClasses extends TestGoogGlobalClasses
}
@Test
+ public void testXMLListSetAttributeComplex()
+ {
+ IBinaryOperatorNode node = getBinaryNode("var a:XMLList;a.(@id==3).@height = '100px'");
+ asBlockWalker.visitBinaryOperator(node);
+ assertOut("a.filter(function(node){return (node.attribute('id') == 3)}).setAttribute('height', '100px')");
+ }
+
+ @Test
public void testXMLSetChild()
{
IBinaryOperatorNode node = getBinaryNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");a.foo = a.child");
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/0b74b6a3/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java
----------------------------------------------------------------------
diff --git a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java
index d345277..99114b3 100644
--- a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java
+++ b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java
@@ -917,6 +917,8 @@ public class JSFlexJSEmitter extends JSGoogEmitter implements IJSFlexJSEmitter
return IdentifierNode.isXMLish(leftDef, getWalker().getProject());
}
+ else if (leftID == ASTNodeID.E4XFilterID)
+ return true;
return false;
}
[18/18] git commit: [flex-falcon]
[refs/heads/feature/maven-migration-test] - Merge branch 'develop' of
https://git-wip-us.apache.org/repos/asf/flex-falcon into
feature/maven-migration-test
Posted by cd...@apache.org.
Merge branch 'develop' of https://git-wip-us.apache.org/repos/asf/flex-falcon into feature/maven-migration-test
Project: http://git-wip-us.apache.org/repos/asf/flex-falcon/repo
Commit: http://git-wip-us.apache.org/repos/asf/flex-falcon/commit/de070636
Tree: http://git-wip-us.apache.org/repos/asf/flex-falcon/tree/de070636
Diff: http://git-wip-us.apache.org/repos/asf/flex-falcon/diff/de070636
Branch: refs/heads/feature/maven-migration-test
Commit: de070636246d09e27b8aa25898cd22aa2dee1ae1
Parents: c3dce49 bc19c66
Author: Christofer Dutz <ch...@codecentric.de>
Authored: Thu Apr 14 09:39:02 2016 +0200
Committer: Christofer Dutz <ch...@codecentric.de>
Committed: Thu Apr 14 09:39:02 2016 +0200
----------------------------------------------------------------------
.../apache/flex/compiler/clients/MXMLJSC.java | 109 ++++++++-------
.../internal/codegen/js/JSSessionModel.java | 2 +
.../codegen/js/flexjs/JSFlexJSEmitter.java | 12 ++
.../codegen/js/jx/BinaryOperatorEmitter.java | 17 +++
.../codegen/js/jx/IdentifierEmitter.java | 14 ++
.../internal/codegen/js/jx/LiteralEmitter.java | 26 ++--
.../internal/codegen/js/utils/EmitterUtils.java | 12 ++
.../internal/codegen/mxml/MXMLWriter.java | 3 +-
.../codegen/mxml/flexjs/MXMLFlexJSEmitter.java | 73 +++++-----
.../mxml/flexjs/MXMLFlexJSPublisher.java | 140 ++++++++++---------
.../driver/js/goog/JSGoogConfiguration.java | 20 +++
.../js/flexjs/TestFlexJSGlobalClasses.java | 58 +++++++-
.../projects/xml_requires/XMLRequire_result.js | 2 +-
13 files changed, 320 insertions(+), 168 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/de070636/compiler-jx/src/main/java/org/apache/flex/compiler/clients/MXMLJSC.java
----------------------------------------------------------------------
diff --cc compiler-jx/src/main/java/org/apache/flex/compiler/clients/MXMLJSC.java
index d324c9f,0000000..c6d9508
mode 100644,000000..100644
--- a/compiler-jx/src/main/java/org/apache/flex/compiler/clients/MXMLJSC.java
+++ b/compiler-jx/src/main/java/org/apache/flex/compiler/clients/MXMLJSC.java
@@@ -1,847 -1,0 +1,852 @@@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+package org.apache.flex.compiler.clients;
+
+import java.io.BufferedOutputStream;
+import java.io.File;
+import java.io.FileNotFoundException;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.List;
+import java.util.Set;
+
+import org.apache.commons.io.FilenameUtils;
+import org.apache.flex.compiler.clients.problems.ProblemPrinter;
+import org.apache.flex.compiler.clients.problems.ProblemQuery;
+import org.apache.flex.compiler.clients.problems.ProblemQueryProvider;
+import org.apache.flex.compiler.clients.problems.WorkspaceProblemFormatter;
+import org.apache.flex.compiler.codegen.js.IJSPublisher;
+import org.apache.flex.compiler.codegen.js.IJSWriter;
+import org.apache.flex.compiler.config.Configuration;
+import org.apache.flex.compiler.config.ConfigurationBuffer;
+import org.apache.flex.compiler.config.Configurator;
+import org.apache.flex.compiler.config.ICompilerSettingsConstants;
+import org.apache.flex.compiler.driver.IBackend;
+import org.apache.flex.compiler.driver.js.IJSApplication;
+import org.apache.flex.compiler.exceptions.ConfigurationException;
+import org.apache.flex.compiler.exceptions.ConfigurationException.IOError;
+import org.apache.flex.compiler.exceptions.ConfigurationException.MustSpecifyTarget;
+import org.apache.flex.compiler.exceptions.ConfigurationException.OnlyOneSource;
+import org.apache.flex.compiler.internal.codegen.js.JSSharedData;
+import org.apache.flex.compiler.internal.config.FlashBuilderConfigurator;
+import org.apache.flex.compiler.internal.driver.as.ASBackend;
+import org.apache.flex.compiler.internal.driver.js.amd.AMDBackend;
+import org.apache.flex.compiler.internal.driver.js.goog.GoogBackend;
+import org.apache.flex.compiler.internal.driver.js.goog.JSGoogConfiguration;
+import org.apache.flex.compiler.internal.driver.js.jsc.JSCBackend;
+import org.apache.flex.compiler.internal.driver.js.node.NodeBackend;
+import org.apache.flex.compiler.internal.driver.mxml.flexjs.MXMLFlexJSBackend;
+import org.apache.flex.compiler.internal.driver.mxml.vf2js.MXMLVF2JSBackend;
+import org.apache.flex.compiler.internal.parsing.as.FlexJSASDocDelegate;
+import org.apache.flex.compiler.internal.projects.CompilerProject;
+import org.apache.flex.compiler.internal.projects.FlexJSProject;
+import org.apache.flex.compiler.internal.projects.ISourceFileHandler;
+import org.apache.flex.compiler.internal.targets.JSTarget;
+import org.apache.flex.compiler.internal.units.ResourceModuleCompilationUnit;
+import org.apache.flex.compiler.internal.units.SourceCompilationUnitFactory;
+import org.apache.flex.compiler.internal.workspaces.Workspace;
+import org.apache.flex.compiler.problems.ConfigurationProblem;
+import org.apache.flex.compiler.problems.ICompilerProblem;
+import org.apache.flex.compiler.problems.InternalCompilerProblem;
+import org.apache.flex.compiler.problems.UnableToBuildSWFProblem;
+import org.apache.flex.compiler.problems.UnexpectedExceptionProblem;
+import org.apache.flex.compiler.projects.ICompilerProject;
+import org.apache.flex.compiler.targets.ITarget;
+import org.apache.flex.compiler.targets.ITarget.TargetType;
+import org.apache.flex.compiler.targets.ITargetSettings;
+import org.apache.flex.compiler.units.ICompilationUnit;
+import org.apache.flex.tools.FlexTool;
+import org.apache.flex.utils.ArgumentUtil;
+import org.apache.flex.utils.FilenameNormalization;
+
+import com.google.common.base.Preconditions;
+import com.google.common.collect.Iterables;
+
+/**
+ * @author Erik de Bruin
+ * @author Michael Schmalle
+ */
+public class MXMLJSC implements JSCompilerEntryPoint, ProblemQueryProvider,
+ FlexTool
+{
+ @Override
+ public ProblemQuery getProblemQuery()
+ {
+ return problems;
+ }
+
+ /*
+ * JS output type enumerations.
+ */
+ public enum JSOutputType
+ {
+ AMD("amd"),
+ FLEXJS("flexjs"),
+ GOOG("goog"),
+ VF2JS("vf2js"),
+ FLEXJS_DUAL("flexjs_dual"),
+ JSC("jsc"),
+ NODE("node");
+
+ private String text;
+
+ JSOutputType(String text)
+ {
+ this.text = text;
+ }
+
+ public String getText()
+ {
+ return this.text;
+ }
+
+ public static JSOutputType fromString(String text)
+ {
+ for (JSOutputType jsOutputType : JSOutputType.values())
+ {
+ if (text.equalsIgnoreCase(jsOutputType.text))
+ return jsOutputType;
+ }
+ return GOOG;
+ }
+ }
+
+ /*
+ * Exit code enumerations.
+ */
+ static enum ExitCode
+ {
+ SUCCESS(0),
+ PRINT_HELP(1),
+ FAILED_WITH_PROBLEMS(2),
+ FAILED_WITH_ERRORS(3),
+ FAILED_WITH_EXCEPTIONS(4),
+ FAILED_WITH_CONFIG_PROBLEMS(5);
+
+ ExitCode(int code)
+ {
+ this.code = code;
+ }
+
+ final int code;
+ }
+
+ public static JSOutputType jsOutputType;
+ public static boolean keepASDoc;
+
+ @Override
+ public String getName()
+ {
+ return FLEX_TOOL_MXMLC;
+ }
+
+ @Override
+ public int execute(String[] args)
+ {
+ final List<ICompilerProblem> problems = new ArrayList<ICompilerProblem>();
+ return mainNoExit(args, problems, true);
+ }
+
+ /**
+ * Java program entry point.
+ *
+ * @param args command line arguments
+ */
+ public static void main(final String[] args)
+ {
+ int exitCode = staticMainNoExit(args);
+ System.exit(exitCode);
+ }
+
+ /**
+ * Entry point for the {@code <compc>} Ant task.
+ *
+ * @param args Command line arguments.
+ * @return An exit code.
+ */
+ public static int staticMainNoExit(final String[] args)
+ {
+ long startTime = System.nanoTime();
+
+ IBackend backend = new ASBackend();
+ String jsOutputTypeString = "";
+ for (String s : args)
+ {
+ String[] kvp = s.split("=");
+
+ if (s.contains("-js-output-type"))
+ {
+ jsOutputTypeString = kvp[1];
+ }
+ }
+
+ if (jsOutputTypeString.equals(""))
+ {
+ jsOutputTypeString = JSOutputType.FLEXJS.getText();
+ }
+
+ jsOutputType = JSOutputType.fromString(jsOutputTypeString);
+ switch (jsOutputType)
+ {
+ case AMD:
+ backend = new AMDBackend();
+ break;
+ case JSC:
+ backend = new JSCBackend();
+ break;
+ case NODE:
+ backend = new NodeBackend();
+ break;
+ case FLEXJS:
+ case FLEXJS_DUAL:
+ backend = new MXMLFlexJSBackend();
+ break;
+ case GOOG:
+ backend = new GoogBackend();
+ break;
+ case VF2JS:
+ backend = new MXMLVF2JSBackend();
+ break;
+ // if you add a new js-output-type here, don't forget to also add it
+ // to flex2.tools.MxmlJSC in flex-compiler-oem for IDE support
+ }
+
+ final MXMLJSC mxmlc = new MXMLJSC(backend);
+ final List<ICompilerProblem> problems = new ArrayList<ICompilerProblem>();
+ final int exitCode = mxmlc.mainNoExit(args, problems, true);
+
+ long endTime = System.nanoTime();
+ JSSharedData.instance.stdout((endTime - startTime) / 1e9 + " seconds");
+
+ return exitCode;
+ }
+
+ protected Workspace workspace;
+ protected FlexJSProject project;
+
+ protected ProblemQuery problems;
+ protected ISourceFileHandler asFileHandler;
+ protected Configuration config;
+ protected Configurator projectConfigurator;
+ private ConfigurationBuffer configBuffer;
+ private ICompilationUnit mainCU;
+ protected ITarget target;
+ protected ITargetSettings targetSettings;
+ protected IJSApplication jsTarget;
+ private IJSPublisher jsPublisher;
+
+ public MXMLJSC(IBackend backend)
+ {
+ JSSharedData.backend = backend;
+ workspace = new Workspace();
+ workspace.setASDocDelegate(new FlexJSASDocDelegate());
+ project = new FlexJSProject(workspace);
+ problems = new ProblemQuery(); // this gets replaced in configure(). Do we need it here?
+ JSSharedData.OUTPUT_EXTENSION = backend.getOutputExtension();
+ JSSharedData.workspace = workspace;
+ asFileHandler = backend.getSourceFileHandlerInstance();
+ }
+
+ @Override
+ public int mainNoExit(final String[] args, List<ICompilerProblem> problems,
+ Boolean printProblems)
+ {
+ int exitCode = -1;
+ try
+ {
+ exitCode = _mainNoExit(ArgumentUtil.fixArgs(args), problems);
+ }
+ catch (Exception e)
+ {
+ JSSharedData.instance.stderr(e.toString());
+ }
+ finally
+ {
+ if (problems != null && !problems.isEmpty())
+ {
+ if (printProblems)
+ {
+ final WorkspaceProblemFormatter formatter = new WorkspaceProblemFormatter(
+ workspace);
+ final ProblemPrinter printer = new ProblemPrinter(formatter);
+ printer.printProblems(problems);
+ }
+ }
+ }
+ return exitCode;
+ }
+
+ /**
+ * Entry point that doesn't call <code>System.exit()</code>. This is for
+ * unit testing.
+ *
+ * @param args command line arguments
+ * @return exit code
+ */
+ private int _mainNoExit(final String[] args,
+ List<ICompilerProblem> outProblems)
+ {
+ ExitCode exitCode = ExitCode.SUCCESS;
+ try
+ {
+ String[] adjustedArgs = args;
+
+ if (jsOutputType != null)
+ {
+ switch (jsOutputType)
+ {
+ case VF2JS:
+ boolean isFlashBuilderProject = useFlashBuilderProjectFiles(args);
+
+ if (isFlashBuilderProject)
+ {
+ adjustedArgs = FlashBuilderConfigurator.computeFlashBuilderArgs(
+ adjustedArgs, getTargetType().getExtension());
+ }
+
+ //String projectFilePath = adjustedArgs[adjustedArgs.length - 1];
+ //
+ //String newProjectFilePath = VF2JSProjectUtils
+ // .createTempProject(projectFilePath,
+ // isFlashBuilderProject);
+ //
+ //adjustedArgs[adjustedArgs.length - 1] = newProjectFilePath;
+
+ break;
+ default:
+ break;
+ }
+ }
+
+ final boolean continueCompilation = configure(adjustedArgs);
+
+ // ToDo (erikdebruin): use JSSharedData for globals ...
+ keepASDoc = ((JSGoogConfiguration) config).getKeepASDoc();
+
+ if (outProblems != null && !config.isVerbose())
+ JSSharedData.STDOUT = JSSharedData.STDERR = null;
+
+ if (continueCompilation)
+ {
+ project.setProblems(problems.getProblems());
- compile();
++ compile();
+ if (problems.hasFilteredProblems())
+ {
+ if (problems.hasErrors())
+ exitCode = ExitCode.FAILED_WITH_ERRORS;
+ else
+ exitCode = ExitCode.FAILED_WITH_PROBLEMS;
+ }
+ }
+ else if (problems.hasFilteredProblems())
+ {
+ exitCode = ExitCode.FAILED_WITH_CONFIG_PROBLEMS;
+ }
+ else
+ {
+ exitCode = ExitCode.PRINT_HELP;
+ }
+ }
+ catch (Exception e)
+ {
+ if (outProblems == null)
+ JSSharedData.instance.stderr(e.getMessage());
+ else
+ {
+ final ICompilerProblem unexpectedExceptionProblem = new UnexpectedExceptionProblem(
+ e);
+ problems.add(unexpectedExceptionProblem);
+ }
+ exitCode = ExitCode.FAILED_WITH_EXCEPTIONS;
+ }
+ finally
+ {
+ waitAndClose();
+
+ if (outProblems != null && problems.hasFilteredProblems())
+ {
+ for (ICompilerProblem problem : problems.getFilteredProblems())
+ {
+ outProblems.add(problem);
+ }
+ }
+ }
+ return exitCode.code;
+ }
+
+ /**
+ * Main body of this program. This method is called from the public static
+ * method's for this program.
+ *
+ * @return true if compiler succeeds
+ * @throws IOException
+ * @throws InterruptedException
+ */
+ protected boolean compile()
+ {
+ boolean compilationSuccess = false;
+
+ try
+ {
+ project.getSourceCompilationUnitFactory().addHandler(asFileHandler);
+
- if (!setupTargetFile())
- return false;
-
- buildArtifact();
++ if (!((JSGoogConfiguration) config).getSkipTranspile())
++ {
++ if (!setupTargetFile())
++ return false;
+
- if (jsTarget != null)
++ buildArtifact();
++ }
++ if (jsTarget != null || ((JSGoogConfiguration) config).getSkipTranspile())
+ {
+ List<ICompilerProblem> errors = new ArrayList<ICompilerProblem>();
+ List<ICompilerProblem> warnings = new ArrayList<ICompilerProblem>();
+
+ if (!config.getCreateTargetWithErrors())
+ {
+ problems.getErrorsAndWarnings(errors, warnings);
+ if (errors.size() > 0)
+ return false;
+ }
+
+ jsPublisher = (IJSPublisher) JSSharedData.backend.createPublisher(
+ project, errors, config);
+
+ File outputFolder = jsPublisher.getOutputFolder();
+
- ArrayList<ICompilationUnit> roots = new ArrayList<ICompilationUnit>();
- roots.add(mainCU);
- Set<ICompilationUnit> incs = target.getIncludesCompilationUnits();
- roots.addAll(incs);
- List<ICompilationUnit> reachableCompilationUnits = project.getReachableCompilationUnitsInSWFOrder(roots);
- for (final ICompilationUnit cu : reachableCompilationUnits)
++ if (!((JSGoogConfiguration) config).getSkipTranspile())
+ {
- ICompilationUnit.UnitType cuType = cu.getCompilationUnitType();
-
- if (cuType == ICompilationUnit.UnitType.AS_UNIT
- || cuType == ICompilationUnit.UnitType.MXML_UNIT)
- {
- final File outputClassFile = getOutputClassFile(
- cu.getQualifiedNames().get(0), outputFolder);
-
- System.out.println("Compiling file: " + outputClassFile);
-
- ICompilationUnit unit = cu;
-
- IJSWriter writer;
- if (cuType == ICompilationUnit.UnitType.AS_UNIT)
- {
- writer = (IJSWriter) JSSharedData.backend.createWriter(project,
- errors, unit, false);
- }
- else
- {
- writer = (IJSWriter) JSSharedData.backend.createMXMLWriter(
- project, errors, unit, false);
- }
-
- BufferedOutputStream out = new BufferedOutputStream(
- new FileOutputStream(outputClassFile));
-
- File outputSourceMapFile = null;
- if (project.config.getSourceMap())
- {
- outputSourceMapFile = getOutputSourceMapFile(
- cu.getQualifiedNames().get(0), outputFolder);
- }
-
- writer.writeTo(out, outputSourceMapFile);
- out.flush();
- out.close();
- writer.close();
- }
++ ArrayList<ICompilationUnit> roots = new ArrayList<ICompilationUnit>();
++ roots.add(mainCU);
++ Set<ICompilationUnit> incs = target.getIncludesCompilationUnits();
++ roots.addAll(incs);
++ List<ICompilationUnit> reachableCompilationUnits = project.getReachableCompilationUnitsInSWFOrder(roots);
++ for (final ICompilationUnit cu : reachableCompilationUnits)
++ {
++ ICompilationUnit.UnitType cuType = cu.getCompilationUnitType();
++
++ if (cuType == ICompilationUnit.UnitType.AS_UNIT
++ || cuType == ICompilationUnit.UnitType.MXML_UNIT)
++ {
++ final File outputClassFile = getOutputClassFile(
++ cu.getQualifiedNames().get(0), outputFolder);
++
++ System.out.println("Compiling file: " + outputClassFile);
++
++ ICompilationUnit unit = cu;
++
++ IJSWriter writer;
++ if (cuType == ICompilationUnit.UnitType.AS_UNIT)
++ {
++ writer = (IJSWriter) JSSharedData.backend.createWriter(project,
++ errors, unit, false);
++ }
++ else
++ {
++ writer = (IJSWriter) JSSharedData.backend.createMXMLWriter(
++ project, errors, unit, false);
++ }
++
++ BufferedOutputStream out = new BufferedOutputStream(
++ new FileOutputStream(outputClassFile));
++
++ File outputSourceMapFile = null;
++ if (project.config.getSourceMap())
++ {
++ outputSourceMapFile = getOutputSourceMapFile(
++ cu.getQualifiedNames().get(0), outputFolder);
++ }
++
++ writer.writeTo(out, outputSourceMapFile);
++ out.flush();
++ out.close();
++ writer.close();
++ }
++ }
+ }
-
++
+ if (jsPublisher != null)
+ {
+ compilationSuccess = jsPublisher.publish(problems);
+ }
+ else
+ {
+ compilationSuccess = true;
+ }
+ }
+ }
+ catch (Exception e)
+ {
+ final ICompilerProblem problem = new InternalCompilerProblem(e);
+ problems.add(problem);
+ }
+
+ return compilationSuccess;
+ }
+
+ /**
+ * Build target artifact.
+ *
+ * @throws InterruptedException threading error
+ * @throws IOException IO error
+ * @throws ConfigurationException
+ */
+ protected void buildArtifact() throws InterruptedException, IOException,
+ ConfigurationException
+ {
+ jsTarget = buildJSTarget();
+ }
+
+ private IJSApplication buildJSTarget() throws InterruptedException,
+ FileNotFoundException, ConfigurationException
+ {
+ final List<ICompilerProblem> problemsBuildingSWF = new ArrayList<ICompilerProblem>();
+
+ project.mainCU = mainCU;
+ final IJSApplication app = buildApplication(project,
+ config.getMainDefinition(), mainCU, problemsBuildingSWF);
+ problems.addAll(problemsBuildingSWF);
+ if (app == null)
+ {
+ ICompilerProblem problem = new UnableToBuildSWFProblem(
+ getOutputFilePath());
+ problems.add(problem);
+ }
+
+ return app;
+ }
+
+ /**
+ * Replaces FlexApplicationProject::buildSWF()
+ *
+ * @param applicationProject
+ * @param rootClassName
+ * @param problems
+ * @return
+ * @throws InterruptedException
+ */
+
+ private IJSApplication buildApplication(CompilerProject applicationProject,
+ String rootClassName, ICompilationUnit mainCU,
+ Collection<ICompilerProblem> problems) throws InterruptedException,
+ ConfigurationException, FileNotFoundException
+ {
+ Collection<ICompilerProblem> fatalProblems = applicationProject.getFatalProblems();
+ if (!fatalProblems.isEmpty())
+ {
+ problems.addAll(fatalProblems);
+ return null;
+ }
+
+ return ((JSTarget) target).build(mainCU, problems);
+ }
+
+ /**
+ * Get the output file path. If {@code -output} is specified, use its value;
+ * otherwise, use the same base name as the target file.
+ *
+ * @return output file path
+ */
+ private String getOutputFilePath()
+ {
+ if (config.getOutput() == null)
+ {
+ final String extension = "." + JSSharedData.OUTPUT_EXTENSION;
+ return FilenameUtils.removeExtension(config.getTargetFile()).concat(
+ extension);
+ }
+ else
+ return config.getOutput();
+ }
+
+ /**
+ * @author Erik de Bruin
+ *
+ * Get the output class file. This includes the (sub)directory in
+ * which the original class file lives. If the directory structure
+ * doesn't exist, it is created.
+ *
+ * @param qname
+ * @param outputFolder
+ * @return output class file path
+ */
+ private File getOutputClassFile(String qname, File outputFolder)
+ {
+ String[] cname = qname.split("\\.");
+ String sdirPath = outputFolder + File.separator;
+ if (cname.length > 0)
+ {
+ for (int i = 0, n = cname.length - 1; i < n; i++)
+ {
+ sdirPath += cname[i] + File.separator;
+ }
+
+ File sdir = new File(sdirPath);
+ if (!sdir.exists())
+ sdir.mkdirs();
+
+ qname = cname[cname.length - 1];
+ }
+
+ return new File(sdirPath + qname + "." + JSSharedData.OUTPUT_EXTENSION);
+ }
+
+ /**
+ * @param qname
+ * @param outputFolder
+ * @return output source map file path
+ */
+ private File getOutputSourceMapFile(String qname, File outputFolder)
+ {
+ String[] cname = qname.split("\\.");
+ String sdirPath = outputFolder + File.separator;
+ if (cname.length > 0)
+ {
+ for (int i = 0, n = cname.length - 1; i < n; i++)
+ {
+ sdirPath += cname[i] + File.separator;
+ }
+
+ File sdir = new File(sdirPath);
+ if (!sdir.exists())
+ sdir.mkdirs();
+
+ qname = cname[cname.length - 1];
+ }
+
+ return new File(sdirPath + qname + "." + JSSharedData.OUTPUT_EXTENSION + ".map");
+ }
+
+ /**
+ * Mxmlc uses target file as the main compilation unit and derive the output
+ * SWF file name from this file.
+ *
+ * @return true if successful, false otherwise.
+ * @throws OnlyOneSource
+ * @throws InterruptedException
+ */
+ protected boolean setupTargetFile() throws InterruptedException
+ {
+ final String mainFileName = config.getTargetFile();
+
+ final String normalizedMainFileName = FilenameNormalization.normalize(mainFileName);
+
+ final SourceCompilationUnitFactory compilationUnitFactory = project.getSourceCompilationUnitFactory();
+
+ File normalizedMainFile = new File(normalizedMainFileName);
+ if (compilationUnitFactory.canCreateCompilationUnit(normalizedMainFile))
+ {
+ project.addIncludeSourceFile(normalizedMainFile);
+
+ final List<String> sourcePath = config.getCompilerSourcePath();
+ String mainQName = null;
+ if (sourcePath != null && !sourcePath.isEmpty())
+ {
+ for (String path : sourcePath)
+ {
+ final String otherPath = new File(path).getAbsolutePath();
+ if (mainFileName.startsWith(otherPath))
+ {
+ mainQName = mainFileName.substring(otherPath.length() + 1);
+ mainQName = mainQName.replaceAll("\\\\", "/");
+ mainQName = mainQName.replaceAll("\\/", ".");
+ if (mainQName.endsWith(".as"))
+ mainQName = mainQName.substring(0,
+ mainQName.length() - 3);
+ break;
+ }
+ }
+ }
+
+ if (mainQName == null)
+ mainQName = FilenameUtils.getBaseName(mainFileName);
+
+ Collection<ICompilationUnit> mainFileCompilationUnits = workspace.getCompilationUnits(
+ normalizedMainFileName, project);
+
+ mainCU = Iterables.getOnlyElement(mainFileCompilationUnits);
+
+ config.setMainDefinition(mainQName);
+ }
+
+ Preconditions.checkNotNull(mainCU,
+ "Main compilation unit can't be null");
+
+ ITargetSettings settings = getTargetSettings();
+ if (settings != null)
+ project.setTargetSettings(settings);
+
+ target = JSSharedData.backend.createTarget(project,
+ getTargetSettings(), null);
+
+ return true;
+ }
+
+ private ITargetSettings getTargetSettings()
+ {
+ if (targetSettings == null)
+ targetSettings = projectConfigurator.getTargetSettings(null);
+
+ return targetSettings;
+ }
+
+ /**
+ * Create a new Configurator. This method may be overridden to allow
+ * Configurator subclasses to be created that have custom configurations.
+ *
+ * @return a new instance or subclass of {@link Configurator}.
+ */
+ protected Configurator createConfigurator()
+ {
+ return JSSharedData.backend.createConfigurator();
+ }
+
+ /**
+ * Load configurations from all the sources.
+ *
+ * @param args command line arguments
+ * @return True if mxmlc should continue with compilation.
+ */
+ protected boolean configure(final String[] args)
+ {
+ project.getSourceCompilationUnitFactory().addHandler(asFileHandler);
+ projectConfigurator = createConfigurator();
+
+ try
+ {
+ if (useFlashBuilderProjectFiles(args)
+ && !jsOutputType.equals(JSOutputType.VF2JS))
+ {
+ projectConfigurator.setConfiguration(
+ FlashBuilderConfigurator.computeFlashBuilderArgs(args,
+ getTargetType().getExtension()),
+ ICompilerSettingsConstants.FILE_SPECS_VAR);
+ }
+ else
+ {
+ projectConfigurator.setConfiguration(args,
+ ICompilerSettingsConstants.FILE_SPECS_VAR);
+ }
+
+ projectConfigurator.applyToProject(project);
+ problems = new ProblemQuery(
+ projectConfigurator.getCompilerProblemSettings());
+
+ project.config = (JSGoogConfiguration)projectConfigurator.getConfiguration();
+ config = projectConfigurator.getConfiguration();
+ configBuffer = projectConfigurator.getConfigurationBuffer();
+ problems.addAll(projectConfigurator.getConfigurationProblems());
+
+ if (configBuffer.getVar("version") != null) //$NON-NLS-1$
+ return false;
+
+ if (problems.hasErrors())
+ return false;
+
+ validateTargetFile();
+ return true;
+ }
+ catch (ConfigurationException e)
+ {
+ final ICompilerProblem problem = new ConfigurationProblem(e);
+ problems.add(problem);
+ return false;
+ }
+ catch (Exception e)
+ {
+ final ICompilerProblem problem = new ConfigurationProblem(null, -1,
+ -1, -1, -1, e.getMessage());
+ problems.add(problem);
+ return false;
+ }
+ finally
+ {
+ if (config == null)
+ {
+ config = new Configuration();
+ configBuffer = new ConfigurationBuffer(Configuration.class,
+ Configuration.getAliases());
+ }
+ }
+ }
+
+ private boolean useFlashBuilderProjectFiles(String[] args)
+ {
+ for (String arg : args)
+ {
+ if (arg.equals("-fb")
+ || arg.equals("-use-flashbuilder-project-files"))
+ return true;
+ }
+ return false;
+ }
+
+ protected TargetType getTargetType()
+ {
+ return TargetType.SWF;
+ }
+
+ /**
+ * Validate target file.
+ *
+ * @throws MustSpecifyTarget
+ * @throws IOError
+ */
+ protected void validateTargetFile() throws ConfigurationException
+ {
+ if (mainCU instanceof ResourceModuleCompilationUnit)
+ return; //when compiling a Resource Module, no target file is defined.
+
+ final String targetFile = config.getTargetFile();
+ if (targetFile == null)
+ throw new ConfigurationException.MustSpecifyTarget(null, null, -1);
+
+ final File file = new File(targetFile);
+ if (!file.exists())
+ throw new ConfigurationException.IOError(targetFile);
+ }
+
+ /**
+ * Wait till the workspace to finish compilation and close.
+ */
+ protected void waitAndClose()
+ {
+ workspace.startIdleState();
+ try
+ {
+ workspace.close();
+ }
+ finally
+ {
+ workspace.endIdleState(Collections.<ICompilerProject, Set<ICompilationUnit>> emptyMap());
+ }
+ }
+
+ /**
+ * Force terminate the compilation process.
+ */
+ protected void close()
+ {
+ workspace.close();
+ }
+}
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/de070636/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/JSSessionModel.java
----------------------------------------------------------------------
diff --cc compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/JSSessionModel.java
index 5c45227,0000000..acd8232
mode 100644,000000..100644
--- a/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/JSSessionModel.java
+++ b/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/JSSessionModel.java
@@@ -1,180 -1,0 +1,182 @@@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+package org.apache.flex.compiler.internal.codegen.js;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.LinkedHashMap;
+import java.util.List;
+import java.util.Stack;
+
+import org.apache.flex.compiler.definitions.IClassDefinition;
+import org.apache.flex.compiler.tree.as.IFunctionNode;
+import org.apache.flex.compiler.tree.as.IGetterNode;
+import org.apache.flex.compiler.tree.as.ISetterNode;
+import org.apache.flex.compiler.tree.as.IVariableNode;
+
+/**
+ * @author Michael Schmalle
+ */
+public class JSSessionModel
+{
+ public static final String CONSTRUCTOR_EMPTY = "emptyConstructor";
+ public static final String CONSTRUCTOR_FULL = "fullConstructor";
+ public static final String SUPER_FUNCTION_CALL = "replaceSuperFunction";
+
+ private IClassDefinition currentClass;
+
+ public static class PropertyNodes
+ {
+ public IGetterNode getter;
+ public ISetterNode setter;
+ }
+
+ private static class Context
+ {
+ public LinkedHashMap<String, PropertyNodes> propertyMap;
+ public List<String> interfacePropertyMap;
+ public LinkedHashMap<String, PropertyNodes> staticPropertyMap;
+ public ArrayList<String> bindableVars;
+ public ArrayList<IVariableNode> vars;
+ public ArrayList<IFunctionNode> methods;
+ public IClassDefinition classDefinition;
+ }
+ private Stack<Context> stack = new Stack<Context>();
+
++ public boolean inE4xFilter = false;
++
+ private LinkedHashMap<String, PropertyNodes> propertyMap = new LinkedHashMap<String, PropertyNodes>();
+
+ private List<String> interfacePropertyMap = new ArrayList<String>();
+
+ private LinkedHashMap<String, PropertyNodes> staticPropertyMap = new LinkedHashMap<String, PropertyNodes>();
+
+ private ArrayList<String> bindableVars = new ArrayList<String>();
+
+ private ArrayList<IVariableNode> vars = new ArrayList<IVariableNode>();
+
+ private ArrayList<IFunctionNode> methods = new ArrayList<IFunctionNode>();
+
+ private HashMap<String, String> internalClasses;
+
+ private int foreachLoopCount = 0;
+
+ public IClassDefinition getCurrentClass()
+ {
+ return currentClass;
+ }
+
+ public void setCurrentClass(IClassDefinition currentClass)
+ {
+ this.currentClass = currentClass;
+ }
+
+ public void pushClass(IClassDefinition currentClass)
+ {
+ Context context = new Context();
+ context.bindableVars = bindableVars;
+ context.interfacePropertyMap = interfacePropertyMap;
+ context.propertyMap = propertyMap;
+ context.staticPropertyMap = staticPropertyMap;
+ context.classDefinition = this.currentClass;
+ context.vars = vars;
+ context.methods = methods;
+ stack.push(context);
+ this.currentClass = currentClass;
+ bindableVars = new ArrayList<String>();
+ staticPropertyMap = new LinkedHashMap<String, PropertyNodes>();
+ interfacePropertyMap = new ArrayList<String>();
+ propertyMap = new LinkedHashMap<String, PropertyNodes>();
+ vars = new ArrayList<IVariableNode>();
+ methods = new ArrayList<IFunctionNode>();
+ }
+
+ public void popClass()
+ {
+ Context context = stack.pop();
+ this.currentClass = context.classDefinition;
+ bindableVars = context.bindableVars;
+ staticPropertyMap = context.staticPropertyMap;
+ propertyMap = context.propertyMap;
+ interfacePropertyMap = context.interfacePropertyMap;
+ vars = context.vars;
+ methods = context.methods;
+ }
+
+ public HashMap<String, PropertyNodes> getPropertyMap()
+ {
+ return propertyMap;
+ }
+
+ public List<String> getInterfacePropertyMap()
+ {
+ return interfacePropertyMap;
+ }
+
+ public HashMap<String, PropertyNodes> getStaticPropertyMap()
+ {
+ return staticPropertyMap;
+ }
+
+ public boolean hasBindableVars()
+ {
+ return bindableVars.size() > 0;
+ }
+
+ public List<String> getBindableVars()
+ {
+ return bindableVars;
+ }
+
+ public List<IVariableNode> getVars()
+ {
+ return vars;
+ }
+
+ public List<IFunctionNode> getMethods()
+ {
+ return methods;
+ }
+
+ public HashMap<String, String> getInternalClasses()
+ {
+ if (internalClasses == null)
+ internalClasses = new HashMap<String, String>();
+ return internalClasses;
+ }
+
+ public boolean isInternalClass(String className)
+ {
+ if (internalClasses == null) return false;
+
+ return internalClasses.containsKey(className);
+ }
+
+ public final void incForeachLoopCount()
+ {
+ foreachLoopCount++;
+ }
+
+ public String getCurrentForeachName()
+ {
+ return "foreachiter" + Integer.toString(foreachLoopCount);
+ }
+
+}
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/de070636/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java
----------------------------------------------------------------------
diff --cc compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java
index cde30e8,0000000..c954e2c
mode 100644,000000..100644
--- a/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java
+++ b/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java
@@@ -1,1009 -1,0 +1,1021 @@@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+package org.apache.flex.compiler.internal.codegen.js.flexjs;
+
+import java.io.FilterWriter;
+import java.util.ArrayList;
+import java.util.List;
+
+import org.apache.flex.compiler.codegen.js.flexjs.IJSFlexJSEmitter;
+import org.apache.flex.compiler.codegen.js.goog.IJSGoogDocEmitter;
+import org.apache.flex.compiler.constants.IASLanguageConstants;
+import org.apache.flex.compiler.definitions.IClassDefinition;
+import org.apache.flex.compiler.definitions.IDefinition;
+import org.apache.flex.compiler.definitions.IPackageDefinition;
+import org.apache.flex.compiler.definitions.ITypeDefinition;
+import org.apache.flex.compiler.internal.codegen.as.ASEmitterTokens;
+import org.apache.flex.compiler.internal.codegen.js.goog.JSGoogEmitter;
+import org.apache.flex.compiler.internal.codegen.js.goog.JSGoogEmitterTokens;
+import org.apache.flex.compiler.internal.codegen.js.jx.AccessorEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.AsIsEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.BinaryOperatorEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.BindableEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.ClassEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.DefinePropertyFunctionEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.FieldEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.ForEachEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.FunctionCallEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.IdentifierEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.InterfaceEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.LiteralEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.MemberAccessEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.MethodEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.ObjectDefinePropertyEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.PackageFooterEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.PackageHeaderEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.SelfReferenceEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.SuperCallEmitter;
+import org.apache.flex.compiler.internal.codegen.js.jx.VarDeclarationEmitter;
+import org.apache.flex.compiler.internal.codegen.js.utils.EmitterUtils;
+import org.apache.flex.compiler.internal.codegen.mxml.flexjs.MXMLFlexJSEmitter;
+import org.apache.flex.compiler.internal.definitions.AccessorDefinition;
+import org.apache.flex.compiler.internal.projects.FlexJSProject;
+import org.apache.flex.compiler.internal.projects.FlexProject;
+import org.apache.flex.compiler.internal.tree.as.BinaryOperatorAsNode;
+import org.apache.flex.compiler.internal.tree.as.BlockNode;
+import org.apache.flex.compiler.internal.tree.as.DynamicAccessNode;
+import org.apache.flex.compiler.internal.tree.as.FunctionCallNode;
+import org.apache.flex.compiler.internal.tree.as.IdentifierNode;
+import org.apache.flex.compiler.internal.tree.as.LabeledStatementNode;
+import org.apache.flex.compiler.internal.tree.as.MemberAccessExpressionNode;
+import org.apache.flex.compiler.internal.tree.as.NumericLiteralNode;
+import org.apache.flex.compiler.projects.ICompilerProject;
+import org.apache.flex.compiler.tree.ASTNodeID;
+import org.apache.flex.compiler.tree.as.IASNode;
+import org.apache.flex.compiler.tree.as.IAccessorNode;
+import org.apache.flex.compiler.tree.as.IBinaryOperatorNode;
+import org.apache.flex.compiler.tree.as.IClassNode;
+import org.apache.flex.compiler.tree.as.IContainerNode;
+import org.apache.flex.compiler.tree.as.IDefinitionNode;
+import org.apache.flex.compiler.tree.as.IExpressionNode;
+import org.apache.flex.compiler.tree.as.IFileNode;
+import org.apache.flex.compiler.tree.as.IForLoopNode;
+import org.apache.flex.compiler.tree.as.IFunctionCallNode;
+import org.apache.flex.compiler.tree.as.IFunctionNode;
+import org.apache.flex.compiler.tree.as.IFunctionObjectNode;
+import org.apache.flex.compiler.tree.as.IGetterNode;
+import org.apache.flex.compiler.tree.as.IIdentifierNode;
+import org.apache.flex.compiler.tree.as.IInterfaceNode;
+import org.apache.flex.compiler.tree.as.ILiteralNode;
+import org.apache.flex.compiler.tree.as.IMemberAccessExpressionNode;
+import org.apache.flex.compiler.tree.as.INamespaceNode;
+import org.apache.flex.compiler.tree.as.IPackageNode;
+import org.apache.flex.compiler.tree.as.IScopedNode;
+import org.apache.flex.compiler.tree.as.ISetterNode;
+import org.apache.flex.compiler.tree.as.IUnaryOperatorNode;
+import org.apache.flex.compiler.tree.as.IVariableNode;
+import org.apache.flex.compiler.utils.ASNodeUtils;
+
+import com.google.common.base.Joiner;
+
+/**
+ * Concrete implementation of the 'FlexJS' JavaScript production.
+ *
+ * @author Michael Schmalle
+ * @author Erik de Bruin
+ */
+public class JSFlexJSEmitter extends JSGoogEmitter implements IJSFlexJSEmitter
+{
+
+ private JSFlexJSDocEmitter docEmitter = null;
+
+ private PackageHeaderEmitter packageHeaderEmitter;
+ public PackageFooterEmitter packageFooterEmitter;
+
+ private BindableEmitter bindableEmitter;
+
+ private ClassEmitter classEmitter;
+ private InterfaceEmitter interfaceEmitter;
+
+ private FieldEmitter fieldEmitter;
+ public VarDeclarationEmitter varDeclarationEmitter;
+ public AccessorEmitter accessorEmitter;
+ public MethodEmitter methodEmitter;
+
+ private FunctionCallEmitter functionCallEmitter;
+ private SuperCallEmitter superCallEmitter;
+ private ForEachEmitter forEachEmitter;
+ private MemberAccessEmitter memberAccessEmitter;
+ private BinaryOperatorEmitter binaryOperatorEmitter;
+ private IdentifierEmitter identifierEmitter;
+ private LiteralEmitter literalEmitter;
+
+ private AsIsEmitter asIsEmitter;
+ private SelfReferenceEmitter selfReferenceEmitter;
+ private ObjectDefinePropertyEmitter objectDefinePropertyEmitter;
+ private DefinePropertyFunctionEmitter definePropertyFunctionEmitter;
+
+ public ArrayList<String> usedNames = new ArrayList<String>();
+
+ @Override
+ public String postProcess(String output)
+ {
+ output = super.postProcess(output);
+
+ String[] lines = output.split("\n");
+ ArrayList<String> finalLines = new ArrayList<String>();
+ boolean foundLanguage = false;
+ boolean foundXML = false;
+ boolean sawRequires = false;
+ boolean stillSearching = true;
+ int addIndex = -1;
+ int len = lines.length;
+ for (int i = 0; i < len; i++)
+ {
+ String line = lines[i];
+ if (stillSearching)
+ {
+ int c = line.indexOf(JSGoogEmitterTokens.GOOG_PROVIDE.getToken());
+ if (c != -1)
+ {
+ // if zero requires are found, require Language after the
+ // call to goog.provide
+ addIndex = i + 1;
+ }
+ c = line.indexOf(JSGoogEmitterTokens.GOOG_REQUIRE.getToken());
+ if (c != -1)
+ {
+ // we found other requires, so we'll just add Language at
+ // the end of the list
+ addIndex = -1;
+ int c2 = line.indexOf(")");
+ String s = line.substring(c + 14, c2 - 1);
+ if (s.equals(JSFlexJSEmitterTokens.LANGUAGE_QNAME.getToken()))
+ {
+ foundLanguage = true;
+ }
+ else if (s.equals(IASLanguageConstants.XML))
+ {
+ foundXML = true;
+ }
+ sawRequires = true;
+ if (!usedNames.contains(s))
+ {
+ removeLineFromMappings(i);
+ continue;
+ }
+ }
+ else if (sawRequires || i == len - 1)
+ {
+ stillSearching = false;
+
+ //when we emitted the requires based on the imports, we may
+ //not have known if Language was needed yet because the
+ //imports are at the beginning of the file. other code,
+ //later in the file, may require Language.
+ ICompilerProject project = getWalker().getProject();
+ if (project instanceof FlexJSProject)
+ {
+ FlexJSProject flexJSProject = (FlexJSProject) project;
+ boolean needLanguage = flexJSProject.needLanguage;
+ if (needLanguage && !foundLanguage)
+ {
+ StringBuilder appendString = new StringBuilder();
+ appendString.append(JSGoogEmitterTokens.GOOG_REQUIRE.getToken());
+ appendString.append(ASEmitterTokens.PAREN_OPEN.getToken());
+ appendString.append(ASEmitterTokens.SINGLE_QUOTE.getToken());
+ appendString.append(JSFlexJSEmitterTokens.LANGUAGE_QNAME.getToken());
+ appendString.append(ASEmitterTokens.SINGLE_QUOTE.getToken());
+ appendString.append(ASEmitterTokens.PAREN_CLOSE.getToken());
+ appendString.append(ASEmitterTokens.SEMICOLON.getToken());
+ if(addIndex != -1)
+ {
+ // if we didn't find other requires, this index
+ // points to the line after goog.provide
+ finalLines.add(addIndex, appendString.toString());
+ addLineToMappings(addIndex);
+ }
+ else
+ {
+ finalLines.add(appendString.toString());
+ addLineToMappings(i);
+ }
+ }
+ boolean needXML = flexJSProject.needXML;
+ if (needXML && !foundXML)
+ {
+ StringBuilder appendString = new StringBuilder();
+ appendString.append(JSGoogEmitterTokens.GOOG_REQUIRE.getToken());
+ appendString.append(ASEmitterTokens.PAREN_OPEN.getToken());
+ appendString.append(ASEmitterTokens.SINGLE_QUOTE.getToken());
+ appendString.append(IASLanguageConstants.XML);
+ appendString.append(ASEmitterTokens.SINGLE_QUOTE.getToken());
+ appendString.append(ASEmitterTokens.PAREN_CLOSE.getToken());
+ appendString.append(ASEmitterTokens.SEMICOLON.getToken());
+ if(addIndex != -1)
+ {
+ // if we didn't find other requires, this index
+ // points to the line after goog.provide
+ finalLines.add(addIndex, appendString.toString());
+ addLineToMappings(addIndex);
+ }
+ else
+ {
+ finalLines.add(appendString.toString());
+ addLineToMappings(i);
+ }
+ }
+ }
+ }
+ }
+ finalLines.add(line);
+ }
+
+ return Joiner.on("\n").join(finalLines);
+ }
+
+ public BindableEmitter getBindableEmitter()
+ {
+ return bindableEmitter;
+ }
+
+ public ClassEmitter getClassEmiter()
+ {
+ return classEmitter;
+ }
+
+ public AccessorEmitter getAccessorEmitter()
+ {
+ return accessorEmitter;
+ }
+
+ public PackageFooterEmitter getPackageFooterEmitter()
+ {
+ return packageFooterEmitter;
+ }
+
+ // TODO (mschmalle) Fix; this is not using the backend doc strategy for replacement
+ @Override
+ public IJSGoogDocEmitter getDocEmitter()
+ {
+ if (docEmitter == null)
+ docEmitter = new JSFlexJSDocEmitter(this);
+ return docEmitter;
+ }
+
+ public JSFlexJSEmitter(FilterWriter out)
+ {
+ super(out);
+
+ packageHeaderEmitter = new PackageHeaderEmitter(this);
+ packageFooterEmitter = new PackageFooterEmitter(this);
+
+ bindableEmitter = new BindableEmitter(this);
+
+ classEmitter = new ClassEmitter(this);
+ interfaceEmitter = new InterfaceEmitter(this);
+
+ fieldEmitter = new FieldEmitter(this);
+ varDeclarationEmitter = new VarDeclarationEmitter(this);
+ accessorEmitter = new AccessorEmitter(this);
+ methodEmitter = new MethodEmitter(this);
+
+ functionCallEmitter = new FunctionCallEmitter(this);
+ superCallEmitter = new SuperCallEmitter(this);
+ forEachEmitter = new ForEachEmitter(this);
+ memberAccessEmitter = new MemberAccessEmitter(this);
+ binaryOperatorEmitter = new BinaryOperatorEmitter(this);
+ identifierEmitter = new IdentifierEmitter(this);
+ literalEmitter = new LiteralEmitter(this);
+
+ asIsEmitter = new AsIsEmitter(this);
+ selfReferenceEmitter = new SelfReferenceEmitter(this);
+ objectDefinePropertyEmitter = new ObjectDefinePropertyEmitter(this);
+ definePropertyFunctionEmitter = new DefinePropertyFunctionEmitter(this);
+
+ }
+
+ @Override
+ protected void writeIndent()
+ {
+ write(JSFlexJSEmitterTokens.INDENT);
+ }
+
+ @Override
+ protected String getIndent(int numIndent)
+ {
+ final StringBuilder sb = new StringBuilder();
+ for (int i = 0; i < numIndent; i++)
+ sb.append(JSFlexJSEmitterTokens.INDENT.getToken());
+ return sb.toString();
+ }
+
+ @Override
+ public void emitLocalNamedFunction(IFunctionNode node)
+ {
+ IFunctionNode fnNode = (IFunctionNode)node.getAncestorOfType(IFunctionNode.class);
+ if (fnNode.getEmittingLocalFunctions())
+ {
+ super.emitLocalNamedFunction(node);
+ }
+ }
+
+ @Override
+ public void emitFunctionBlockHeader(IFunctionNode node)
+ {
+ node.setEmittingLocalFunctions(true);
+ super.emitFunctionBlockHeader(node);
+ if (node.isConstructor())
+ {
+ IClassNode cnode = (IClassNode) node
+ .getAncestorOfType(IClassNode.class);
+ emitComplexInitializers(cnode);
+ }
+ if (node.containsLocalFunctions())
+ {
+ List<IFunctionNode> anonFns = node.getLocalFunctions();
+ int n = anonFns.size();
+ for (int i = 0; i < n; i++)
+ {
+ IFunctionNode anonFn = anonFns.get(i);
+ if (anonFn.getParent().getNodeID() == ASTNodeID.AnonymousFunctionID)
+ {
+ write("var /** @type {Function} */ __localFn" + Integer.toString(i) + "__ = ");
+ getWalker().walk(anonFn.getParent());
+ }
+ else
+ {
+ getWalker().walk(anonFn);
+ write(ASEmitterTokens.SEMICOLON);
+ }
+ this.writeNewline();
+ }
+ }
+ node.setEmittingLocalFunctions(false);
+ }
+
+ @Override
+ public void emitFunctionObject(IFunctionObjectNode node)
+ {
+ IFunctionNode fnNode = (IFunctionNode)node.getAncestorOfType(IFunctionNode.class);
+ if (fnNode == null || fnNode.getEmittingLocalFunctions())
+ {
+ super.emitFunctionObject(node);
+ }
+ else
+ {
+ List<IFunctionNode> anonFns = fnNode.getLocalFunctions();
+ int i = anonFns.indexOf(node.getFunctionNode());
+ if (i < 0)
+ System.out.println("missing index for " + node.toString());
+ else
+ write("__localFn" + Integer.toString(i) + "__");
+ }
+ }
+
+ @Override
+ public void emitNamespace(INamespaceNode node)
+ {
+ write(formatQualifiedName(node.getName()));
+ write(ASEmitterTokens.SPACE);
+ writeToken(ASEmitterTokens.EQUAL);
+ writeToken(ASEmitterTokens.NEW);
+ write(IASLanguageConstants.Namespace);
+ write(ASEmitterTokens.PAREN_OPEN);
+ getWalker().walk(node.getNamespaceURINode());
+ write(ASEmitterTokens.PAREN_CLOSE);
+ write(ASEmitterTokens.SEMICOLON);
+ }
+
+ @Override
+ public void emitMemberName(IDefinitionNode node)
+ {
+ write(node.getName());
+ }
+
+ @Override
+ public String formatQualifiedName(String name)
+ {
+ return formatQualifiedName(name, false);
+ }
+
+ public MXMLFlexJSEmitter mxmlEmitter = null;
+
+ public String formatQualifiedName(String name, boolean isDoc)
+ {
+ if (mxmlEmitter != null)
+ name = mxmlEmitter.formatQualifiedName(name);
+ /*
+ if (name.contains("goog.") || name.startsWith("Vector."))
+ return name;
+ name = name.replaceAll("\\.", "_");
+ */
+ if (getModel().isInternalClass(name))
+ return getModel().getInternalClasses().get(name);
+ if (name.startsWith("window."))
+ name = name.substring(7);
+ else if (!isDoc)
+ {
+ if (!usedNames.contains(name))
+ usedNames.add(name);
+ }
+ return name;
+ }
+
+ //--------------------------------------------------------------------------
+ // Package Level
+ //--------------------------------------------------------------------------
+
+ @Override
+ public void emitPackageHeader(IPackageDefinition definition)
+ {
+ IPackageNode packageNode = definition.getNode();
+ IFileNode fileNode = (IFileNode) packageNode.getAncestorOfType(IFileNode.class);
+ int nodeCount = fileNode.getChildCount();
+ String mainClassName = null;
+ for (int i = 0; i < nodeCount; i++)
+ {
+ IASNode pnode = fileNode.getChild(i);
+
+ if (pnode instanceof IPackageNode)
+ {
+ IScopedNode snode = ((IPackageNode)pnode).getScopedNode();
+ int snodeCount = snode.getChildCount();
+ for (int j = 0; j < snodeCount; j++)
+ {
+ IASNode cnode = snode.getChild(j);
+ if (cnode instanceof IClassNode)
+ {
+ mainClassName = ((IClassNode)cnode).getQualifiedName();
+ break;
+ }
+ }
+ }
+ else if (pnode instanceof IClassNode)
+ {
+ String className = ((IClassNode)pnode).getQualifiedName();
+ getModel().getInternalClasses().put(className, mainClassName + "." + className);
+ }
+ else if (pnode instanceof IInterfaceNode)
+ {
+ String className = ((IInterfaceNode)pnode).getQualifiedName();
+ getModel().getInternalClasses().put(className, mainClassName + "." + className);
+ }
+ else if (pnode instanceof IFunctionNode)
+ {
+ String className = ((IFunctionNode)pnode).getQualifiedName();
+ getModel().getInternalClasses().put(className, mainClassName + "." + className);
+ }
+ else if (pnode instanceof INamespaceNode)
+ {
+ String className = ((INamespaceNode)pnode).getQualifiedName();
+ getModel().getInternalClasses().put(className, mainClassName + "." + className);
+ }
+ else if (pnode instanceof IVariableNode)
+ {
+ String className = ((IVariableNode)pnode).getQualifiedName();
+ getModel().getInternalClasses().put(className, mainClassName + "." + className);
+ }
+ }
+
+ packageHeaderEmitter.emit(definition);
+ }
+
+ @Override
+ public void emitPackageHeaderContents(IPackageDefinition definition)
+ {
+ packageHeaderEmitter.emitContents(definition);
+ usedNames.clear();
+ }
+
+ @Override
+ public void emitPackageFooter(IPackageDefinition definition)
+ {
+ packageFooterEmitter.emit(definition);
+ }
+
+ //--------------------------------------------------------------------------
+ // Class
+ //--------------------------------------------------------------------------
+
+ @Override
+ public void emitClass(IClassNode node)
+ {
+ classEmitter.emit(node);
+ }
+
+ @Override
+ public void emitInterface(IInterfaceNode node)
+ {
+ interfaceEmitter.emit(node);
+ }
+
+ @Override
+ public void emitField(IVariableNode node)
+ {
+ fieldEmitter.emit(node);
+ }
+
+ @Override
+ public void emitVarDeclaration(IVariableNode node)
+ {
+ varDeclarationEmitter.emit(node);
+ }
+
+ @Override
+ public void emitAccessors(IAccessorNode node)
+ {
+ accessorEmitter.emit(node);
+ }
+
+ @Override
+ public void emitGetAccessor(IGetterNode node)
+ {
+ accessorEmitter.emitGet(node);
+ }
+
+ @Override
+ public void emitSetAccessor(ISetterNode node)
+ {
+ accessorEmitter.emitSet(node);
+ }
+
+ @Override
+ public void emitMethod(IFunctionNode node)
+ {
+ methodEmitter.emit(node);
+ }
+
+ public void emitComplexInitializers(IClassNode node)
+ {
+ classEmitter.emitComplexInitializers(node);
+ }
+
+ //--------------------------------------------------------------------------
+ // Statements
+ //--------------------------------------------------------------------------
+
+ @Override
+ public void emitFunctionCall(IFunctionCallNode node)
+ {
+ functionCallEmitter.emit(node);
+ }
+
+ @Override
+ public void emitForEachLoop(IForLoopNode node)
+ {
+ forEachEmitter.emit(node);
+ }
+
+ //--------------------------------------------------------------------------
+ // Expressions
+ //--------------------------------------------------------------------------
+
+ @Override
+ public void emitSuperCall(IASNode node, String type)
+ {
+ superCallEmitter.emit(node, type);
+ }
+
+ @Override
+ public void emitMemberAccessExpression(IMemberAccessExpressionNode node)
+ {
+ memberAccessEmitter.emit(node);
+ }
+
+ @Override
+ public void emitArguments(IContainerNode node)
+ {
+ IContainerNode newNode = node;
+ int len = node.getChildCount();
+ if (len == 2)
+ {
+ ICompilerProject project = getWalker().getProject();;
+ IFunctionCallNode fcNode = (IFunctionCallNode) node.getParent();
+ IExpressionNode nameNode = fcNode.getNameNode();
+ IDefinition def = nameNode.resolve(project);
+ if (def != null && def.getBaseName().equals("insertAt"))
+ {
+ if (def.getParent() != null &&
+ def.getParent().getQualifiedName().equals("Array"))
+ {
+ if (nameNode instanceof MemberAccessExpressionNode)
+ {
+ newNode = EmitterUtils.insertArgumentsAt(node, 1, new NumericLiteralNode("0"));
+ }
+ }
+ }
+ }
+ if (len == 1)
+ {
+ ICompilerProject project = getWalker().getProject();;
+ IFunctionCallNode fcNode = (IFunctionCallNode) node.getParent();
+ IExpressionNode nameNode = fcNode.getNameNode();
+ IDefinition def = nameNode.resolve(project);
+ if (def != null && def.getBaseName().equals("removeAt"))
+ {
+ if (def.getParent() != null &&
+ def.getParent().getQualifiedName().equals("Array"))
+ {
+ if (nameNode instanceof MemberAccessExpressionNode)
+ {
+ newNode = EmitterUtils.insertArgumentsAfter(node, new NumericLiteralNode("1"));
+ }
+ }
+ }
+ else if (def != null && def.getBaseName().equals("parseInt"))
+ {
+ IDefinition parentDef = def.getParent();
+ if (parentDef == null)
+ {
+ if (nameNode instanceof IdentifierNode)
+ {
+ newNode = EmitterUtils.insertArgumentsAfter(node, new NumericLiteralNode("10"));
+ }
+ }
+ }
+ }
+ super.emitArguments(newNode);
+ }
+
+ @Override
+ public void emitE4XFilter(IMemberAccessExpressionNode node)
+ {
++ getModel().inE4xFilter = true;
+ getWalker().walk(node.getLeftOperandNode());
+ write(".filter(function(node){return (node.");
+ String s = stringifyNode(node.getRightOperandNode());
+ if (s.startsWith("(") && s.endsWith(")"))
+ s = s.substring(1, s.length() - 1);
+ write(s);
+ write(")})");
++ getModel().inE4xFilter = false;
+ }
+
+ @Override
+ public void emitBinaryOperator(IBinaryOperatorNode node)
+ {
+ binaryOperatorEmitter.emit(node);
+ }
+
+ @Override
+ public void emitIdentifier(IIdentifierNode node)
+ {
+ identifierEmitter.emit(node);
+ }
+
+ @Override
+ public void emitLiteral(ILiteralNode node)
+ {
+ literalEmitter.emit(node);
+ }
+
+ //--------------------------------------------------------------------------
+ // Specific
+ //--------------------------------------------------------------------------
+
+ public void emitIsAs(IExpressionNode node, IExpressionNode left, IExpressionNode right, ASTNodeID id, boolean coercion)
+ {
+ asIsEmitter.emitIsAs(node, left, right, id, coercion);
+ }
+
+ @Override
+ protected void emitSelfReference(IFunctionNode node)
+ {
+ selfReferenceEmitter.emit(node);
+ }
+
+ @Override
+ protected void emitObjectDefineProperty(IAccessorNode node)
+ {
+ objectDefinePropertyEmitter.emit(node);
+ }
+
+ @Override
+ public void emitDefinePropertyFunction(IAccessorNode node)
+ {
+ definePropertyFunctionEmitter.emit(node);
+ }
+
+ public String stringifyDefineProperties(IClassDefinition cdef)
+ {
+ setBufferWrite(true);
+ accessorEmitter.emit(cdef);
+ String result = getBuilder().toString();
+ getBuilder().setLength(0);
+ setBufferWrite(false);
+ return result;
+ }
+
+ @Override
+ public void emitClosureStart()
+ {
+ ICompilerProject project = getWalker().getProject();;
+ if (project instanceof FlexJSProject)
+ ((FlexJSProject)project).needLanguage = true;
+ write(JSFlexJSEmitterTokens.CLOSURE_FUNCTION_NAME);
+ write(ASEmitterTokens.PAREN_OPEN);
+ }
+
+ @Override
+ public void emitClosureEnd(IASNode node)
+ {
+ write(ASEmitterTokens.COMMA);
+ write(ASEmitterTokens.SPACE);
+ write(ASEmitterTokens.SINGLE_QUOTE);
+ if (node.getNodeID() == ASTNodeID.IdentifierID)
+ write(((IIdentifierNode)node).getName());
+ else if (node.getNodeID() == ASTNodeID.MemberAccessExpressionID)
+ writeChainName(node);
+ else
+ System.out.println("unexpected node in emitClosureEnd");
+ write(ASEmitterTokens.SINGLE_QUOTE);
+ write(ASEmitterTokens.PAREN_CLOSE);
+ }
+
+ @Override
+ public void emitStatement(IASNode node)
+ {
+ // don't emit named local functions as statements
+ // they are emitted as part of the function block header
+ if (node.getNodeID() == ASTNodeID.FunctionID)
+ {
+ return;
+ }
+ super.emitStatement(node);
+ }
+ private void writeChainName(IASNode node)
+ {
+ while (node.getNodeID() == ASTNodeID.MemberAccessExpressionID)
+ {
+ node = ((IMemberAccessExpressionNode)node).getRightOperandNode();
+ }
+ if (node.getNodeID() == ASTNodeID.IdentifierID)
+ write(((IdentifierNode)node).getName());
+ else
+ System.out.println("unexpected node in emitClosureEnd");
+ }
+
+ @Override
+ public void emitUnaryOperator(IUnaryOperatorNode node)
+ {
+ if (node.getNodeID() == ASTNodeID.Op_DeleteID)
+ {
+ if (node.getChild(0).getNodeID() == ASTNodeID.ArrayIndexExpressionID)
+ {
+ if (node.getChild(0).getChild(0).getNodeID() == ASTNodeID.MemberAccessExpressionID)
+ {
+ MemberAccessExpressionNode obj = (MemberAccessExpressionNode)(node.getChild(0).getChild(0));
+ if (isXMLList(obj))
+ {
+ if (ASNodeUtils.hasParenOpen(node))
+ write(ASEmitterTokens.PAREN_OPEN);
+
+ getWalker().walk(obj);
+ DynamicAccessNode dan = (DynamicAccessNode)(node.getChild(0));
+ IASNode indexNode = dan.getChild(1);
+ write(".removeChildAt(");
+ getWalker().walk(indexNode);
+ write(")");
+ if (ASNodeUtils.hasParenClose(node))
+ write(ASEmitterTokens.PAREN_CLOSE);
+ return;
+ }
+ }
+ else if (node.getChild(0).getChild(0).getNodeID() == ASTNodeID.IdentifierID)
+ {
+ if (isXML((IdentifierNode)(node.getChild(0).getChild(0))))
+ {
+ if (ASNodeUtils.hasParenOpen(node))
+ write(ASEmitterTokens.PAREN_OPEN);
+
+ getWalker().walk(node.getChild(0).getChild(0));
+ DynamicAccessNode dan = (DynamicAccessNode)(node.getChild(0));
+ IASNode indexNode = dan.getChild(1);
+ write(".removeChild(");
+ getWalker().walk(indexNode);
+ write(")");
+ if (ASNodeUtils.hasParenClose(node))
+ write(ASEmitterTokens.PAREN_CLOSE);
+ return;
+ }
+ else if (isProxy((IdentifierNode)(node.getChild(0).getChild(0))))
+ {
+ if (ASNodeUtils.hasParenOpen(node))
+ write(ASEmitterTokens.PAREN_OPEN);
+
+ getWalker().walk(node.getChild(0).getChild(0));
+ DynamicAccessNode dan = (DynamicAccessNode)(node.getChild(0));
+ IASNode indexNode = dan.getChild(1);
+ write(".deleteProperty(");
+ getWalker().walk(indexNode);
+ write(")");
+ if (ASNodeUtils.hasParenClose(node))
+ write(ASEmitterTokens.PAREN_CLOSE);
+ return;
+ }
+ }
+
+ }
+ else if (node.getChild(0).getNodeID() == ASTNodeID.MemberAccessExpressionID)
+ {
+ MemberAccessExpressionNode obj = (MemberAccessExpressionNode)(node.getChild(0));
+ if (isXMLList(obj))
+ {
+ if (ASNodeUtils.hasParenOpen(node))
+ write(ASEmitterTokens.PAREN_OPEN);
+
+ String s = stringifyNode(obj.getLeftOperandNode());
+ write(s);
+ write(".removeChild('");
+ s = stringifyNode(obj.getRightOperandNode());
+ write(s);
+ write("')");
+ if (ASNodeUtils.hasParenClose(node))
+ write(ASEmitterTokens.PAREN_CLOSE);
+ return;
+ }
+ }
+
+ }
+ else if (node.getNodeID() == ASTNodeID.Op_AtID)
+ {
+ write("attribute('");
+ getWalker().walk(node.getOperandNode());
+ write("')");
+ return;
+ }
+
+ super.emitUnaryOperator(node);
+
+ }
+
+ /**
+ * resolveType on an XML expression returns null
+ * (see IdentiferNode.resolveType).
+ * So, we have to walk the tree ourselves and resolve
+ * individual pieces.
+ * @param obj
+ * @return
+ */
+ public boolean isXMLList(MemberAccessExpressionNode obj)
+ {
+ IExpressionNode leftNode = obj.getLeftOperandNode();
+ IExpressionNode rightNode = obj.getRightOperandNode();
+ ASTNodeID rightID = rightNode.getNodeID();
+ if (rightID == ASTNodeID.IdentifierID)
+ {
+ IDefinition rightDef = rightNode.resolveType(getWalker().getProject());
+ if (rightDef != null)
+ return IdentifierNode.isXMLish(rightDef, getWalker().getProject());
+ }
+ ASTNodeID leftID = leftNode.getNodeID();
+ if (leftID == ASTNodeID.IdentifierID)
+ {
+ IDefinition leftDef = leftNode.resolveType(getWalker().getProject());
+ if (leftDef != null)
+ return IdentifierNode.isXMLish(leftDef, getWalker().getProject());
+ }
+ else if (leftID == ASTNodeID.MemberAccessExpressionID)
+ {
+ return isXMLList((MemberAccessExpressionNode)leftNode);
+ }
+ else if (leftID == ASTNodeID.FunctionCallID)
+ {
+ FunctionCallNode fcn = (FunctionCallNode)leftNode;
+ String fname = fcn.getFunctionName();
+ if (fname.equals("XML") || fname.equals("XMLList"))
+ return true;
+ }
+ else if (leftID == ASTNodeID.Op_AsID)
+ {
+ BinaryOperatorAsNode boan = (BinaryOperatorAsNode)leftNode;
+ String fname = ((IdentifierNode)boan.getChild(1)).getName();
+ if (fname.equals("XML") || fname.equals("XMLList"))
+ return true;
+ }
++ else if (leftID == ASTNodeID.ArrayIndexExpressionID)
++ {
++ leftNode = (IExpressionNode)(leftNode.getChild(0));
++ IDefinition leftDef = leftNode.resolveType(getWalker().getProject());
++ if (leftDef != null)
++ return IdentifierNode.isXMLish(leftDef, getWalker().getProject());
++
++ }
++ else if (leftID == ASTNodeID.E4XFilterID)
++ return true;
+ return false;
+ }
+
+ /**
+ * resolveType on an XML expression returns null
+ * (see IdentiferNode.resolveType).
+ * So, we have to walk the tree ourselves and resolve
+ * individual pieces.
+ * @param obj
+ * @return
+ */
+ public boolean isProxy(IExpressionNode obj)
+ {
+ FlexProject project = (FlexProject)getWalker().getProject();
+ // See if it is Proxy
+ ITypeDefinition leftDef = obj.resolveType(project);
+ if (leftDef == null)
+ {
+ if (obj.getNodeID() == ASTNodeID.MemberAccessExpressionID)
+ {
+ IExpressionNode leftNode = ((MemberAccessExpressionNode)obj).getLeftOperandNode();
+ leftDef = leftNode.resolveType(project);
+ if (leftDef != null && leftDef.isInstanceOf(project.getProxyBaseClass(), project))
+ return true;
+ while (leftNode.getNodeID() == ASTNodeID.MemberAccessExpressionID)
+ {
+ // walk up chain looking for a proxy
+ leftNode = ((MemberAccessExpressionNode)leftNode).getLeftOperandNode();
+ leftDef = leftNode.resolveType(project);
+ if (leftDef != null && leftDef.isInstanceOf(project.getProxyBaseClass(), project))
+ return true;
+ }
+ }
+ return false;
+ }
+ return leftDef.isInstanceOf(project.getProxyBaseClass(), project);
+ }
+
+ /**
+ * resolveType on an XML expression returns null
+ * (see IdentiferNode.resolveType).
+ * So, we have to walk the tree ourselves and resolve
+ * individual pieces.
+ * @param obj
+ * @return
+ */
+ public boolean isDateProperty(IExpressionNode obj)
+ {
+ FlexProject project = (FlexProject)getWalker().getProject();
+ if (obj.getNodeID() == ASTNodeID.MemberAccessExpressionID)
+ {
+ IDefinition leftDef;
+ IExpressionNode leftNode = ((MemberAccessExpressionNode)obj).getLeftOperandNode();
+ IExpressionNode rightNode = ((MemberAccessExpressionNode)obj).getRightOperandNode();
+ leftDef = leftNode.resolveType(project);
+ IDefinition rightDef = rightNode.resolve(project);
+ if (leftDef != null && leftDef.getQualifiedName().equals("Date") && rightDef instanceof AccessorDefinition)
+ {
+ return true;
+ }
+ }
+ return false;
+ }
+
+ /**
+ * resolveType on an XML expression returns null
+ * (see IdentiferNode.resolveType).
+ * So, we have to walk the tree ourselves and resolve
+ * individual pieces.
+ * @param obj
+ * @return
+ */
+ public boolean isXML(IExpressionNode obj)
+ {
+ // See if the left side is XML or XMLList
+ IDefinition leftDef = obj.resolveType(getWalker().getProject());
+ return IdentifierNode.isXMLish(leftDef, getWalker().getProject());
+ }
+
+ public MemberAccessExpressionNode getLastMAEInChain(MemberAccessExpressionNode node)
+ {
+ while (node.getRightOperandNode() instanceof MemberAccessExpressionNode)
+ node = (MemberAccessExpressionNode)node.getRightOperandNode();
+ return node;
+ }
+
+ @Override
+ public void emitLabelStatement(LabeledStatementNode node)
+ {
+ BlockNode innerBlock = node.getLabeledStatement();
+ if (innerBlock.getChildCount() == 1 && innerBlock.getChild(0).getNodeID() == ASTNodeID.ForEachLoopID)
+ {
+ getWalker().walk(node.getLabeledStatement());
+ return; // for each emitter will emit label in the right spot
+ }
+ super.emitLabelStatement(node);
+ }
+}
[15/18] git commit: [flex-falcon]
[refs/heads/feature/maven-migration-test] - Merge branch 'develop' of
https://git-wip-us.apache.org/repos/asf/flex-falcon into
feature/maven-migration-test
Posted by cd...@apache.org.
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/de070636/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/mxml/flexjs/MXMLFlexJSPublisher.java
----------------------------------------------------------------------
diff --cc compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/mxml/flexjs/MXMLFlexJSPublisher.java
index 5f5387c,0000000..170a24b
mode 100644,000000..100644
--- a/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/mxml/flexjs/MXMLFlexJSPublisher.java
+++ b/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/mxml/flexjs/MXMLFlexJSPublisher.java
@@@ -1,656 -1,0 +1,670 @@@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+package org.apache.flex.compiler.internal.codegen.mxml.flexjs;
+
+import java.io.BufferedReader;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.io.OutputStream;
+import java.net.URL;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Comparator;
+import java.util.List;
+import java.util.Map;
+
+import org.apache.commons.io.FileUtils;
+import org.apache.commons.io.FilenameUtils;
+import org.apache.commons.io.filefilter.DirectoryFileFilter;
+import org.apache.commons.io.filefilter.FileFileFilter;
+import org.apache.commons.io.filefilter.FileFilterUtils;
+import org.apache.commons.io.filefilter.IOFileFilter;
+import org.apache.commons.io.filefilter.RegexFileFilter;
+import org.apache.flex.compiler.clients.problems.ProblemQuery;
+import org.apache.flex.compiler.codegen.js.IJSPublisher;
+import org.apache.flex.compiler.config.Configuration;
+import org.apache.flex.compiler.css.ICSSPropertyValue;
+import org.apache.flex.compiler.internal.codegen.js.JSSharedData;
+import org.apache.flex.compiler.internal.codegen.js.goog.JSGoogEmitterTokens;
+import org.apache.flex.compiler.internal.codegen.js.goog.JSGoogPublisher;
+import org.apache.flex.compiler.internal.css.CSSArrayPropertyValue;
+import org.apache.flex.compiler.internal.css.CSSFontFace;
+import org.apache.flex.compiler.internal.css.CSSFunctionCallPropertyValue;
+import org.apache.flex.compiler.internal.driver.js.flexjs.JSCSSCompilationSession;
+import org.apache.flex.compiler.internal.driver.js.goog.JSGoogConfiguration;
+import org.apache.flex.compiler.internal.graph.GoogDepsWriter;
+import org.apache.flex.compiler.internal.projects.FlexJSProject;
+import org.apache.flex.compiler.utils.JSClosureCompilerWrapper;
+import org.apache.flex.swc.ISWC;
+import org.apache.flex.swc.ISWCFileEntry;
+
+public class MXMLFlexJSPublisher extends JSGoogPublisher implements IJSPublisher
+{
+
+ public static final String FLEXJS_OUTPUT_DIR_NAME = "bin";
+ public static final String FLEXJS_INTERMEDIATE_DIR_NAME = "js-debug";
+ public static final String FLEXJS_RELEASE_DIR_NAME = "js-release";
+
+ private static final String FLEXJS_EXTERNS = "externs";
+
+ class DependencyRecord
+ {
+ String path;
+ String deps;
+ String line;
+ int lineNumber;
+ }
+
+ class DependencyLineComparator implements Comparator<DependencyRecord>
+ {
+ @Override
+ public int compare(DependencyRecord o1, DependencyRecord o2)
+ {
+ return new Integer(o1.lineNumber).compareTo(o2.lineNumber);
+ }
+ }
+
+ public MXMLFlexJSPublisher(Configuration config, FlexJSProject project)
+ {
+ super(config);
+
+ this.isMarmotinniRun = ((JSGoogConfiguration) configuration).getMarmotinni() != null;
+ this.outputPathParameter = configuration.getOutput();
+ this.useStrictPublishing = ((JSGoogConfiguration) configuration).getStrictPublish();
+
+ this.project = project;
+ }
+
+ private FlexJSProject project;
+
+ private boolean isMarmotinniRun;
+ private String outputPathParameter;
+ private boolean useStrictPublishing;
+ private String closureLibDirPath;
+
+ @Override
+ public File getOutputFolder()
+ {
+ // (erikdebruin) - If there is a -marmotinni switch, we want
+ // the output redirected to the directory it specifies.
+ // - If there is an -output switch, use that path as the
+ // output parent folder.
+ if (isMarmotinniRun)
+ {
+ outputParentFolder = new File(((JSGoogConfiguration) configuration).getMarmotinni());
+ }
+ else if (outputPathParameter != null)
+ {
+ outputParentFolder = new File(outputPathParameter);
+ // FB usually specified -output <project-path>/bin-release/app.swf
+ if (outputPathParameter.contains(".swf"))
+ outputParentFolder = outputParentFolder.getParentFile().getParentFile();
+ }
+ else
+ {
+ outputParentFolder = new File(configuration.getTargetFileDirectory()).getParentFile();
+ }
+
+ outputParentFolder = new File(outputParentFolder, FLEXJS_OUTPUT_DIR_NAME);
+
+ outputFolder = new File(outputParentFolder, File.separator + FLEXJS_INTERMEDIATE_DIR_NAME);
+
+ // (erikdebruin) Marmotinni handles file management, so we
+ // bypass the setup.
- if (!isMarmotinniRun)
++ if (!isMarmotinniRun && !((JSGoogConfiguration)configuration).getSkipTranspile())
+ setupOutputFolder();
+
+ return outputFolder;
+ }
+
+ @Override
+ public boolean publish(ProblemQuery problems) throws IOException
+ {
+ @SuppressWarnings("unused")
+ boolean ok;
+ // boolean subsetGoog = true;
+
+ final String intermediateDirPath = outputFolder.getPath();
+ final File intermediateDir = new File(intermediateDirPath);
+ File srcDir = new File(configuration.getTargetFile());
+ srcDir = srcDir.getAbsoluteFile();
+ srcDir = srcDir.getParentFile();
+
+ final String projectName = FilenameUtils.getBaseName(configuration.getTargetFile());
+ final String outputFileName = projectName + "." + JSSharedData.OUTPUT_EXTENSION;
+
+ File releaseDir = new File(outputParentFolder, FLEXJS_RELEASE_DIR_NAME);
+ final String releaseDirPath = releaseDir.getPath();
+
+ if (!isMarmotinniRun)
+ {
+ if (releaseDir.exists())
+ {
+ org.apache.commons.io.FileUtils.deleteQuietly(releaseDir);
+ }
+
- if (!releaseDir.mkdirs())
- {
- throw new IOException("Unable to create release directory at " + releaseDir.getAbsolutePath());
- }
++ if (!configuration.debug())
++ {
++ if (!releaseDir.mkdirs())
++ {
++ throw new IOException("Unable to create release directory at " + releaseDir.getAbsolutePath());
++ }
++ }
+ }
-
++
+ // If the closure-lib parameter is empty we'll try to find the resources
+ // in the classpath, dump its content to the output directory and use
+ // this
+ // as closure-lib parameter.
+ if (((JSGoogConfiguration) configuration).isClosureLibSet())
+ {
+ closureLibDirPath = ((JSGoogConfiguration) configuration).getClosureLib();
+ }
+ else
+ {
+ // Check if the "goog/deps.js" is available in the classpath.
+ URL resource = Thread.currentThread().getContextClassLoader().getResource("goog/deps.js");
+ if (resource != null)
+ {
+ File closureLibDir = new File(intermediateDir.getParent(), "closure");
+
+ // Only create and dump the content, if the directory does not
+ // exists.
+ if (!closureLibDir.exists())
+ {
+ if (!closureLibDir.mkdirs())
+ {
+ throw new IOException("Unable to create directory for closure-lib at "
+ + closureLibDir.getAbsolutePath());
+ }
+
+ // Strip the url of the parts we don't need.
+ // Unless we are not using some insanely complex setup
+ // the resource will always be on the same machine.
+ String resourceJarPath = resource.getFile();
+ if (resourceJarPath.contains(":"))
+ {
+ resourceJarPath = resourceJarPath.substring(resourceJarPath.lastIndexOf(":") + 1);
+ }
+ if (resourceJarPath.contains("!"))
+ {
+ resourceJarPath = resourceJarPath.substring(0, resourceJarPath.indexOf("!"));
+ }
+ File resourceJar = new File(resourceJarPath);
+
+ // Dump the closure lib from classpath.
+ dumpJar(resourceJar, closureLibDir);
+ }
+ // The compiler automatically adds a "closure" to the lib dir
+ // path,
+ // so we omit this here.
+ closureLibDirPath = intermediateDir.getParentFile().getPath();
+ }
+ // Fallback to the default.
+ else
+ {
+ closureLibDirPath = ((JSGoogConfiguration) configuration).getClosureLib();
+ }
+ }
-
++
+ // Dump FlexJS to the target directory.
+ @SuppressWarnings("unused")
+ String flexJsLibDirPath;
+ // Check if the "FlexJS/src/createjs_externals.js" is available in the
+ // classpath.
+ URL resource = Thread.currentThread().getContextClassLoader().getResource("FlexJS/src/createjs_externals.js");
+ if (resource != null)
+ {
+ File flexJsLibDir = new File(intermediateDir.getParent(), "flexjs");
+
+ // Only create and dump the content, if the directory does not
+ // exists.
+ if (!flexJsLibDir.exists())
+ {
+ if (!flexJsLibDir.mkdirs())
+ {
+ throw new IOException("Unable to create directory for flexjs-lib at "
+ + flexJsLibDir.getAbsolutePath());
+ }
+
+ // Strip the url of the parts we don't need.
+ // Unless we are not using some insanely complex setup
+ // the resource will always be on the same machine.
+ String resourceJarPath = resource.getFile();
+ if (resourceJarPath.contains(":"))
+ {
+ resourceJarPath = resourceJarPath.substring(resourceJarPath.lastIndexOf(":") + 1);
+ }
+ if (resourceJarPath.contains("!"))
+ {
+ resourceJarPath = resourceJarPath.substring(0, resourceJarPath.indexOf("!"));
+ }
+ File resourceJar = new File(resourceJarPath);
+
+ // Dump the closure lib from classpath.
+ dumpJar(resourceJar, flexJsLibDir);
+ }
+ // The compiler automatically adds a "closure" to the lib dir path,
+ // so we omit this here.
+ flexJsLibDirPath = intermediateDir.getParentFile().getPath();
+ }
+
+ final String closureGoogSrcLibDirPath = closureLibDirPath + "/closure/goog/";
+ final String closureGoogTgtLibDirPath = intermediateDirPath + "/library/closure/goog";
+ // final String depsSrcFilePath = intermediateDirPath
+ // + "/library/closure/goog/deps.js";
+ @SuppressWarnings("unused")
+ final String depsTgtFilePath = intermediateDirPath + "/deps.js";
+ final String projectIntermediateJSFilePath = intermediateDirPath + File.separator + outputFileName;
+ final String projectReleaseJSFilePath = releaseDirPath + File.separator + outputFileName;
-
- appendExportSymbol(projectIntermediateJSFilePath, projectName);
- appendEncodedCSS(projectIntermediateJSFilePath, projectName);
-
- // if (!subsetGoog)
- // {
- // (erikdebruin) We need to leave the 'goog' files and dependencies well
- // enough alone. We copy the entire library over so the
- // 'goog' dependencies will resolve without our help.
- FileUtils.copyDirectory(new File(closureGoogSrcLibDirPath), new File(closureGoogTgtLibDirPath));
- // }
-
++
++ if (!((JSGoogConfiguration)configuration).getSkipTranspile())
++ {
++ appendExportSymbol(projectIntermediateJSFilePath, projectName);
++ appendEncodedCSS(projectIntermediateJSFilePath, projectName);
++
++ // if (!subsetGoog)
++ // {
++ // (erikdebruin) We need to leave the 'goog' files and dependencies well
++ // enough alone. We copy the entire library over so the
++ // 'goog' dependencies will resolve without our help.
++ FileUtils.copyDirectory(new File(closureGoogSrcLibDirPath), new File(closureGoogTgtLibDirPath));
++ // }
++ }
++
+ JSClosureCompilerWrapper compilerWrapper = new JSClosureCompilerWrapper(((JSGoogConfiguration) configuration).getJSCompilerOptions());
+
+ List<ISWC> swcs = project.getLibraries();
+
+ // (erikdebruin) We don't want to forget that we need to tell the GCC
+ // about them fancy externs we've been working so hard on
+ for (ISWC swc : swcs)
+ {
+ Map<String, ISWCFileEntry> files = swc.getFiles();
+ for (String key : files.keySet())
+ {
+ if (key.startsWith(FLEXJS_EXTERNS))
+ {
+ ISWCFileEntry fileEntry = swc.getFile(key);
+ if (fileEntry != null)
+ {
+ File destFile = new File(intermediateDirPath + File.separator + key);
+ InputStream inStream = fileEntry.createInputStream();
+ OutputStream outStream = FileUtils.openOutputStream(destFile);
+ byte[] b = new byte[1024 * 1024];
+ int bytes_read;
+ while ((bytes_read = inStream.read(b)) != -1)
+ {
+ outStream.write(b, 0, bytes_read);
+ }
+ outStream.flush();
+ outStream.close();
+ inStream.close();
+
+ String destPath = destFile.getAbsolutePath();
+
+ System.out.println("using extern: " + destPath);
+
+ compilerWrapper.addJSExternsFile(destPath);
+ }
+ }
+ }
+ }
+
+ GoogDepsWriter gdw = new GoogDepsWriter(intermediateDir, projectName, (JSGoogConfiguration) configuration, swcs);
+ StringBuilder depsFileData = new StringBuilder();
+ try
+ {
+ ArrayList<String> fileList = gdw.getListOfFiles(problems);
+ for (String file : fileList)
+ {
+ compilerWrapper.addJSSourceFile(file);
+ }
+ ok = gdw.generateDeps(problems, depsFileData);
+ /*
+ * if (!subsetGoog) { writeFile(depsTgtFilePath,
+ * depsFileData.toString(), false); } else { String s =
+ * depsFileData.toString(); int c = s.indexOf("'goog.");
+ * ArrayList<String> googreqs = new ArrayList<String>(); while (c !=
+ * -1) { int c2 = s.indexOf("'", c + 1); String googreq =
+ * s.substring(c, c2 + 1); googreqs.add(googreq); c =
+ * s.indexOf("'goog.", c2); } HashMap<String, DependencyRecord>
+ * defmap = new HashMap<String, DependencyRecord>(); // read in
+ * goog's deps.js FileInputStream fis = new
+ * FileInputStream(closureGoogSrcLibDirPath + "/deps.js"); Scanner
+ * scanner = new Scanner(fis, "UTF-8"); String addDependency =
+ * "goog.addDependency('"; int currentLine = 0; while
+ * (scanner.hasNextLine()) { String googline = scanner.nextLine();
+ * if (googline.indexOf(addDependency) == 0) { int c1 =
+ * googline.indexOf("'", addDependency.length() + 1); String
+ * googpath = googline.substring(addDependency.length(), c1); String
+ * googdefs = googline.substring(googline.indexOf("[") + 1,
+ * googline.indexOf("]")); String googdeps =
+ * googline.substring(googline.lastIndexOf("[") + 1,
+ * googline.lastIndexOf("]")); String[] thedefs =
+ * googdefs.split(","); DependencyRecord deprec = new
+ * DependencyRecord(); deprec.path = googpath; deprec.deps =
+ * googdeps; deprec.line = googline; deprec.lineNumber =
+ * currentLine; for (String def : thedefs) { def = def.trim();
+ * defmap.put(def, deprec); } } currentLine++; } // (erikdebruin)
+ * Prevent 'Resource leak' warning on line 212: scanner.close();
+ * ArrayList<DependencyRecord> subsetdeps = new
+ * ArrayList<DependencyRecord>(); HashMap<String, String> gotgoog =
+ * new HashMap<String, String>(); for (String req : googreqs) {
+ * DependencyRecord deprec = defmap.get(req); // if we've already
+ * processed this file, skip if (!gotgoog.containsKey(deprec.path))
+ * { gotgoog.put(deprec.path, null); subsetdeps.add(deprec);
+ * addDeps(subsetdeps, gotgoog, defmap, deprec.deps); } } // now we
+ * should have the subset of files we need in the order needed
+ * StringBuilder sb = new StringBuilder();
+ * sb.append("goog.addDependency('base.js', ['goog'], []);\n"); File
+ * file = new File(closureGoogSrcLibDirPath + "/base.js");
+ * FileUtils.copyFileToDirectory(file, new
+ * File(closureGoogTgtLibDirPath));
+ * compilerWrapper.addJSSourceFile(file.getCanonicalPath());
+ * Collections.sort(subsetdeps, new DependencyLineComparator()); for
+ * (DependencyRecord subsetdeprec : subsetdeps) {
+ * sb.append(subsetdeprec.line).append("\n"); }
+ * writeFile(depsTgtFilePath, sb.toString() +
+ * depsFileData.toString(), false); // copy the required files for
+ * (String googfn : gotgoog.keySet()) { file = new
+ * File(closureGoogSrcLibDirPath + File.separator + googfn); String
+ * dir = closureGoogTgtLibDirPath; if (googfn.contains("/")) { dir
+ * += File.separator + googfn.substring(0, googfn.lastIndexOf("/"));
+ * } FileUtils.copyFileToDirectory(file, new File(dir));
+ * compilerWrapper.addJSSourceFile(file.getCanonicalPath()); } }
+ */
+ }
+ catch (InterruptedException e)
+ {
+ e.printStackTrace();
+ return false;
+ }
+
+ IOFileFilter pngSuffixFilter = FileFilterUtils.and(FileFileFilter.FILE,
+ FileFilterUtils.suffixFileFilter(".png"));
+ IOFileFilter gifSuffixFilter = FileFilterUtils.and(FileFileFilter.FILE,
+ FileFilterUtils.suffixFileFilter(".gif"));
+ IOFileFilter jpgSuffixFilter = FileFilterUtils.and(FileFileFilter.FILE,
+ FileFilterUtils.suffixFileFilter(".jpg"));
+ IOFileFilter jsonSuffixFilter = FileFilterUtils.and(FileFileFilter.FILE,
+ FileFilterUtils.suffixFileFilter(".json"));
+ IOFileFilter assetFiles = FileFilterUtils.or(pngSuffixFilter, jpgSuffixFilter, gifSuffixFilter,
+ jsonSuffixFilter);
+ IOFileFilter subdirs = FileFilterUtils.or(DirectoryFileFilter.DIRECTORY, assetFiles);
+
+ FileUtils.copyDirectory(srcDir, intermediateDir, subdirs);
- FileUtils.copyDirectory(srcDir, releaseDir, subdirs);
++ if (!configuration.debug())
++ FileUtils.copyDirectory(srcDir, releaseDir, subdirs);
+
- // File srcDeps = new File(depsSrcFilePath);
++ // File srcDeps = new File(depsSrcFilePath);
+
- writeHTML("intermediate", projectName, intermediateDirPath, depsFileData.toString(), gdw.additionalHTML);
- writeHTML("release", projectName, releaseDirPath, null, gdw.additionalHTML);
- if (project.needCSS)
++ if (!((JSGoogConfiguration)configuration).getSkipTranspile())
++ writeHTML("intermediate", projectName, intermediateDirPath, depsFileData.toString(), gdw.additionalHTML);
++ if (!configuration.debug())
++ writeHTML("release", projectName, releaseDirPath, null, gdw.additionalHTML);
++ if (project.needCSS || ((JSGoogConfiguration)configuration).getSkipTranspile())
+ {
- writeCSS(projectName, intermediateDirPath);
- writeCSS(projectName, releaseDirPath);
++ if (!((JSGoogConfiguration)configuration).getSkipTranspile())
++ writeCSS(projectName, intermediateDirPath);
++ if (!configuration.debug())
++ FileUtils.copyFile(new File(intermediateDirPath + File.separator + projectName + ".css"),
++ new File(releaseDirPath + File.separator + projectName + ".css"));
+ }
-
- /*
- * if (!subsetGoog) { // (erikdebruin) add 'goog' files Collection<File>
- * files = org.apache.commons.io.FileUtils.listFiles(new File(
- * closureGoogTgtLibDirPath), new RegexFileFilter("^.*(\\.js)"),
- * DirectoryFileFilter.DIRECTORY); for (File file : files) {
- * compilerWrapper.addJSSourceFile(file.getCanonicalPath()); } }
- */
- Collection<File> files = org.apache.commons.io.FileUtils.listFiles(new File(closureGoogSrcLibDirPath),
- new RegexFileFilter("^.*(\\.js)"), DirectoryFileFilter.DIRECTORY);
- for (File file : files)
++
++ if (!configuration.debug())
+ {
- compilerWrapper.addJSSourceFile(file.getCanonicalPath());
++ /*
++ * if (!subsetGoog) { // (erikdebruin) add 'goog' files Collection<File>
++ * files = org.apache.commons.io.FileUtils.listFiles(new File(
++ * closureGoogTgtLibDirPath), new RegexFileFilter("^.*(\\.js)"),
++ * DirectoryFileFilter.DIRECTORY); for (File file : files) {
++ * compilerWrapper.addJSSourceFile(file.getCanonicalPath()); } }
++ */
++ Collection<File> files = org.apache.commons.io.FileUtils.listFiles(new File(closureGoogSrcLibDirPath),
++ new RegexFileFilter("^.*(\\.js)"), DirectoryFileFilter.DIRECTORY);
++ for (File file : files)
++ {
++ compilerWrapper.addJSSourceFile(file.getCanonicalPath());
++ }
++
++ /*
++ * // (erikdebruin) add project files for (String filePath :
++ * gdw.filePathsInOrder) { compilerWrapper.addJSSourceFile( new
++ * File(filePath).getCanonicalPath()); }
++ */
++
++ compilerWrapper.setOptions(projectReleaseJSFilePath, useStrictPublishing, projectName);
++
++ /*
++ * // (erikdebruin) Include the 'goog' deps to allow the compiler to
++ * resolve // dependencies. compilerWrapper.addJSSourceFile(
++ * closureGoogSrcLibDirPath + File.separator + "deps.js");
++ */
++ List<String> externs = ((JSGoogConfiguration) configuration).getExternalJSLib();
++ for (String extern : externs)
++ {
++ compilerWrapper.addJSExternsFile(extern);
++ }
++
++ compilerWrapper.targetFilePath = projectReleaseJSFilePath;
++ compilerWrapper.compile();
++
++ appendSourceMapLocation(projectReleaseJSFilePath, projectName);
+ }
-
- /*
- * // (erikdebruin) add project files for (String filePath :
- * gdw.filePathsInOrder) { compilerWrapper.addJSSourceFile( new
- * File(filePath).getCanonicalPath()); }
- */
-
- compilerWrapper.setOptions(projectReleaseJSFilePath, useStrictPublishing, projectName);
-
- /*
- * // (erikdebruin) Include the 'goog' deps to allow the compiler to
- * resolve // dependencies. compilerWrapper.addJSSourceFile(
- * closureGoogSrcLibDirPath + File.separator + "deps.js");
- */
- List<String> externs = ((JSGoogConfiguration) configuration).getExternalJSLib();
- for (String extern : externs)
- {
- compilerWrapper.addJSExternsFile(extern);
- }
-
- compilerWrapper.targetFilePath = projectReleaseJSFilePath;
- compilerWrapper.compile();
-
- appendSourceMapLocation(projectReleaseJSFilePath, projectName);
-
+ /*
+ * if (!isMarmotinniRun) { String allDeps = ""; if (!subsetGoog) {
+ * allDeps += FileUtils.readFileToString(srcDeps); } allDeps +=
+ * FileUtils.readFileToString(new File(depsTgtFilePath));
+ *
+ * FileUtils.writeStringToFile(srcDeps, allDeps);
+ *
+ * org.apache.commons.io.FileUtils.deleteQuietly(new
+ * File(depsTgtFilePath)); }
+ */
+
+ // if (ok)
+ System.out.println("The project '" + projectName + "' has been successfully compiled and optimized.");
+
+ return true;
+ }
+
+ /*
+ * private void addDeps(ArrayList<DependencyRecord> subsetdeps,
+ * HashMap<String, String> gotgoog, HashMap<String, DependencyRecord>
+ * defmap, String deps) { if (deps.length() == 0) { return; }
+ *
+ * String[] deplist = deps.split(","); for (String dep : deplist) { dep =
+ * dep.trim(); DependencyRecord deprec = defmap.get(dep); if
+ * (!gotgoog.containsKey(deprec.path)) { gotgoog.put(deprec.path, null); //
+ * put addDependencyLine in subset file subsetdeps.add(deprec);
+ * addDeps(subsetdeps, gotgoog, defmap, deprec.deps); } } }
+ */
+
+ private void appendExportSymbol(String path, String projectName) throws IOException
+ {
+ //every file should already have exportsymbol
+ //writeFile(path, "\n\n// Ensures the symbol will be visible after compiler renaming.\n" + "goog.exportSymbol('"
+ // + projectName + "', " + projectName + ");\n", true);
+ }
+
+ private void appendEncodedCSS(String path, String projectName) throws IOException
+ {
+ if (!project.needCSS)
+ return;
+
+ StringBuilder appendString = new StringBuilder();
+ appendString.append("\n\n");
+ appendString.append(projectName);
+ appendString.append(".prototype.cssData = [");
+ JSCSSCompilationSession cssSession = (JSCSSCompilationSession) project.getCSSCompilationSession();
+ String s = cssSession.getEncodedCSS();
+ int reqidx = s.indexOf(JSGoogEmitterTokens.GOOG_REQUIRE.getToken());
+ if (reqidx != -1)
+ {
+ String reqs = s.substring(reqidx);
+ s = s.substring(0, reqidx - 1);
+ String fileData = readCode(new File(path));
+ reqidx = fileData.indexOf(JSGoogEmitterTokens.GOOG_REQUIRE.getToken());
+ String after = fileData.substring(reqidx);
+ String before = fileData.substring(0, reqidx - 1);
+ s = before + reqs + after + appendString.toString() + s;
+ writeFile(path, s, false);
+ }
+ else
+ {
+ appendString.append(s);
+ writeFile(path, appendString.toString(), true);
+ }
+ }
+
+ protected String readCode(File file)
+ {
+ String code = "";
+ try
+ {
+ BufferedReader in = new BufferedReader(new InputStreamReader(new FileInputStream(file), "UTF8"));
+
+ String line = in.readLine();
+
+ while (line != null)
+ {
+ code += line + "\n";
+ line = in.readLine();
+ }
+ code = code.substring(0, code.length() - 1);
+
+ in.close();
+ }
+ catch (Exception e)
+ {
+ // nothing to see, move along...
+ }
+
+ return code;
+ }
+
+ protected void writeHTML(String type, String projectName, String dirPath, String deps, List<String> additionalHTML)
+ throws IOException
+ {
+ StringBuilder htmlFile = new StringBuilder();
+ htmlFile.append("<!DOCTYPE html>\n");
+ htmlFile.append("<html>\n");
+ htmlFile.append("<head>\n");
+ htmlFile.append("\t<meta http-equiv=\"X-UA-Compatible\" content=\"IE=edge,chrome=1\">\n");
+ htmlFile.append("\t<meta http-equiv=\"Content-Type\" content=\"text/html; charset=utf-8\">\n");
+ htmlFile.append("\t<link rel=\"stylesheet\" type=\"text/css\" href=\"").append(projectName).append(".css\">\n");
+
+ for (String s : additionalHTML)
+ htmlFile.append(s).append("\n");
+
+ if ("intermediate".equals(type))
+ {
+ htmlFile.append("\t<script type=\"text/javascript\" src=\"./library/closure/goog/base.js\"></script>\n");
+ htmlFile.append("\t<script type=\"text/javascript\">\n");
+ htmlFile.append(deps);
+ htmlFile.append("\t\tgoog.require(\"");
+ htmlFile.append(projectName);
+ htmlFile.append("\");\n");
+ htmlFile.append("\t</script>\n");
+ }
+ else
+ {
+ htmlFile.append("\t<script type=\"text/javascript\" src=\"./");
+ htmlFile.append(projectName);
+ htmlFile.append(".js\"></script>\n");
+ }
+
+ htmlFile.append("</head>\n");
+ htmlFile.append("<body>\n");
+ htmlFile.append("\t<script type=\"text/javascript\">\n");
+ htmlFile.append("\t\tnew ");
+ htmlFile.append(projectName);
+ htmlFile.append("()");
+ htmlFile.append(".start();\n");
+ htmlFile.append("\t</script>\n");
+ htmlFile.append("</body>\n");
+ htmlFile.append("</html>");
+
+ writeFile(dirPath + File.separator + "index.html", htmlFile.toString(), false);
+ }
+
+ private void writeCSS(String projectName, String dirPath) throws IOException
+ {
+ JSCSSCompilationSession cssSession = (JSCSSCompilationSession) project.getCSSCompilationSession();
+ writeFile(dirPath + File.separator + projectName + ".css", cssSession.emitCSS(), false);
+ for (CSSFontFace fontFace : cssSession.fontFaces)
+ {
+ // check frameworks/fonts folder
+ String configdir = ((JSGoogConfiguration) configuration).getLoadConfig();
+ File dir = new File(configdir);
+ dir = dir.getParentFile();
+ for (ICSSPropertyValue prop : fontFace.getSources())
+ {
+ if (prop instanceof CSSArrayPropertyValue)
+ {
+ for (ICSSPropertyValue value : ((CSSArrayPropertyValue)prop).getElements())
+ {
+ CSSFunctionCallPropertyValue fn = (CSSFunctionCallPropertyValue)value;
+ String fontPath = fn.rawArguments;
+ if (fontPath.startsWith("'"))
+ fontPath = fontPath.substring(1, fontPath.length() - 1);
+ if (fontPath.startsWith("\""))
+ fontPath = fontPath.substring(1, fontPath.length() - 1);
+ int c = fontPath.indexOf("?");
+ if (c != -1)
+ fontPath = fontPath.substring(0, c);
+ File fontFile = new File(dir.getAbsolutePath() + File.separator + fontPath);
+ File destFile = new File(dirPath + File.separator + fontPath);
+ if (fontFile.exists())
+ {
+ if (!destFile.exists())
+ FileUtils.copyFile(fontFile, destFile);
+ }
+ }
+ }
+ else
+ {
+ if (prop instanceof CSSFunctionCallPropertyValue)
+ {
+ CSSFunctionCallPropertyValue fn = (CSSFunctionCallPropertyValue)prop;
+ String fontPath = fn.rawArguments;
+ if (fontPath.startsWith("'"))
+ fontPath = fontPath.substring(1, fontPath.length() - 1);
+ if (fontPath.startsWith("\""))
+ fontPath = fontPath.substring(1, fontPath.length() - 1);
+ int c = fontPath.indexOf("?");
+ if (c != -1)
+ fontPath = fontPath.substring(0, c);
+ File fontFile = new File(dir.getAbsolutePath() + File.separator + fontPath);
+ File destFile = new File(dirPath + File.separator + fontPath);
+ if (fontFile.exists())
+ {
+ if (!destFile.exists())
+ FileUtils.copyFile(fontFile, destFile);
+ }
+ }
+ }
+ }
+ }
+ }
+}
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/de070636/compiler-jx/src/main/java/org/apache/flex/compiler/internal/driver/js/goog/JSGoogConfiguration.java
----------------------------------------------------------------------
diff --cc compiler-jx/src/main/java/org/apache/flex/compiler/internal/driver/js/goog/JSGoogConfiguration.java
index 0f03323,0000000..6eb1037
mode 100644,000000..100644
--- a/compiler-jx/src/main/java/org/apache/flex/compiler/internal/driver/js/goog/JSGoogConfiguration.java
+++ b/compiler-jx/src/main/java/org/apache/flex/compiler/internal/driver/js/goog/JSGoogConfiguration.java
@@@ -1,311 -1,0 +1,331 @@@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+package org.apache.flex.compiler.internal.driver.js.goog;
+
+import java.io.File;
+import java.io.IOException;
+import java.net.URLDecoder;
+import java.util.ArrayList;
+import java.util.List;
+
+import org.apache.flex.compiler.clients.JSConfiguration;
+import org.apache.flex.compiler.clients.MXMLJSC;
+import org.apache.flex.compiler.config.ConfigurationValue;
+import org.apache.flex.compiler.exceptions.ConfigurationException;
+import org.apache.flex.compiler.internal.config.annotations.Config;
+import org.apache.flex.compiler.internal.config.annotations.FlexOnly;
+import org.apache.flex.compiler.internal.config.annotations.InfiniteArguments;
+import org.apache.flex.compiler.internal.config.annotations.Mapping;
+
+/**
+ * The {@link JSGoogConfiguration} class holds all compiler arguments needed for
+ * compiling ActionScript to JavaScript the 'goog' way.
+ * <p>
+ * Specific flags are implemented here for the configuration to be loaded by the
+ * configure() method of {@link MXMLJSC}.
+ * <p>
+ * This class inherits all compiler arguments from the MXMLC compiler.
+ *
+ * @author Erik de Bruin
+ */
+public class JSGoogConfiguration extends JSConfiguration
+{
+ public JSGoogConfiguration()
+ {
+ }
+
+ //
+ // 'closure-lib'
+ //
+
+ protected String closureLib = "";
+
+ public boolean isClosureLibSet() {
+ return !closureLib.isEmpty();
+ }
+
+ public String getClosureLib()
+ {
+ try
+ {
+ if (closureLib.equals(""))
+ {
+ return getAbsolutePathFromPathRelativeToMXMLC(
+ "../../js/lib/google/closure-library");
+ }
+ }
+ catch (Exception e) { /* better to try and fail... */ }
+
+ return closureLib;
+ }
+
+ @Config
+ @Mapping("closure-lib")
+ public void setClosureLib(ConfigurationValue cv, String value)
+ throws ConfigurationException
+ {
+ if (value != null)
+ closureLib = value;
+ }
+
+ //
+ // Override 'compiler.binding-value-change-event-type'
+ //
+
+ private String bindingValueChangeEventType = "valueChange";
+
+ @Override
+ public String getBindingValueChangeEventType()
+ {
+ return bindingValueChangeEventType;
+ }
+
+ @Override
+ @Config(advanced = true)
+ public void setCompilerBindingValueChangeEventType(ConfigurationValue cv, String b)
+ {
+ bindingValueChangeEventType = b;
+ }
+
+ //
+ // Override 'compiler.mxml.children-as-data'
+ //
+
+ private Boolean childrenAsData = true;
+
+ @Override
+ public Boolean getCompilerMxmlChildrenAsData()
+ {
+ return childrenAsData;
+ }
+
+ @Override
+ @Config
+ @Mapping({"compiler", "mxml", "children-as-data"})
+ @FlexOnly
+ public void setCompilerMxmlChildrenAsData(ConfigurationValue cv, Boolean asData) throws ConfigurationException
+ {
+ childrenAsData = asData;
+ }
+
+ //
+ // 'marmotinni'
+ //
+
+ private String marmotinni;
+
+ public String getMarmotinni()
+ {
+ return marmotinni;
+ }
+
+ @Config
+ @Mapping("marmotinni")
+ public void setMarmotinni(ConfigurationValue cv, String value)
+ throws ConfigurationException
+ {
+ marmotinni = value;
+ }
+
+ //
+ // 'sdk-js-lib'
+ //
+
+ protected List<String> sdkJSLib = new ArrayList<String>();
+
+ public List<String> getSDKJSLib()
+ {
+ if (sdkJSLib.size() == 0)
+ {
+ try
+ {
+ String path = getAbsolutePathFromPathRelativeToMXMLC(
+ "../../frameworks/js/FlexJS/src");
+
+ sdkJSLib.add(path);
+ }
+ catch (Exception e) { /* better to try and fail... */ }
+ }
+
+ return sdkJSLib;
+ }
+
+ @Config(allowMultiple = true)
+ @Mapping("sdk-js-lib")
+ @InfiniteArguments
+ public void setSDKJSLib(ConfigurationValue cv, List<String> value)
+ throws ConfigurationException
+ {
+ sdkJSLib.addAll(value);
+ }
+
+ //
+ // 'external-js-lib'
+ //
+
+ private List<String> externalJSLib = new ArrayList<String>();
+
+ public List<String> getExternalJSLib()
+ {
+ return externalJSLib;
+ }
+
+ @Config(allowMultiple = true)
+ @Mapping("external-js-lib")
+ @InfiniteArguments
+ public void setExternalJSLib(ConfigurationValue cv, List<String> value)
+ throws ConfigurationException
+ {
+ externalJSLib.addAll(value);
+ }
+
+ //
+ // 'strict-publish'
+ //
+
+ private boolean strictPublish = true;
+
+ public boolean getStrictPublish()
+ {
+ return strictPublish;
+ }
+
+ @Config
+ @Mapping("strict-publish")
+ public void setStrictPublish(ConfigurationValue cv, boolean value)
+ throws ConfigurationException
+ {
+ strictPublish = value;
+ }
+
+ //
+ // 'keep-asdoc'
+ //
+
+ private boolean keepASDoc = true;
+
+ public boolean getKeepASDoc()
+ {
+ return keepASDoc;
+ }
+
+ @Config
+ @Mapping("keep-asdoc")
+ public void setKeepASDoc(ConfigurationValue cv, boolean value)
+ throws ConfigurationException
+ {
+ keepASDoc = value;
+ }
+
+
+
+ //
+ // 'remove-circulars'
+ //
+
+ private boolean removeCirculars = false;
+
+ public boolean getRemoveCirculars()
+ {
+ return removeCirculars;
+ }
+
+ @Config
+ @Mapping("remove-circulars")
+ public void setRemoveCirculars(ConfigurationValue cv, boolean value)
+ throws ConfigurationException
+ {
+ removeCirculars = value;
+ }
+
+
++ //
++ // 'skip-transpile'
++ //
++
++ private boolean skipTranspile = false;
++
++ public boolean getSkipTranspile()
++ {
++ return skipTranspile;
++ }
++
++ @Config
++ @Mapping("skip-transpile")
++ public void setSkipTranspile(ConfigurationValue cv, boolean value)
++ throws ConfigurationException
++ {
++ skipTranspile = value;
++ }
++
++
+
+ protected String getAbsolutePathFromPathRelativeToMXMLC(String relativePath)
+ throws IOException
+ {
+ String mxmlcURL = MXMLJSC.class.getProtectionDomain().getCodeSource()
+ .getLocation().getPath();
+
+ File mxmlc = new File(URLDecoder.decode(mxmlcURL, "utf-8"));
+
+ return new File(mxmlc.getParent() + File.separator + relativePath)
+ .getCanonicalPath();
+ }
+
+ //
+ // 'js-compiler-option'
+ //
+
+ protected List<String> jsCompilerOptions = new ArrayList<String>();
+
+ public List<String> getJSCompilerOptions()
+ {
+ return jsCompilerOptions;
+ }
+
+ @Config(allowMultiple = true)
+ @Mapping("js-compiler-option")
+ @InfiniteArguments
+ public void setJSCompilerOptions(ConfigurationValue cv, List<String> value)
+ throws ConfigurationException
+ {
+ jsCompilerOptions.addAll(value);
+ }
+
+ //
+ // 'js-output-optimization'
+ //
+
+ protected List<String> jsOutputOptimizations = new ArrayList<String>();
+
+ public List<String> getJSOutputOptimizations()
+ {
+ return jsOutputOptimizations;
+ }
+
+ @Config(allowMultiple = true)
+ @Mapping("js-output-optimization")
+ @InfiniteArguments
+ public void setJSOutputOptimizations(ConfigurationValue cv, List<String> value)
+ throws ConfigurationException
+ {
+ jsOutputOptimizations.addAll(value);
+ }
+}
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/de070636/compiler-jx/src/test/java/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
----------------------------------------------------------------------
diff --cc compiler-jx/src/test/java/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
index 638f71b,0000000..ba03b6d
mode 100644,000000..100644
--- a/compiler-jx/src/test/java/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
+++ b/compiler-jx/src/test/java/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
@@@ -1,666 -1,0 +1,716 @@@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+package org.apache.flex.compiler.internal.codegen.js.flexjs;
+
+import org.apache.flex.compiler.driver.IBackend;
+import org.apache.flex.compiler.internal.codegen.js.goog.TestGoogGlobalClasses;
+import org.apache.flex.compiler.internal.driver.js.flexjs.FlexJSBackend;
+import org.apache.flex.compiler.internal.driver.js.goog.JSGoogConfiguration;
+import org.apache.flex.compiler.internal.projects.FlexJSProject;
+import org.apache.flex.compiler.internal.tree.as.VariableNode;
+import org.apache.flex.compiler.tree.as.IASNode;
+import org.apache.flex.compiler.tree.as.IBinaryOperatorNode;
+import org.apache.flex.compiler.tree.as.IForLoopNode;
+import org.apache.flex.compiler.tree.as.IFunctionCallNode;
+import org.apache.flex.compiler.tree.as.IFunctionNode;
+import org.apache.flex.compiler.tree.as.IUnaryOperatorNode;
+import org.apache.flex.compiler.tree.as.IVariableNode;
+import org.junit.Test;
+import org.junit.Ignore;
+
+/**
+ * @author Erik de Bruin
+ */
+public class TestFlexJSGlobalClasses extends TestGoogGlobalClasses
+{
+ @Override
+ public void setUp()
+ {
+ project = new FlexJSProject(workspace);
+ ((FlexJSProject)project).config = new JSGoogConfiguration();
+ project.setProxyBaseClass("flash.utils.Proxy");
+ super.setUp();
+ }
+
+ @Override
+ protected IBackend createBackend()
+ {
+ return new FlexJSBackend();
+ }
+
+ @Override
+ @Test
+ public void testArguments()
+ {
+ IFunctionNode node = getMethod("function a():void { trace(arguments);}");
+ asBlockWalker.visitFunction(node);
+ assertOut("FalconTest_A.prototype.a = function() {\n org.apache.flex.utils.Language.trace(arguments);\n}");
+ }
+
+ @Test
+ public void testArrayNoArgs()
+ {
+ IVariableNode node = getVariable("var a:Array = new Array();");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {Array} */ a = new Array()");
+ }
+
+ @Test
+ public void testArrayStringArgs()
+ {
+ IVariableNode node = getVariable("var a:Array = new Array('Hello', 'World');");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {Array} */ a = new Array('Hello', 'World')");
+ }
+
+ @Test
+ public void testArraySizeArg()
+ {
+ IVariableNode node = getVariable("var a:Array = new Array(30);");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {Array} */ a = new Array(30)");
+ }
+
+ @Test
+ public void testArrayNumberArgs()
+ {
+ IVariableNode node = getVariable("var a:Array = new Array(30, 40);");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {Array} */ a = new Array(30, 40)");
+ }
+
+ @Test
+ public void testArrayArrayArg()
+ {
+ IVariableNode node = getVariable("var a:Array = new Array(['Hello', 'World']);");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {Array} */ a = new Array(['Hello', 'World'])");
+ }
+
+ @Test
+ public void testArrayConstCaseInsensitive()
+ {
+ IVariableNode node = getVariable("var a:Number = Array.CASEINSENSITIVE");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {number} */ a = 1");
+ }
+
+ @Test
+ public void testArrayConstNumeric()
+ {
+ IVariableNode node = getVariable("var a:Number = Array.NUMERIC");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {number} */ a = 16");
+ }
+
+ @Ignore
+ public void testArrayRemoveAt()
+ {
+ // requires FP19 or newer
+ IBinaryOperatorNode node = getBinaryNode("var a:Array = new Array(); a.removeAt(2)");
+ IFunctionCallNode parentNode = (IFunctionCallNode)(node.getParent());
+ asBlockWalker.visitFunctionCall(parentNode);
+ assertOut("a.splice(2, 1)");
+ }
+
+ @Ignore
+ public void testArrayInsertAt()
+ {
+ // requires FP19 or newer
+ IBinaryOperatorNode node = getBinaryNode("var a:Array = new Array(); a.insertAt(2, 'foo')");
+ IFunctionCallNode parentNode = (IFunctionCallNode)(node.getParent());
+ asBlockWalker.visitFunctionCall(parentNode);
+ assertOut("a.splice(2, 0, 'foo')");
+ }
+
+ @Test
+ public void testArraySortOn()
+ {
+ IBinaryOperatorNode node = getBinaryNode("var a:Array = new Array(); a.sortOn('foo')");
+ IFunctionCallNode parentNode = (IFunctionCallNode)(node.getParent());
+ asBlockWalker.visitFunctionCall(parentNode);
+ assertOut("org.apache.flex.utils.Language.sortOn(a, 'foo')");
+ }
+
+ @Test
+ public void testArraySortOnTwoArgs()
+ {
+ IBinaryOperatorNode node = getBinaryNode("var a:Array = new Array(); a.sortOn('foo', 10)");
+ IFunctionCallNode parentNode = (IFunctionCallNode)(node.getParent());
+ asBlockWalker.visitFunctionCall(parentNode);
+ assertOut("org.apache.flex.utils.Language.sortOn(a, 'foo', 10)");
+ }
+
+ @Test
+ public void testIntConstMaxValue()
+ {
+ IVariableNode node = getVariable("var a:Number = int.MAX_VALUE");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {number} */ a = 2147483648");
+ }
+
+ @Test
+ public void testIntConstMinValue()
+ {
+ IVariableNode node = getVariable("var a:Number = int.MIN_VALUE");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {number} */ a = -2147483648");
+ }
+
+ @Test
+ public void testUintConstMaxValue()
+ {
+ IVariableNode node = getVariable("var a:Number = uint.MAX_VALUE");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {number} */ a = 4294967295");
+ }
+
+ @Test
+ public void testUintConstMinValue()
+ {
+ IVariableNode node = getVariable("var a:Number = uint.MIN_VALUE");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {number} */ a = 0");
+ }
+
+ @Test
+ public void testDateGetMinutes()
+ {
+ IVariableNode node = getVariable("var a:Date = new Date(); var b:Number = a.minutes");
+ node = (IVariableNode)(node.getParent().getChild(1));
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {number} */ b = a.getMinutes()");
+ }
+
+ @Test
+ public void testDateSetMinutes()
+ {
+ IBinaryOperatorNode node = getBinaryNode("var a:Date = new Date(); a.minutes = 10");
+ asBlockWalker.visitBinaryOperator(node);
+ assertOut("a.setMinutes(10, a.getSeconds(), a.getMilliseconds())");
+ }
+
+ @Test
+ public void testDateGetMinutesMethod()
+ {
+ IVariableNode node = getVariable("var a:Date = new Date(); var b:Number = a.getMinutes()");
+ node = (IVariableNode)(node.getParent().getChild(1));
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {number} */ b = a.getMinutes()");
+ }
+
+ @Test
+ public void testDateSetMinutesMethod()
+ {
+ IBinaryOperatorNode node = getBinaryNode("var a:Date = new Date(); a.setMinutes(10, 0, 0)");
+ IFunctionCallNode parentNode = (IFunctionCallNode)(node.getParent());
+ asBlockWalker.visitFunctionCall(parentNode);
+ assertOut("a.setMinutes(10, 0, 0)");
+ }
+
+ @Override
+ @Test
+ public void testVector()
+ {
+ IVariableNode node = getVariable("var a:Vector.<String> = new Vector.<String>(['Hello', 'World']);");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {Array} */ a = new Array(['Hello', 'World'])");
+ }
+
+ @Test
+ public void testVectorLiteral_1()
+ {
+ IVariableNode node = getVariable("var a:Vector.<String> = new <String>[];");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {Array} */ a = []");
+ }
+
+ @Test
+ public void testVectorLiteral_2()
+ {
+ IVariableNode node = getVariable("var a:Vector.<int> = new <int>[0, 1, 2, 3];");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {Array} */ a = [0, 1, 2, 3]");
+ }
+
+ @Test
+ public void testVectorLiteral_3()
+ {
+ IVariableNode node = getVariable("var a:Vector.<String> = new <String>[\"one\", \"two\", \"three\";");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {Array} */ a = [\"one\", \"two\", \"three\"]");
+ }
+
+ @Test
+ public void testVectorNoArgs()
+ {
+ IVariableNode node = getVariable("var a:Vector.<String> = new Vector.<String>();");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {Array} */ a = new Array()");
+ }
+
+ @Test
+ public void testVectorStringArgs()
+ {
+ IVariableNode node = getVariable("var a:Vector.<String> = new Vector.<String>('Hello', 'World');");
+ asBlockWalker.visitVariable(node);
+ // expected error?
+ assertOut("var /** @type {Array} */ a = new Array('Hello', 'World')");
+ }
+
+ @Test
+ public void testVectorStringArgs3()
+ {
+ IVariableNode node = getVariable("var a:Vector.<String> = new Vector.<String>('Hello', 'World', 'Three');");
+ asBlockWalker.visitVariable(node);
+ // expected error?
+ assertOut("var /** @type {Array} */ a = new Array('Hello', 'World', 'Three')");
+ }
+
+ @Test
+ public void testVectorSizeArg()
+ {
+ IVariableNode node = getVariable("var a:Vector.<String> = new Vector.<String>(30);");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {Array} */ a = new Array(30)");
+ }
+
+ @Test
+ public void testVectorNumberArgs()
+ {
+ IVariableNode node = getVariable("var a:Vector.<String> = new Vector.<String>(30, 40);");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {Array} */ a = new Array(30, 40)");
+ }
+
+ @Test
+ public void testVectorArrayArg()
+ {
+ IVariableNode node = getVariable("var a:Vector.<String> = new Vector.<String>(['Hello', 'World']);");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {Array} */ a = new Array(['Hello', 'World'])");
+ }
+
+ @Test
+ public void testXML()
+ {
+ IVariableNode node = getVariable("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {XML} */ a = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\")");
+ }
+
+ @Test
+ public void testXMLLiteral()
+ {
+ IVariableNode node = getVariable("var a:XML = <top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>");
+ asBlockWalker.visitVariable(node);
- assertOut("var /** @type {XML} */ a = new XML( \"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\") ");
++ assertOut("var /** @type {XML} */ a = new XML( \"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\")");
++ }
++
++ @Test
++ public void testXMLLiteralMultiline()
++ {
++ IVariableNode node = getVariable("var a:XML = <top attr1='cat'>\n<child attr2='dog'>\n<grandchild attr3='fish'>text</grandchild>\n</child>\n</top>");
++ asBlockWalker.visitVariable(node);
++ assertOut("var /** @type {XML} */ a = new XML( \"<top attr1='cat'>\\\n<child attr2='dog'>\\\n<grandchild attr3='fish'>text</grandchild>\\\n</child>\\\n</top>\")");
+ }
+
+ @Test
+ public void testXMLLiteralWithTemplate()
+ {
+ VariableNode node = (VariableNode)getNode("private function get tagname():String { return 'name'; };\n" +
+ "private function get attributename():String { return 'id'; };\n" +
+ "private function get attributevalue():Number { return 5; };\n" +
+ "private function get content():String { return 'Fred'; };\n" +
+ "private function test() { var a:XML = <{tagname} {attributename}={attributevalue}>{content}</{tagname}>;}",
+ VariableNode.class, WRAP_LEVEL_CLASS);
+ asBlockWalker.visitVariable(node);
- assertOut("var /** @type {XML} */ a = new XML( '<' + this.tagname + ' ' + this.attributename + '=' + this.attributevalue + '>' + this.content + '</' + this.tagname + '>') ");
++ assertOut("var /** @type {XML} */ a = new XML( '<' + this.tagname + ' ' + this.attributename + '=' + this.attributevalue + '>' + this.content + '</' + this.tagname + '>')");
+ }
+
+ @Test
+ public void testXMLLiteralAsParam()
+ {
+ IFunctionCallNode node = (IFunctionCallNode)getNode("var a:XML; a.appendChild(<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>)",
+ IFunctionCallNode.class);
+ asBlockWalker.visitFunctionCall(node);
- assertOut("a.appendChild(new XML( \"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\") )");
++ assertOut("a.appendChild(new XML( \"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\"))");
+ }
+
+ @Test
+ public void testXMLLiteralInReassign()
+ {
+ IBinaryOperatorNode node = getBinaryNode("var a:XML = <foo />; a = <top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>)");
+ asBlockWalker.visitBinaryOperator(node);
- assertOut("a = new XML( \"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\") ");
++ assertOut("a = new XML( \"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\")");
+ }
+
+ @Test
+ public void testXMLSingleDot()
+ {
+ IVariableNode node = getVariable("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");var b:XMLList = a.child;");
+ IASNode parentNode = node.getParent();
+ node = (IVariableNode) parentNode.getChild(1);
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {XMLList} */ b = a.child('child')");
+ }
+
+ @Test
+ public void testXMLSingleDotChain()
+ {
+ IVariableNode node = getVariable("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");var b:XMLList = a.child.grandchild;");
+ IASNode parentNode = node.getParent();
+ node = (IVariableNode) parentNode.getChild(1);
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {XMLList} */ b = a.child('child').child('grandchild')");
+ }
+
+ @Test
+ public void testXMLDelete()
+ {
+ IUnaryOperatorNode node = getUnaryNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");delete a.child;");
+ asBlockWalker.visitUnaryOperator(node);
+ assertOut("a.removeChild('child')");
+ }
+
+ @Test
+ public void testXMLDeleteChain()
+ {
+ IUnaryOperatorNode node = getUnaryNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");delete a.child.grandchild;");
+ asBlockWalker.visitUnaryOperator(node);
+ assertOut("a.child('child').removeChild('grandchild')");
+ }
+
+ @Test
+ public void testXMLDeleteObjChain()
+ {
+ IUnaryOperatorNode node = getUnaryNode("public var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");private function foo() { delete this.a.child.grandchild;}",
+ WRAP_LEVEL_CLASS);
+ asBlockWalker.visitUnaryOperator(node);
+ assertOut("this.a.child('child').removeChild('grandchild')");
+ }
+
+ @Test
+ public void testXMLDeleteCastChain()
+ {
+ IUnaryOperatorNode node = getUnaryNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");var b:Object = { xml: a};delete XML(b.xml).child.grandchild;");
+ asBlockWalker.visitUnaryOperator(node);
+ assertOut("org.apache.flex.utils.Language.as(b.xml, XML, true).child('child').removeChild('grandchild')");
+ }
+
+ @Test
+ public void testXMLDeleteCastAsChain()
+ {
+ IUnaryOperatorNode node = getUnaryNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");var b:Object = { xml: a};delete (b.xml as XML).child.grandchild;");
+ asBlockWalker.visitUnaryOperator(node);
+ assertOut("org.apache.flex.utils.Language.as(b.xml, XML).child('child').removeChild('grandchild')");
+ }
+
+ @Test
+ public void testXMLListDelete()
+ {
+ IUnaryOperatorNode node = getUnaryNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");delete a.child[0];");
+ asBlockWalker.visitUnaryOperator(node);
+ assertOut("a.child('child').removeChildAt(0)");
+ }
+
+ @Test
+ public void testXMLListChain()
+ {
+ IUnaryOperatorNode node = getUnaryNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");delete a.child.grandchild[0];");
+ asBlockWalker.visitUnaryOperator(node);
+ assertOut("a.child('child').child('grandchild').removeChildAt(0)");
+ }
+
+ @Test
+ public void testXMLListObjChain()
+ {
+ IUnaryOperatorNode node = getUnaryNode("public var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");private function foo() { delete this.a.child.grandchild[0];}",
+ WRAP_LEVEL_CLASS);
+ asBlockWalker.visitUnaryOperator(node);
+ assertOut("this.a.child('child').child('grandchild').removeChildAt(0)");
+ }
+
+ @Test
+ public void testXMLListCastChain()
+ {
+ IUnaryOperatorNode node = getUnaryNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");var b:Object = { xml: a};delete XML(b.xml).child.grandchild[0];");
+ asBlockWalker.visitUnaryOperator(node);
+ assertOut("org.apache.flex.utils.Language.as(b.xml, XML, true).child('child').child('grandchild').removeChildAt(0)");
+ }
+
+ @Test
+ public void testXMLListAsCastChain()
+ {
+ IUnaryOperatorNode node = getUnaryNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");var b:Object = { xml: a};delete (b.xml as XML).child.grandchild[0];");
+ asBlockWalker.visitUnaryOperator(node);
+ assertOut("org.apache.flex.utils.Language.as(b.xml, XML).child('child').child('grandchild').removeChildAt(0)");
+ }
+
+ @Test
+ public void testXMLNameFunction()
+ {
+ IVariableNode node = getVariable("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");var b:String = a.name();");
+ IASNode parentNode = node.getParent();
+ node = (IVariableNode) parentNode.getChild(1);
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {string} */ b = a.name()");
+ }
+
+ @Test
+ public void testXMLListLengthFunction()
+ {
+ IVariableNode node = getVariable("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");var b:int = a.child.length();");
+ IASNode parentNode = node.getParent();
+ node = (IVariableNode) parentNode.getChild(1);
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {number} */ b = a.child('child').length()");
+ }
+
+ @Test
+ public void testXMLDoubleDot()
+ {
+ IVariableNode node = getVariable("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");var b:XMLList = a..child;");
+ IASNode parentNode = node.getParent();
+ node = (IVariableNode) parentNode.getChild(1);
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {XMLList} */ b = a.descendants('child')");
+ }
+
+ @Test
+ public void testXMLAttribute()
+ {
+ IVariableNode node = getVariable("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");var b:XMLList = a.@attr1;");
+ IASNode parentNode = node.getParent();
+ node = (IVariableNode) parentNode.getChild(1);
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {XMLList} */ b = a.attribute('attr1')");
+ }
+
+ @Test
+ public void testXMLFilter()
+ {
+ IVariableNode node = getVariable("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");var b:XMLList = a..grandchild.(@attr2 == 'fish');");
+ IASNode parentNode = node.getParent();
+ node = (IVariableNode) parentNode.getChild(1);
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {XMLList} */ b = a.descendants('grandchild').filter(function(node){return (node.attribute('attr2') == 'fish')})");
+ }
+
+ @Test
++ public void testXMLFilterForChild()
++ {
++ IVariableNode node = getVariable("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");var b:XMLList = a..grandchild.(year == '2016');");
++ IASNode parentNode = node.getParent();
++ node = (IVariableNode) parentNode.getChild(1);
++ asBlockWalker.visitVariable(node);
++ assertOut("var /** @type {XMLList} */ b = a.descendants('grandchild').filter(function(node){return (node.child('year') == '2016')})");
++ }
++
++ @Test
++ public void testXMLFilterWithAttribute()
++ {
++ IBinaryOperatorNode node = (IBinaryOperatorNode)getNode("private var attribute:Function; private function test() {var a:XMLList; a = a.(attribute('name').length())};", IBinaryOperatorNode.class, WRAP_LEVEL_CLASS);
++ asBlockWalker.visitBinaryOperator(node);
++ assertOut("a = a.filter(function(node){return (node.attribute('name').length())})");
++ }
++
++ @Test
+ public void testXMLSetAttribute()
+ {
+ IBinaryOperatorNode node = getBinaryNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");a.@bar = 'foo'");
+ asBlockWalker.visitBinaryOperator(node);
+ assertOut("a.setAttribute('bar', 'foo')");
+ }
+
+ @Test
++ public void testXMLListSetAttribute()
++ {
++ IBinaryOperatorNode node = getBinaryNode("var a:XMLList;a[1].@bar = 'foo'");
++ asBlockWalker.visitBinaryOperator(node);
++ assertOut("a[1].setAttribute('bar', 'foo')");
++ }
++
++ @Test
++ public void testXMLListSetAttributeComplex()
++ {
++ IBinaryOperatorNode node = getBinaryNode("var a:XMLList;a.(@id==3).@height = '100px'");
++ asBlockWalker.visitBinaryOperator(node);
++ assertOut("a.filter(function(node){return (node.attribute('id') == 3)}).setAttribute('height', '100px')");
++ }
++
++ @Test
+ public void testXMLSetChild()
+ {
+ IBinaryOperatorNode node = getBinaryNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");a.foo = a.child");
+ asBlockWalker.visitBinaryOperator(node);
+ assertOut("a.setChild('foo', a.child('child'))");
+ }
+
+ @Test
+ public void testXMLListConcat()
+ {
+ IBinaryOperatorNode node = getBinaryNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");a.foo += a.child");
+ asBlockWalker.visitBinaryOperator(node);
+ assertOut("a.child('foo').concat(a.child('child'))");
+ }
+
+ @Test
++ public void testXMLListConcat2()
++ {
++ IBinaryOperatorNode node = getBinaryNode("var a:XMLList; var b:XMLList; a += b");
++ asBlockWalker.visitBinaryOperator(node);
++ assertOut("a.concat(b)");
++ }
++
++ @Test
+ public void testXMLListAddAndAssign()
+ {
+ IBinaryOperatorNode node = getBinaryNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");a.foo = a.child + a..grandchild");
+ asBlockWalker.visitBinaryOperator(node);
+ assertOut("a.setChild('foo', a.child('child').copy().concat(a.descendants('grandchild')))");
+ }
+
+ @Test
+ public void testXMLForLoop()
+ {
+ IForLoopNode node = getForLoopNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");for (var p:* in a) delete a[p];");
+ asBlockWalker.visitForLoop(node);
+ assertOut("for (var /** @type {*} */ p in a.elementNames())\n a.removeChild(p);");
+ }
+
+ @Test
+ public void testXMLForEachLoop()
+ {
+ IForLoopNode node = getForLoopNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");for each (var p:XMLList in a) var i:int = p.length();");
+ asBlockWalker.visitForLoop(node);
+ assertOut("var foreachiter0_target = a;\nfor (var foreachiter0 in foreachiter0_target.elementNames()) \n{\nvar p = foreachiter0_target.child(foreachiter0);\n\n var /** @type {number} */ i = p.length();}\n");
+ }
+
+ @Test
+ public void testNamespaceNoArg()
+ {
+ IVariableNode node = getVariable("var a:Namespace = new Namespace();");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {Namespace} */ a = new Namespace()");
+ }
+
+ @Test
+ public void testNamespaceOneArg()
+ {
+ IVariableNode node = getVariable("var a:Namespace = new Namespace('foo');");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {Namespace} */ a = new Namespace('foo')");
+ }
+
+ @Test
+ public void testNamespaceTwoArg()
+ {
+ IVariableNode node = getVariable("var a:Namespace = new Namespace('foo', 'bar');");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {Namespace} */ a = new Namespace('foo', 'bar')");
+ }
+
+ @Test
+ public void testQNameNoArg()
+ {
+ IVariableNode node = getVariable("var a:QName = new QName();");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {QName} */ a = new QName()");
+ }
+
+ @Test
+ public void testQNameTwoArg()
+ {
+ IVariableNode node = getVariable("var a:QName = new QName(new Namespace('foo'), 'bar');");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {QName} */ a = new QName(new Namespace('foo'), 'bar')");
+ }
+
+ @Test
+ public void testQNameOneArg()
+ {
+ IVariableNode node = getVariable("var a:QName = new QName(new QName(new Namespace('foo'), 'bar'));");
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {QName} */ a = new QName(new QName(new Namespace('foo'), 'bar'))");
+ }
+
+
+ @Test
+ public void testProxy()
+ {
+ IFunctionNode node = (IFunctionNode) getNode(
+ "import flash.utils.Proxy; public class B {public function b() { var a:Proxy = new Proxy();a.foo = 'bar'; }}",
+ IFunctionNode.class, WRAP_LEVEL_PACKAGE, true);
+ asBlockWalker.visitFunction(node);
+ assertOut("/**\n * @export\n */\nfoo.bar.B.prototype.b = function() {\n var /** @type {flash.utils.Proxy} */ a = new flash.utils.Proxy();\n a.setProperty('foo', 'bar');\n}");
+ }
+
+ @Test
+ public void testProxyGet()
+ {
+ IFunctionNode node = (IFunctionNode) getNode(
+ "import flash.utils.Proxy; public class B {public function b() { var a:Proxy = new Proxy();var bar:* = a.foo; }}",
+ IFunctionNode.class, WRAP_LEVEL_PACKAGE, true);
+ asBlockWalker.visitFunction(node);
+ assertOut("/**\n * @export\n */\nfoo.bar.B.prototype.b = function() {\n var /** @type {flash.utils.Proxy} */ a = new flash.utils.Proxy();\n var /** @type {*} */ bar = a.getProperty('foo');\n}");
+ }
+
+ @Test
+ public void testProxyConcat()
+ {
+ IFunctionNode node = (IFunctionNode) getNode(
+ "import flash.utils.Proxy; public class B {public function b() { var a:Proxy = new Proxy();var baz:String = a.foo + 'bar'; }}",
+ IFunctionNode.class, WRAP_LEVEL_PACKAGE, true);
+ asBlockWalker.visitFunction(node);
+ assertOut("/**\n * @export\n */\nfoo.bar.B.prototype.b = function() {\n var /** @type {flash.utils.Proxy} */ a = new flash.utils.Proxy();\n var /** @type {string} */ baz = a.getProperty('foo') + 'bar';\n}");
+ }
+
+ @Test
+ public void testProxyAddAndAssign()
+ {
+ IFunctionNode node = (IFunctionNode) getNode(
+ "import flash.utils.Proxy; public class B {public function b() { var a:Proxy = new Proxy();a.foo += 'bar'; }}",
+ IFunctionNode.class, WRAP_LEVEL_PACKAGE, true);
+ asBlockWalker.visitFunction(node);
+ assertOut("/**\n * @export\n */\nfoo.bar.B.prototype.b = function() {\n var /** @type {flash.utils.Proxy} */ a = new flash.utils.Proxy();\n a.setProperty('foo', a.getProperty('foo') + 'bar');\n}");
+ }
+
+ @Test
+ public void testProxyForLoop()
+ {
+ IForLoopNode node = (IForLoopNode) getNode(
+ "import flash.utils.Proxy; public class B {public function b() { var a:Proxy = new Proxy();for (var p:* in a) delete a[p];; }}",
+ IForLoopNode.class, WRAP_LEVEL_PACKAGE, true);
+ asBlockWalker.visitForLoop(node);
+ assertOut("for (var /** @type {*} */ p in a.propertyNames())\n a.deleteProperty(p);");
+ }
+
+ @Test
+ public void testProxyForEachLoop()
+ {
+ IForLoopNode node = (IForLoopNode) getNode(
+ "import flash.utils.Proxy; public class B {public function b() { var a:Proxy = new Proxy();for each (var p:String in a) var i:int = p.length; }}",
+ IForLoopNode.class, WRAP_LEVEL_PACKAGE, true);
+ asBlockWalker.visitForLoop(node);
+ assertOut("var foreachiter0_target = a;\nfor (var foreachiter0 in foreachiter0_target.propertyNames()) \n{\nvar p = foreachiter0_target.getProperty(foreachiter0);\n\n var /** @type {number} */ i = p.length;}\n");
+ }
+
+}
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/de070636/compiler-jx/src/test/resources/flexjs/projects/xml_requires/XMLRequire_result.js
----------------------------------------------------------------------
diff --cc compiler-jx/src/test/resources/flexjs/projects/xml_requires/XMLRequire_result.js
index d6affbe,0000000..3f8722a
mode 100644,000000..100644
--- a/compiler-jx/src/test/resources/flexjs/projects/xml_requires/XMLRequire_result.js
+++ b/compiler-jx/src/test/resources/flexjs/projects/xml_requires/XMLRequire_result.js
@@@ -1,74 -1,0 +1,74 @@@
+/**
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+/**
+ * XMLRequire
+ *
+ * @fileoverview
+ *
+ * @suppress {checkTypes|accessControls}
+ */
+
+goog.provide('XMLRequire');
+
+goog.require('XML');
+
+
+
+
+
+/**
+ * @constructor
+ */
+XMLRequire = function() {
- var /** @type {XML} */ myXML = new XML( '<node />') ;
++ var /** @type {XML} */ myXML = new XML( '<node />');
+};
+
+
+/**
+ * Metadata
+ *
+ * @type {Object.<string, Array.<Object>>}
+ */
+XMLRequire.prototype.FLEXJS_CLASS_INFO = { names: [{ name: 'XMLRequire', qName: 'XMLRequire'}] };
+
+
+/**
+ * Prevent renaming of class. Needed for reflection.
+ */
+goog.exportSymbol('XMLRequire', XMLRequire);
+
+
+
+/**
+ * Reflection
+ *
+ * @return {Object.<string, Function>}
+ */
+XMLRequire.prototype.FLEXJS_REFLECTION_INFO = function () {
+ return {
+ variables: function () {
+ return {
+ };
+ },
+ accessors: function () {
+ return {
+ };
+ },
+ methods: function () {
+ return {
+ 'XMLRequire': { type: '', declaredBy: 'XMLRequire'}
+ };
+ }
+ };
+};
[17/18] git commit: [flex-falcon]
[refs/heads/feature/maven-migration-test] - Merge branch 'develop' of
https://git-wip-us.apache.org/repos/asf/flex-falcon into
feature/maven-migration-test
Posted by cd...@apache.org.
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/de070636/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/jx/BinaryOperatorEmitter.java
----------------------------------------------------------------------
diff --cc compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/jx/BinaryOperatorEmitter.java
index 6e5cc75,0000000..aab9712
mode 100644,000000..100644
--- a/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/jx/BinaryOperatorEmitter.java
+++ b/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/jx/BinaryOperatorEmitter.java
@@@ -1,504 -1,0 +1,521 @@@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+package org.apache.flex.compiler.internal.codegen.js.jx;
+
+import org.apache.flex.compiler.codegen.ISubEmitter;
+import org.apache.flex.compiler.codegen.js.IJSEmitter;
+import org.apache.flex.compiler.definitions.IDefinition;
+import org.apache.flex.compiler.internal.codegen.as.ASEmitterTokens;
+import org.apache.flex.compiler.internal.codegen.js.JSSubEmitter;
+import org.apache.flex.compiler.internal.codegen.js.flexjs.JSFlexJSEmitter;
+import org.apache.flex.compiler.internal.codegen.js.flexjs.JSFlexJSEmitterTokens;
+import org.apache.flex.compiler.internal.definitions.AccessorDefinition;
+import org.apache.flex.compiler.internal.projects.FlexJSProject;
++import org.apache.flex.compiler.internal.tree.as.IdentifierNode;
+import org.apache.flex.compiler.internal.tree.as.MemberAccessExpressionNode;
+import org.apache.flex.compiler.internal.tree.as.UnaryOperatorAtNode;
+import org.apache.flex.compiler.projects.ICompilerProject;
+import org.apache.flex.compiler.tree.ASTNodeID;
+import org.apache.flex.compiler.tree.as.IASNode;
+import org.apache.flex.compiler.tree.as.IBinaryOperatorNode;
+import org.apache.flex.compiler.tree.as.IClassNode;
+import org.apache.flex.compiler.tree.as.IExpressionNode;
+import org.apache.flex.compiler.tree.as.IIdentifierNode;
+import org.apache.flex.compiler.utils.ASNodeUtils;
+
+public class BinaryOperatorEmitter extends JSSubEmitter implements
+ ISubEmitter<IBinaryOperatorNode>
+{
+
+ public BinaryOperatorEmitter(IJSEmitter emitter)
+ {
+ super(emitter);
+ }
+
+ @Override
+ public void emit(IBinaryOperatorNode node)
+ {
+ // TODO (mschmalle) will remove this cast as more things get abstracted
+ JSFlexJSEmitter fjs = (JSFlexJSEmitter) getEmitter();
+
+ ASTNodeID id = node.getNodeID();
+ /*
+ if (id == ASTNodeID.Op_InID
+ || id == ASTNodeID.Op_LogicalAndAssignID
+ || id == ASTNodeID.Op_LogicalOrAssignID)
+ {
+ super.emitBinaryOperator(node);
+ }
+ else */if (id == ASTNodeID.Op_IsID || id == ASTNodeID.Op_AsID)
+ {
+ fjs.emitIsAs(node, node.getLeftOperandNode(), node.getRightOperandNode(),
+ id, false);
+ }
+ else if (id == ASTNodeID.Op_InstanceOfID)
+ {
+ getWalker().walk(node.getLeftOperandNode());
+
+ startMapping(node, node.getLeftOperandNode());
+ write(ASEmitterTokens.SPACE);
+ writeToken(ASEmitterTokens.INSTANCEOF);
+ endMapping(node);
+
+ IDefinition dnode = (node.getRightOperandNode())
+ .resolve(getProject());
+ if (dnode != null)
+ write(getEmitter()
+ .formatQualifiedName(dnode.getQualifiedName()));
+ else
+ getWalker().walk(node.getRightOperandNode());
+ }
+ else
+ {
+ IExpressionNode leftSide = node.getLeftOperandNode();
+ if (leftSide.getNodeID() == ASTNodeID.MemberAccessExpressionID)
+ {
+ IASNode lnode = leftSide.getChild(0);
+ IASNode rnode = leftSide.getChild(1);
+ IDefinition rnodeDef = (rnode instanceof IIdentifierNode) ?
+ ((IIdentifierNode) rnode).resolve(getWalker().getProject()) :
+ null;
+ if (lnode.getNodeID() == ASTNodeID.SuperID
+ && rnodeDef instanceof AccessorDefinition)
+ {
+ String op = node.getOperator().getOperatorText();
+ boolean isAssignment = op.contains("=")
+ && !op.contains("==")
+ && !(op.startsWith("<") || op.startsWith(">") || op
+ .startsWith("!"));
+ if (isAssignment)
+ {
+ ICompilerProject project = this.getProject();
+ if (project instanceof FlexJSProject)
+ ((FlexJSProject)project).needLanguage = true;
+
+ write(JSFlexJSEmitterTokens.LANGUAGE_QNAME);
+ write(ASEmitterTokens.MEMBER_ACCESS);
+ write(JSFlexJSEmitterTokens.SUPERSETTER);
+ write(ASEmitterTokens.PAREN_OPEN);
+ IClassNode cnode = (IClassNode) node
+ .getAncestorOfType(IClassNode.class);
+ write(getEmitter().formatQualifiedName(
+ cnode.getQualifiedName()));
+ writeToken(ASEmitterTokens.COMMA);
+ write(ASEmitterTokens.THIS);
+ writeToken(ASEmitterTokens.COMMA);
+ write(ASEmitterTokens.SINGLE_QUOTE);
+ write(rnodeDef.getBaseName());
+ write(ASEmitterTokens.SINGLE_QUOTE);
+ writeToken(ASEmitterTokens.COMMA);
+
+ if (op.length() > 1) // += and things like that
+ {
+ write(JSFlexJSEmitterTokens.LANGUAGE_QNAME);
+ write(ASEmitterTokens.MEMBER_ACCESS);
+ write(JSFlexJSEmitterTokens.SUPERSETTER);
+ write(ASEmitterTokens.PAREN_OPEN);
+ write(getEmitter().formatQualifiedName(
+ cnode.getQualifiedName()));
+ writeToken(ASEmitterTokens.COMMA);
+ write(ASEmitterTokens.THIS);
+ writeToken(ASEmitterTokens.COMMA);
+ write(ASEmitterTokens.SINGLE_QUOTE);
+ write(rnodeDef.getBaseName());
+ write(ASEmitterTokens.SINGLE_QUOTE);
+ write(ASEmitterTokens.PAREN_CLOSE);
+ write(op.substring(0, 1));
+ }
+
+ getWalker().walk(node.getRightOperandNode());
+ write(ASEmitterTokens.PAREN_CLOSE);
+ return;
+ }
+ }
+ else if (((JSFlexJSEmitter)getEmitter()).isXMLList((MemberAccessExpressionNode)leftSide))
+ {
+ MemberAccessExpressionNode xmlNode = (MemberAccessExpressionNode)leftSide;
+ if (node.getNodeID() == ASTNodeID.Op_AssignId)
+ {
+ getWalker().walk(xmlNode.getLeftOperandNode());
+ IExpressionNode rightSide = xmlNode.getRightOperandNode();
+ if (rightSide instanceof UnaryOperatorAtNode)
+ {
+ write(".setAttribute('");
+ getWalker().walk(((UnaryOperatorAtNode)rightSide).getChild(0));
+ }
+ else
+ {
+ write(".setChild('");
+ getWalker().walk(rightSide);
+ }
+ write("', ");
+ getWalker().walk(node.getRightOperandNode());
+ write(ASEmitterTokens.PAREN_CLOSE);
+ return;
+ }
+ else if (node.getNodeID() == ASTNodeID.Op_AddAssignID)
+ {
+ getWalker().walk(xmlNode);
+ write(".concat(");
+ getWalker().walk(node.getRightOperandNode());
+ write(ASEmitterTokens.PAREN_CLOSE);
+ return;
+ }
+ else if (node.getNodeID() == ASTNodeID.Op_AddID)
+ {
+ getWalker().walk(xmlNode);
+ write(".copy().concat(");
+ getWalker().walk(node.getRightOperandNode());
+ write(ASEmitterTokens.PAREN_CLOSE);
+ return;
+ }
+ }
+ else if (((JSFlexJSEmitter)getEmitter()).isProxy((MemberAccessExpressionNode)leftSide))
+ {
+ MemberAccessExpressionNode proxyNode = (MemberAccessExpressionNode)leftSide;
+ if (node.getNodeID() == ASTNodeID.Op_AssignId)
+ {
+ getWalker().walk(proxyNode.getLeftOperandNode());
+ IExpressionNode rightSide = proxyNode.getRightOperandNode();
+ write(".setProperty('");
+ getWalker().walk(rightSide);
+ write("', ");
+ getWalker().walk(node.getRightOperandNode());
+ write(ASEmitterTokens.PAREN_CLOSE);
+ return;
+ }
+ else if (node.getNodeID() == ASTNodeID.Op_AddAssignID)
+ {
+ IExpressionNode rightSide = proxyNode.getRightOperandNode();
+ getWalker().walk(proxyNode.getLeftOperandNode());
+ write(".setProperty('");
+ getWalker().walk(rightSide);
+ write("', ");
+ getWalker().walk(proxyNode.getLeftOperandNode());
+ write(".getProperty(");
+ write(ASEmitterTokens.SINGLE_QUOTE);
+ getWalker().walk(rightSide);
+ write(ASEmitterTokens.SINGLE_QUOTE);
+ write(ASEmitterTokens.PAREN_CLOSE);
+ write(" + ");
+ getWalker().walk(node.getRightOperandNode());
+ write(ASEmitterTokens.PAREN_CLOSE);
+ return;
+ }
+ }
+ else if (((JSFlexJSEmitter)getEmitter()).isDateProperty((MemberAccessExpressionNode)leftSide))
+ {
+ specialCaseDate(node, (MemberAccessExpressionNode)leftSide);
+ return;
+ }
+ }
++ else if (leftSide.getNodeID() == ASTNodeID.IdentifierID)
++ {
++ IDefinition leftDef = leftSide.resolveType(getWalker().getProject());
++ if ((leftDef != null)
++ && IdentifierNode.isXMLish(leftDef, getWalker().getProject()))
++ {
++ if (node.getNodeID() == ASTNodeID.Op_AddAssignID)
++ {
++ getWalker().walk(leftSide);
++ write(".concat(");
++ getWalker().walk(node.getRightOperandNode());
++ write(ASEmitterTokens.PAREN_CLOSE);
++ return;
++ }
++ }
++ }
+
+ super_emitBinaryOperator(node);
+ /*
+ IExpressionNode leftSide = node.getLeftOperandNode();
+
+ IExpressionNode property = null;
+ int leftSideChildCount = leftSide.getChildCount();
+ if (leftSideChildCount > 0)
+ {
+ IASNode childNode = leftSide.getChild(leftSideChildCount - 1);
+ if (childNode instanceof IExpressionNode)
+ property = (IExpressionNode) childNode;
+ else
+ property = leftSide;
+ }
+ else
+ property = leftSide;
+
+ IDefinition def = null;
+ if (property instanceof IIdentifierNode)
+ def = ((IIdentifierNode) property).resolve(getWalker()
+ .getProject());
+
+ boolean isSuper = false;
+ if (leftSide.getNodeID() == ASTNodeID.MemberAccessExpressionID)
+ {
+ IASNode cnode = leftSide.getChild(0);
+ ASTNodeID cId = cnode.getNodeID();
+
+ isSuper = cId == ASTNodeID.SuperID;
+ }
+
+ String op = node.getOperator().getOperatorText();
+ boolean isAssignment = op.contains("=") && !op.contains("==") &&
+ !(op.startsWith("<") ||
+ op.startsWith(">") ||
+ op.startsWith("!"));
+
+ if (def instanceof AccessorDefinition && isAssignment)
+ {
+ // this will make the set_foo call
+ getWalker().walk(leftSide);
+ }
+ else if (isSuper)
+ {
+ emitSuperCall(node, "");
+ }
+ else
+ {
+ if (ASNodeUtils.hasParenOpen(node))
+ write(ASEmitterTokens.PAREN_OPEN);
+
+ getWalker().walk(leftSide);
+
+ if (node.getNodeID() != ASTNodeID.Op_CommaID)
+ write(ASEmitterTokens.SPACE);
+
+ writeToken(node.getOperator().getOperatorText());
+
+ getWalker().walk(node.getRightOperandNode());
+
+ if (ASNodeUtils.hasParenClose(node))
+ write(ASEmitterTokens.PAREN_CLOSE);
+ }
+ */
+ }
+ }
+
+ private void super_emitBinaryOperator(IBinaryOperatorNode node)
+ {
+ if (ASNodeUtils.hasParenOpen(node))
+ write(ASEmitterTokens.PAREN_OPEN);
+
+ ASTNodeID id = node.getNodeID();
+
+ if (id == ASTNodeID.Op_IsID)
+ {
+ write(ASEmitterTokens.IS);
+ write(ASEmitterTokens.PAREN_OPEN);
+ getWalker().walk(node.getLeftOperandNode());
+ writeToken(ASEmitterTokens.COMMA);
+ getWalker().walk(node.getRightOperandNode());
+ write(ASEmitterTokens.PAREN_CLOSE);
+ }
+ else if (id == ASTNodeID.Op_AsID)
+ {
+ // (is(a, b) ? a : null)
+ write(ASEmitterTokens.PAREN_OPEN);
+ write(ASEmitterTokens.IS);
+ write(ASEmitterTokens.PAREN_OPEN);
+ getWalker().walk(node.getLeftOperandNode());
+ writeToken(ASEmitterTokens.COMMA);
+ getWalker().walk(node.getRightOperandNode());
+ writeToken(ASEmitterTokens.PAREN_CLOSE);
+ writeToken(ASEmitterTokens.TERNARY);
+ getWalker().walk(node.getLeftOperandNode());
+ write(ASEmitterTokens.SPACE);
+ writeToken(ASEmitterTokens.COLON);
+ write(ASEmitterTokens.NULL);
+ write(ASEmitterTokens.PAREN_CLOSE);
+ }
+ else
+ {
+ getWalker().walk(node.getLeftOperandNode());
+
+ startMapping(node, node.getLeftOperandNode());
+
+ if (id != ASTNodeID.Op_CommaID)
+ write(ASEmitterTokens.SPACE);
+
+ // (erikdebruin) rewrite 'a &&= b' to 'a = a && b'
+ if (id == ASTNodeID.Op_LogicalAndAssignID
+ || id == ASTNodeID.Op_LogicalOrAssignID)
+ {
+ IIdentifierNode lnode = (IIdentifierNode) node
+ .getLeftOperandNode();
+
+ writeToken(ASEmitterTokens.EQUAL);
+ endMapping(node);
+ write(lnode.getName());
+
+ startMapping(node, node.getLeftOperandNode());
+ write(ASEmitterTokens.SPACE);
+ write((id == ASTNodeID.Op_LogicalAndAssignID) ? ASEmitterTokens.LOGICAL_AND
+ : ASEmitterTokens.LOGICAL_OR);
+ }
+ else
+ {
+ write(node.getOperator().getOperatorText());
+ }
+
+ write(ASEmitterTokens.SPACE);
+ endMapping(node);
+
+ /*
+ IDefinition definition = node.getRightOperandNode().resolve(getProject());
+ if (definition instanceof FunctionDefinition &&
+ (!(definition instanceof AccessorDefinition)))
+ {
+ }
+ else */
+ getWalker().walk(node.getRightOperandNode());
+ if (node.getNodeID() == ASTNodeID.Op_InID &&
+ ((JSFlexJSEmitter)getEmitter()).isXML(node.getRightOperandNode()))
+ {
+ write(".elementNames()");
+ }
+ else if (node.getNodeID() == ASTNodeID.Op_InID &&
+ ((JSFlexJSEmitter)getEmitter()).isProxy(node.getRightOperandNode()))
+ {
+ write(".propertyNames()");
+ }
+ }
+
+ if (ASNodeUtils.hasParenOpen(node))
+ write(ASEmitterTokens.PAREN_CLOSE);
+ }
+
+ private enum DateProperties
+ {
+ FULLYEAR("fullYear", "setFullYear"),
+ MONTH("month", "setMonth"),
+ DATE("date", "setDate"),
+ FULLYEARUTC("fullYearUTC", "setUTCFullYear"),
+ MONTHUTC("monthUTC", "setUTCMonth"),
+ DATEUTC("dateUTC", "setUTCDate"),
+ HOURS("hours", "setHours"),
+ MINUTES("minutes", "setMinutes"),
+ SECONDS("seconds", "setSeconds"),
+ MILLISECONDS("milliseconds", "setMilliseconds"),
+ HOURSUTC("hoursUTC", "setUTCHours"),
+ MINUTESUTC("minutesUTC", "setUTCMinutes"),
+ SECONDSUTC("secondsUTC", "setUTCSeconds"),
+ MILLISECONDSUTC("millisecondsUTC", "setUTCMilliseconds");
+
+ DateProperties(String value, String functionName)
+ {
+ this.value = value;
+ this.functionName = functionName;
+ }
+
+ private String value;
+ private String functionName;
+
+ public String getFunctionName()
+ {
+ return functionName;
+ }
+ }
+
+ void specialCaseDate(IBinaryOperatorNode node, MemberAccessExpressionNode leftSide)
+ {
+ MemberAccessExpressionNode dateNode = (MemberAccessExpressionNode)leftSide;
+ IIdentifierNode rightSide = (IIdentifierNode)dateNode.getRightOperandNode();
+ getWalker().walk(dateNode.getLeftOperandNode());
+ String rightName = rightSide.getName();
+ DateProperties prop = DateProperties.valueOf(rightName.toUpperCase());
+ write(ASEmitterTokens.MEMBER_ACCESS);
+ write(prop.getFunctionName());
+ write(ASEmitterTokens.PAREN_OPEN);
+ getWalker().walk(node.getRightOperandNode());
+ switch (prop)
+ {
+ case FULLYEAR:
+ write(ASEmitterTokens.COMMA);
+ write(ASEmitterTokens.SPACE);
+ getWalker().walk(dateNode.getLeftOperandNode());
+ write(ASEmitterTokens.MEMBER_ACCESS);
+ write("getMonth()");
+ // fall through
+ case MONTH:
+ write(ASEmitterTokens.COMMA);
+ write(ASEmitterTokens.SPACE);
+ getWalker().walk(dateNode.getLeftOperandNode());
+ write(ASEmitterTokens.MEMBER_ACCESS);
+ write("getDate()");
+ break;
+ case FULLYEARUTC:
+ write(ASEmitterTokens.COMMA);
+ write(ASEmitterTokens.SPACE);
+ getWalker().walk(dateNode.getLeftOperandNode());
+ write(ASEmitterTokens.MEMBER_ACCESS);
+ write("getMonthUTC()");
+ // fall through
+ case MONTHUTC:
+ write(ASEmitterTokens.COMMA);
+ write(ASEmitterTokens.SPACE);
+ getWalker().walk(dateNode.getLeftOperandNode());
+ write(ASEmitterTokens.MEMBER_ACCESS);
+ write("getDateUTC()");
+ break;
+ case HOURS:
+ write(ASEmitterTokens.COMMA);
+ write(ASEmitterTokens.SPACE);
+ getWalker().walk(dateNode.getLeftOperandNode());
+ write(ASEmitterTokens.MEMBER_ACCESS);
+ write("getMinutes()");
+ // fall through
+ case MINUTES:
+ write(ASEmitterTokens.COMMA);
+ write(ASEmitterTokens.SPACE);
+ getWalker().walk(dateNode.getLeftOperandNode());
+ write(ASEmitterTokens.MEMBER_ACCESS);
+ write("getSeconds()");
+ // fall through
+ case SECONDS:
+ write(ASEmitterTokens.COMMA);
+ write(ASEmitterTokens.SPACE);
+ getWalker().walk(dateNode.getLeftOperandNode());
+ write(ASEmitterTokens.MEMBER_ACCESS);
+ write("getMilliseconds()");
+ break;
+ case HOURSUTC:
+ write(ASEmitterTokens.COMMA);
+ write(ASEmitterTokens.SPACE);
+ getWalker().walk(dateNode.getLeftOperandNode());
+ write(ASEmitterTokens.MEMBER_ACCESS);
+ write("getUTCMinutes()");
+ // fall through
+ case MINUTESUTC:
+ write(ASEmitterTokens.COMMA);
+ write(ASEmitterTokens.SPACE);
+ getWalker().walk(dateNode.getLeftOperandNode());
+ write(ASEmitterTokens.MEMBER_ACCESS);
+ write("getUTCSeconds()");
+ // fall through
+ case SECONDSUTC:
+ write(ASEmitterTokens.COMMA);
+ write(ASEmitterTokens.SPACE);
+ getWalker().walk(dateNode.getLeftOperandNode());
+ write(ASEmitterTokens.MEMBER_ACCESS);
+ write("getUTCMilliseconds()");
+ break;
+ }
+ write(ASEmitterTokens.PAREN_CLOSE);
+ }
+}
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/de070636/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/jx/IdentifierEmitter.java
----------------------------------------------------------------------
diff --cc compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/jx/IdentifierEmitter.java
index 0d91fcf,0000000..24df201
mode 100644,000000..100644
--- a/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/jx/IdentifierEmitter.java
+++ b/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/jx/IdentifierEmitter.java
@@@ -1,257 -1,0 +1,271 @@@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+package org.apache.flex.compiler.internal.codegen.js.jx;
+
+import org.apache.flex.compiler.codegen.ISubEmitter;
+import org.apache.flex.compiler.codegen.js.IJSEmitter;
+import org.apache.flex.compiler.definitions.IDefinition;
+import org.apache.flex.compiler.definitions.IFunctionDefinition;
+import org.apache.flex.compiler.definitions.IFunctionDefinition.FunctionClassification;
+import org.apache.flex.compiler.definitions.IVariableDefinition;
+import org.apache.flex.compiler.definitions.IVariableDefinition.VariableClassification;
+import org.apache.flex.compiler.internal.codegen.as.ASEmitterTokens;
+import org.apache.flex.compiler.internal.codegen.js.JSSubEmitter;
+import org.apache.flex.compiler.internal.codegen.js.goog.JSGoogEmitterTokens;
+import org.apache.flex.compiler.internal.codegen.js.utils.EmitterUtils;
+import org.apache.flex.compiler.internal.definitions.AccessorDefinition;
+import org.apache.flex.compiler.internal.definitions.FunctionDefinition;
+import org.apache.flex.compiler.internal.definitions.TypeDefinitionBase;
+import org.apache.flex.compiler.internal.tree.as.NonResolvingIdentifierNode;
+import org.apache.flex.compiler.tree.ASTNodeID;
+import org.apache.flex.compiler.tree.as.IASNode;
++import org.apache.flex.compiler.tree.as.IBinaryOperatorNode;
+import org.apache.flex.compiler.tree.as.IFunctionObjectNode;
+import org.apache.flex.compiler.tree.as.IIdentifierNode;
+import org.apache.flex.compiler.tree.as.IMemberAccessExpressionNode;
+import org.apache.flex.compiler.utils.NativeUtils;
+
+public class IdentifierEmitter extends JSSubEmitter implements
+ ISubEmitter<IIdentifierNode>
+{
+
+ public IdentifierEmitter(IJSEmitter emitter)
+ {
+ super(emitter);
+ }
+
+ @Override
+ public void emit(IIdentifierNode node)
+ {
+ if (node instanceof NonResolvingIdentifierNode)
+ {
+ startMapping(node);
+ write(node.getName());
+ endMapping(node);
+ return;
+ }
+ IDefinition nodeDef = ((IIdentifierNode) node).resolve(getProject());
+
+ IASNode parentNode = node.getParent();
+ ASTNodeID parentNodeId = parentNode.getNodeID();
++ IASNode grandparentNode = parentNode.getParent();
++ ASTNodeID grandparentNodeId = (parentNode != null) ? grandparentNode.getNodeID() : null;
+
+ boolean identifierIsAccessorFunction = nodeDef instanceof AccessorDefinition;
+ boolean identifierIsPlainFunction = nodeDef instanceof FunctionDefinition
+ && !identifierIsAccessorFunction;
+ boolean emitName = true;
+
+ if (nodeDef != null && nodeDef.isStatic())
+ {
+ String sname = nodeDef.getParent().getQualifiedName();
+ if (sname.equals("Array"))
+ {
+ String baseName = nodeDef.getBaseName();
+ if (baseName.equals("CASEINSENSITIVE"))
+ {
+ write("1");
+ return;
+ }
+ else if (baseName.equals("DESCENDING"))
+ {
+ write("2");
+ return;
+ }
+ else if (baseName.equals("UNIQUESORT"))
+ {
+ write("4");
+ return;
+ }
+ else if (baseName.equals("RETURNINDEXEDARRAY"))
+ {
+ write("8");
+ return;
+ }
+ else if (baseName.equals("NUMERIC"))
+ {
+ write("16");
+ return;
+ }
+ }
+ else if (sname.equals("int"))
+ {
+ String baseName = nodeDef.getBaseName();
+ if (baseName.equals("MAX_VALUE"))
+ {
+ write("2147483648");
+ return;
+ }
+ else if (baseName.equals("MIN_VALUE"))
+ {
+ write("-2147483648");
+ return;
+ }
+ }
+ else if (sname.equals("uint"))
+ {
+ String baseName = nodeDef.getBaseName();
+ if (baseName.equals("MAX_VALUE"))
+ {
+ write("4294967295");
+ return;
+ }
+ else if (baseName.equals("MIN_VALUE"))
+ {
+ write("0");
+ return;
+ }
+ }
+ if (sname.length() > 0)
+ {
+ write(getEmitter().formatQualifiedName(sname));
+ write(ASEmitterTokens.MEMBER_ACCESS);
+ }
+ }
+ else if (!NativeUtils.isNative(node.getName()))
+ {
+ boolean identifierIsLocalOrInstanceFunctionAsValue = false;
+ if (identifierIsPlainFunction)
+ {
+ FunctionClassification fc = ((FunctionDefinition)nodeDef).getFunctionClassification();
+ identifierIsLocalOrInstanceFunctionAsValue =
+ (fc == FunctionClassification.LOCAL || fc == FunctionClassification.CLASS_MEMBER) &&
+ // not a value if parent is a function call or member access expression
+ (!(parentNodeId == ASTNodeID.MemberAccessExpressionID || parentNodeId == ASTNodeID.FunctionCallID));
+
+ }
+ // an instance method as a parameter or
+ // a local function
+ boolean generateClosure = (parentNodeId == ASTNodeID.ContainerID
+ && identifierIsPlainFunction && ((FunctionDefinition) nodeDef)
+ .getFunctionClassification() == FunctionClassification.CLASS_MEMBER)
+ || identifierIsLocalOrInstanceFunctionAsValue;
+
+ if (generateClosure)
+ {
+ getEmitter().emitClosureStart();
+ }
+
+ if (EmitterUtils.writeThis(getProject(), getModel(), node))
+ {
+ IFunctionObjectNode functionObjectNode = (IFunctionObjectNode) node
+ .getParent().getAncestorOfType(
+ IFunctionObjectNode.class);
+
++ startMapping(node);
+ if (functionObjectNode != null)
+ write(JSGoogEmitterTokens.SELF);
+ else
+ write(ASEmitterTokens.THIS);
+
+ write(ASEmitterTokens.MEMBER_ACCESS);
++ endMapping(node);
+ }
+
+ if (generateClosure)
+ {
+ write(node.getName());
+
+ writeToken(ASEmitterTokens.COMMA);
+ write(ASEmitterTokens.THIS);
+ getEmitter().emitClosureEnd(node);
+ emitName = false;
+ }
+ }
+
+ //IDefinition parentDef = (nodeDef != null) ? nodeDef.getParent() : null;
+ //boolean isNative = (parentDef != null)
+ // && NativeUtils.isNative(parentDef.getBaseName());
+ if (emitName)
+ {
+ if (nodeDef != null)
+ {
+ // this can be optimized but this way lets
+ // us breakpoint on the node.getName() to make
+ // sure it is ok to always use the short name in an MAE
+ String qname = nodeDef.getQualifiedName();
+ boolean isPackageOrFileMember = false;
+ if (nodeDef instanceof IVariableDefinition)
+ {
+ IVariableDefinition variable = (IVariableDefinition) nodeDef;
+ VariableClassification classification = variable.getVariableClassification();
+ if (classification == VariableClassification.PACKAGE_MEMBER ||
+ classification == VariableClassification.FILE_MEMBER)
+ {
+ isPackageOrFileMember = true;
+ }
+ }
+ else if (nodeDef instanceof IFunctionDefinition)
+ {
+ IFunctionDefinition func = (IFunctionDefinition) nodeDef;
+ FunctionClassification classification = func.getFunctionClassification();
+ if (classification == FunctionClassification.PACKAGE_MEMBER ||
+ classification == FunctionClassification.FILE_MEMBER)
+ {
+ isPackageOrFileMember = true;
+ }
+ }
+ boolean needsFormattedName = false;
+ if (isPackageOrFileMember && parentNodeId == ASTNodeID.MemberAccessExpressionID)
+ {
+ IMemberAccessExpressionNode parentMemberAccessNode = (IMemberAccessExpressionNode) parentNode;
+ //if the package or file member isn't on the left side of a
+ //member access expression, it shouldn't be fully qualified
+ needsFormattedName = parentMemberAccessNode.getLeftOperandNode() == node;
+ }
+ startMapping(node);
+ if (parentNodeId == ASTNodeID.MemberAccessExpressionID)
+ {
+ if (needsFormattedName)
+ {
+ write(getEmitter().formatQualifiedName(qname));
+ }
+ else
+ {
+ write(node.getName());
+ }
+ }
+ else if (isPackageOrFileMember)
+ write(getEmitter().formatQualifiedName(qname));
+ else if (nodeDef instanceof TypeDefinitionBase)
+ write(getEmitter().formatQualifiedName(qname));
+ else
+ write(qname);
+ endMapping(node);
+ }
++ else if (grandparentNodeId == ASTNodeID.E4XFilterID &&
++ (!(parentNodeId == ASTNodeID.MemberAccessExpressionID || parentNodeId == ASTNodeID.Op_DescendantsID)))
++ {
++ startMapping(node);
++ write("child('");
++ write(node.getName());
++ write("')");
++ endMapping(node);
++ }
+ else
+ {
+ startMapping(node);
+ write(node.getName());
+ endMapping(node);
+ }
+ }
+ }
+
+}
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/de070636/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/jx/LiteralEmitter.java
----------------------------------------------------------------------
diff --cc compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/jx/LiteralEmitter.java
index 70d2c48,0000000..068d870
mode 100644,000000..100644
--- a/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/jx/LiteralEmitter.java
+++ b/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/jx/LiteralEmitter.java
@@@ -1,134 -1,0 +1,136 @@@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+package org.apache.flex.compiler.internal.codegen.js.jx;
+
+import org.apache.flex.compiler.codegen.ISubEmitter;
+import org.apache.flex.compiler.codegen.js.IJSEmitter;
+import org.apache.flex.compiler.internal.codegen.as.ASEmitterTokens;
+import org.apache.flex.compiler.internal.codegen.js.JSSubEmitter;
+import org.apache.flex.compiler.internal.tree.as.IdentifierNode;
+import org.apache.flex.compiler.internal.tree.as.LiteralNode;
+import org.apache.flex.compiler.internal.tree.as.RegExpLiteralNode;
+import org.apache.flex.compiler.internal.tree.as.XMLLiteralNode;
+import org.apache.flex.compiler.tree.as.IASNode;
+import org.apache.flex.compiler.tree.as.ILiteralNode;
+import org.apache.flex.compiler.tree.as.ILiteralNode.LiteralType;
+
+public class LiteralEmitter extends JSSubEmitter implements
+ ISubEmitter<ILiteralNode>
+{
+
+ public LiteralEmitter(IJSEmitter emitter)
+ {
+ super(emitter);
+ }
+
+ @Override
+ public void emit(ILiteralNode node)
+ {
+ boolean isWritten = false;
+
++ String newlineReplacement = "\\\\n";
+ String s = node.getValue(true);
+ if (!(node instanceof RegExpLiteralNode))
+ {
+ if (node.getLiteralType() == LiteralType.XML)
+ {
- write("new XML");
- writeToken(ASEmitterTokens.PAREN_OPEN);
++ newlineReplacement = "\\\\\n";
+ XMLLiteralNode xmlNode = (XMLLiteralNode)node;
+ if (xmlNode.getContentsNode().getChildCount() == 1)
+ {
+ if (s.contains("'"))
- write("\"" + s + "\"");
++ s = "\"" + s + "\"";
+ else
- write("'" + s + "'");
- isWritten = true;
++ s = "'" + s + "'";
++ s = "new XML( " + s + ")";
+ }
+ else
+ {
++ StringBuilder sb = new StringBuilder();
++ sb.append("new XML( ");
+ // probably contains {initializers}
+ int n = xmlNode.getContentsNode().getChildCount();
+ for (int i = 0; i < n; i++)
+ {
+ if (i > 0)
- write(" + ");
++ sb.append(" + ");
+ IASNode child = xmlNode.getContentsNode().getChild(i);
+ if (child instanceof LiteralNode)
+ {
+ s = ((LiteralNode)child).getValue(true);
+ if (s.contains("'"))
- write("\"" + s + "\"");
++ sb.append("\"" + s + "\"");
+ else
- write("'" + s + "'");
- isWritten = true;
++ sb.append("'" + s + "'");
+ }
+ else if (child instanceof IdentifierNode)
+ {
+ s = getEmitter().stringifyNode(child);
- write(s);
++ sb.append(s);
+ }
+ }
++ sb.append(")");
++ s = sb.toString();
+ }
- writeToken(ASEmitterTokens.PAREN_CLOSE);
+ }
+ s = s.replaceAll("\n", "__NEWLINE_PLACEHOLDER__");
+ s = s.replaceAll("\r", "__CR_PLACEHOLDER__");
+ s = s.replaceAll("\t", "__TAB_PLACEHOLDER__");
+ s = s.replaceAll("\f", "__FORMFEED_PLACEHOLDER__");
+ s = s.replaceAll("\b", "__BACKSPACE_PLACEHOLDER__");
+ s = s.replaceAll("\\\\\"", "__QUOTE_PLACEHOLDER__");
+ s = s.replaceAll("\\\\", "__ESCAPE_PLACEHOLDER__");
+ //s = "\'" + s.replaceAll("\'", "\\\\\'") + "\'";
+ s = s.replaceAll("__ESCAPE_PLACEHOLDER__", "\\\\\\\\");
+ s = s.replaceAll("__QUOTE_PLACEHOLDER__", "\\\\\"");
+ s = s.replaceAll("__BACKSPACE_PLACEHOLDER__", "\\\\b");
+ s = s.replaceAll("__FORMFEED_PLACEHOLDER__", "\\\\f");
+ s = s.replaceAll("__TAB_PLACEHOLDER__", "\\\\t");
+ s = s.replaceAll("__CR_PLACEHOLDER__", "\\\\r");
- s = s.replaceAll("__NEWLINE_PLACEHOLDER__", "\\\\n");
++ s = s.replaceAll("__NEWLINE_PLACEHOLDER__", newlineReplacement);
+ if (node.getLiteralType() == LiteralType.STRING)
+ {
+ char c = s.charAt(0);
+ if (c == '"')
+ {
+ s = s.substring(1, s.length() - 1);
+ s = s.replace("\"", "\\\"");
+ s = "\"" + s + "\"";
+ }
+ else if (c == '\'')
+ {
+ s = s.substring(1, s.length() - 1);
+ s = s.replace("'", "\\'");
+ s = "'" + s + "'";
+ }
+ s = s.replace("\u2028", "\\u2028");
+ s = s.replace("\u2029", "\\u2029");
+ }
+
+ }
+
+ if (!isWritten)
+ {
+ startMapping(node);
+ write(s);
+ endMapping(node);
+ }
+ }
+}
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/de070636/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/utils/EmitterUtils.java
----------------------------------------------------------------------
diff --cc compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/utils/EmitterUtils.java
index ebe21ee,0000000..1180476
mode 100644,000000..100644
--- a/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/utils/EmitterUtils.java
+++ b/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/js/utils/EmitterUtils.java
@@@ -1,513 -1,0 +1,525 @@@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+package org.apache.flex.compiler.internal.codegen.js.utils;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import org.apache.flex.compiler.constants.IASLanguageConstants;
+import org.apache.flex.compiler.definitions.IClassDefinition;
+import org.apache.flex.compiler.definitions.IDefinition;
+import org.apache.flex.compiler.definitions.IFunctionDefinition;
+import org.apache.flex.compiler.definitions.IFunctionDefinition.FunctionClassification;
+import org.apache.flex.compiler.definitions.INamespaceDefinition;
+import org.apache.flex.compiler.definitions.ITypeDefinition;
+import org.apache.flex.compiler.definitions.IVariableDefinition;
+import org.apache.flex.compiler.internal.codegen.js.JSSessionModel;
+import org.apache.flex.compiler.internal.definitions.AccessorDefinition;
+import org.apache.flex.compiler.internal.definitions.ClassDefinition;
+import org.apache.flex.compiler.internal.definitions.FunctionDefinition;
+import org.apache.flex.compiler.internal.definitions.ParameterDefinition;
+import org.apache.flex.compiler.internal.definitions.VariableDefinition;
+import org.apache.flex.compiler.internal.projects.CompilerProject;
+import org.apache.flex.compiler.internal.scopes.TypeScope;
+import org.apache.flex.compiler.internal.tree.as.ContainerNode;
+import org.apache.flex.compiler.internal.tree.as.NodeBase;
+import org.apache.flex.compiler.internal.tree.as.ParameterNode;
+import org.apache.flex.compiler.projects.ICompilerProject;
+import org.apache.flex.compiler.tree.ASTNodeID;
+import org.apache.flex.compiler.tree.as.IASNode;
+import org.apache.flex.compiler.tree.as.IClassNode;
+import org.apache.flex.compiler.tree.as.IContainerNode;
+import org.apache.flex.compiler.tree.as.IDefinitionNode;
+import org.apache.flex.compiler.tree.as.IExpressionNode;
+import org.apache.flex.compiler.tree.as.IFunctionNode;
+import org.apache.flex.compiler.tree.as.IIdentifierNode;
+import org.apache.flex.compiler.tree.as.IPackageNode;
+import org.apache.flex.compiler.tree.as.IParameterNode;
+import org.apache.flex.compiler.tree.as.IScopedNode;
+import org.apache.flex.compiler.tree.as.ITypeNode;
+import org.apache.flex.compiler.tree.as.IVariableNode;
+import org.apache.flex.compiler.utils.NativeUtils;
+
+/**
+ * Various static methods used in shared emitter logic.
+ */
+public class EmitterUtils
+{
+ public static ITypeNode findTypeNode(IPackageNode node)
+ {
+ IScopedNode scope = node.getScopedNode();
+ for (int i = 0; i < scope.getChildCount(); i++)
+ {
+ IASNode child = scope.getChild(i);
+ if (child instanceof ITypeNode)
+ return (ITypeNode) child;
+ }
+ return null;
+ }
+
+ public static ITypeDefinition findType(Collection<IDefinition> definitions)
+ {
+ for (IDefinition definition : definitions)
+ {
+ if (definition instanceof ITypeDefinition)
+ return (ITypeDefinition) definition;
+ }
+ return null;
+ }
+
+ public static IFunctionDefinition findFunction(Collection<IDefinition> definitions)
+ {
+ for (IDefinition definition : definitions)
+ {
+ if (definition instanceof IFunctionDefinition)
+ return (IFunctionDefinition) definition;
+ }
+ return null;
+ }
+
+ public static IFunctionNode findFunctionNode(IPackageNode node)
+ {
+ IScopedNode scope = node.getScopedNode();
+ for (int i = 0; i < scope.getChildCount(); i++)
+ {
+ IASNode child = scope.getChild(i);
+ if (child instanceof IFunctionNode)
+ return (IFunctionNode) child;
+ }
+ return null;
+ }
+
+ public static IVariableNode findVariableNode(IPackageNode node)
+ {
+ IScopedNode scope = node.getScopedNode();
+ for (int i = 0; i < scope.getChildCount(); i++)
+ {
+ IASNode child = scope.getChild(i);
+ if (child instanceof IVariableNode)
+ return (IVariableNode) child;
+ }
+ return null;
+ }
+
+ public static IVariableDefinition findVariable(Collection<IDefinition> definitions)
+ {
+ for (IDefinition definition : definitions)
+ {
+ if (definition instanceof IVariableDefinition)
+ return (IVariableDefinition) definition;
+ }
+ return null;
+ }
+
+ public static ITypeDefinition getTypeDefinition(IDefinitionNode node)
+ {
+ ITypeNode tnode = (ITypeNode) node.getAncestorOfType(ITypeNode.class);
+ if (tnode != null)
+ {
+ return (ITypeDefinition) tnode.getDefinition();
+ }
+ return null;
+ }
+
+ public static boolean isSameClass(IDefinition pdef, IDefinition thisClass,
+ ICompilerProject project)
+ {
+ if (pdef == thisClass)
+ return true;
+
+ IDefinition cdef = ((ClassDefinition) thisClass)
+ .resolveBaseClass(project);
+ while (cdef != null)
+ {
+ // needs to be a loop
+ if (cdef == pdef)
+ return true;
+ cdef = ((ClassDefinition) cdef).resolveBaseClass(project);
+ }
+ return false;
+ }
+
+ public static boolean hasSuperClass(ICompilerProject project,
+ IDefinitionNode node)
+ {
+ IClassDefinition superClassDefinition = getSuperClassDefinition(node,
+ project);
+ // XXX (mschmalle) this is nulling for MXML super class, figure out why
+ if (superClassDefinition == null)
+ return false;
+ String qname = superClassDefinition.getQualifiedName();
+ return superClassDefinition != null
+ && !qname.equals(IASLanguageConstants.Object);
+ }
+
+ public static boolean hasSuperCall(IScopedNode node)
+ {
+ for (int i = node.getChildCount() - 1; i > -1; i--)
+ {
+ IASNode cnode = node.getChild(i);
+ if (cnode.getNodeID() == ASTNodeID.FunctionCallID
+ && cnode.getChild(0).getNodeID() == ASTNodeID.SuperID)
+ return true;
+ }
+
+ return false;
+ }
+
+ public static boolean hasBody(IFunctionNode node)
+ {
+ IScopedNode scope = node.getScopedNode();
+ return scope.getChildCount() > 0;
+ }
+
+ public static IClassDefinition getSuperClassDefinition(
+ IDefinitionNode node, ICompilerProject project)
+ {
+ IDefinition parent = node.getDefinition().getParent();
+ if (parent instanceof IClassDefinition)
+ {
+ IClassDefinition parentClassDef = (IClassDefinition) parent;
+ IClassDefinition superClass = parentClassDef.resolveBaseClass(project);
+ return superClass;
+ }
+ return null;
+ }
+
+ public static List<String> resolveImports(ITypeDefinition type)
+ {
+ ArrayList<String> list = new ArrayList<String>();
+ IScopedNode scopeNode = type.getContainedScope().getScopeNode();
+ if (scopeNode != null)
+ {
+ scopeNode.getAllImports(list);
+ }
+ else
+ {
+ // MXML
+ ClassDefinition cdefinition = (ClassDefinition) type;
+ String[] implicitImports = cdefinition.getImplicitImports();
+ for (String imp : implicitImports)
+ {
+ list.add(imp);
+ }
+ }
+ return list;
+ }
+
+ public static IClassDefinition getClassDefinition(IDefinitionNode node)
+ {
+ IClassNode tnode = (IClassNode) node
+ .getAncestorOfType(IClassNode.class);
+ return (tnode != null) ? tnode.getDefinition() : null;
+ }
+
+ public static IParameterNode getRest(IParameterNode[] nodes)
+ {
+ for (IParameterNode node : nodes)
+ {
+ if (node.isRest())
+ return node;
+ }
+
+ return null;
+ }
+
+ public static Map<Integer, IParameterNode> getDefaults(
+ IParameterNode[] nodes)
+ {
+ Map<Integer, IParameterNode> result = new HashMap<Integer, IParameterNode>();
+ int i = 0;
+ boolean hasDefaults = false;
+ for (IParameterNode node : nodes)
+ {
+ if (node.hasDefaultValue())
+ {
+ hasDefaults = true;
+ result.put(i, node);
+ }
+ else
+ {
+ result.put(i, null);
+ }
+ i++;
+ }
+
+ if (!hasDefaults)
+ return null;
+
+ return result;
+ }
+
+ public static boolean writeThis(ICompilerProject project,
+ JSSessionModel model, IIdentifierNode node)
+ {
+ IClassNode classNode = (IClassNode) node
+ .getAncestorOfType(IClassNode.class);
+
+ IDefinition nodeDef = node.resolve(project);
+
+ IASNode parentNode = node.getParent();
+ ASTNodeID parentNodeId = parentNode.getNodeID();
+
+ IASNode firstChild = parentNode.getChild(0);
+
+ final IClassDefinition thisClass = model.getCurrentClass();
+
+ boolean identifierIsMemberAccess = parentNodeId == ASTNodeID.MemberAccessExpressionID;
+
+ if (nodeDef instanceof ParameterDefinition)
+ return false;
+
+ if (classNode == null) // script in MXML and AS interface definitions
+ {
++ if (parentNodeId == ASTNodeID.FunctionCallID && model.inE4xFilter)
++ {
++ // instance methods must be qualified with 'this'?
++ // or maybe we need to test if identifier exists on XML/XMLList
++ return false;
++ }
+ if (nodeDef instanceof VariableDefinition)
+ {
+ IDefinition pdef = ((VariableDefinition) nodeDef).getParent();
+
+ if (thisClass == null || !isSameClass(pdef, thisClass, project))
+ return false;
+
+ if (identifierIsMemberAccess)
+ return node == firstChild;
+
+ return parentNodeId == ASTNodeID.ContainerID
+ || !(parentNode instanceof ParameterNode);
+ }
+ else if (nodeDef instanceof AccessorDefinition)
+ {
+ IDefinition pdef = ((AccessorDefinition) nodeDef).getParent();
+
+ if (thisClass == null || !isSameClass(pdef, thisClass, project))
+ return false;
+
+ if (identifierIsMemberAccess)
+ return node == firstChild;
+
+ return true;
+ }
+ else if (parentNodeId == ASTNodeID.ContainerID
+ && nodeDef instanceof FunctionDefinition)
+ {
+ return ((FunctionDefinition) nodeDef)
+ .getFunctionClassification() == FunctionClassification.CLASS_MEMBER; // for 'goog.bind'
+ }
+ else
+ {
+ boolean isFileOrPackageMember = false;
+ if(nodeDef instanceof FunctionDefinition)
+ {
+ FunctionClassification classification = ((FunctionDefinition) nodeDef).getFunctionClassification();
+ if(classification == FunctionClassification.FILE_MEMBER ||
+ classification == FunctionClassification.PACKAGE_MEMBER)
+ {
+ isFileOrPackageMember = true;
+ }
+ }
+ return parentNodeId == ASTNodeID.FunctionCallID
+ && !(nodeDef instanceof AccessorDefinition)
+ && !identifierIsMemberAccess
+ && !isFileOrPackageMember;
+ }
+ }
+ else
+ {
++ if (parentNodeId == ASTNodeID.FunctionCallID && model.inE4xFilter)
++ {
++ // instance methods must be qualified with 'this'?
++ // or maybe we need to test if identifier exists on XML/XMLList
++ return false;
++ }
+ if (nodeDef != null && !nodeDef.isInternal()
+ && isClassMember(project, nodeDef, classNode))
+ {
+ if (identifierIsMemberAccess)
+ {
+ return node == firstChild;
+ }
+ else
+ {
+ boolean identifierIsLocalFunction = nodeDef instanceof FunctionDefinition
+ && !(nodeDef instanceof AccessorDefinition)
+ && ((FunctionDefinition) nodeDef)
+ .getFunctionClassification() == IFunctionDefinition.FunctionClassification.LOCAL;
+
+ return !identifierIsLocalFunction;
+ }
+ }
+ }
+
+ return false;
+ }
+
+ public static boolean isClassMember(ICompilerProject project,
+ IDefinition nodeDef, IClassNode classNode)
+ {
+ TypeScope cscope = (TypeScope) classNode.getDefinition()
+ .getContainedScope();
+
+ Set<INamespaceDefinition> nsSet = cscope.getNamespaceSet(project);
+ Collection<IDefinition> defs = new HashSet<IDefinition>();
+
+ cscope.getAllPropertiesForMemberAccess((CompilerProject) project, defs,
+ nsSet);
+
+ Iterator<IDefinition> visiblePropertiesIterator = defs.iterator();
+ while (visiblePropertiesIterator.hasNext())
+ {
+ if (nodeDef.getQualifiedName().equals(
+ visiblePropertiesIterator.next().getQualifiedName()))
+ return true;
+ }
+
+ return false;
+ }
+
+ public static boolean isScalar(IExpressionNode node)
+ {
+ ASTNodeID id = node.getNodeID();
+ if (id == ASTNodeID.LiteralBooleanID ||
+ id == ASTNodeID.LiteralIntegerID ||
+ id == ASTNodeID.LiteralIntegerZeroID ||
+ id == ASTNodeID.LiteralDoubleID ||
+ id == ASTNodeID.LiteralNullID ||
+ id == ASTNodeID.LiteralNumberID ||
+ id == ASTNodeID.LiteralRegexID ||
+ id == ASTNodeID.LiteralStringID ||
+ id == ASTNodeID.LiteralUintID)
+ return true;
+ if (id == ASTNodeID.IdentifierID)
+ {
+ IIdentifierNode idnode = (IIdentifierNode)node;
+ String idname = idnode.getName();
+ if (idname.equals(NativeUtils.NativeASType.Infinity.name()) ||
+ idname.equals(NativeUtils.NativeASType.undefined.name()) ||
+ idname.equals(NativeUtils.NativeASType.NaN.name()))
+ return true;
+ }
+ // special case -Infinity
+ if (id == ASTNodeID.Op_SubtractID &&
+ node.getChildCount() == 1)
+ {
+ IASNode child = node.getChild(0);
+ if (child.getNodeID() == ASTNodeID.IdentifierID)
+ {
+ IIdentifierNode idnode = (IIdentifierNode)child;
+ String idname = idnode.getName();
+ if (idname.equals(NativeUtils.NativeASType.Infinity.name()))
+ return true;
+ }
+ }
+ return false;
+ }
+
+ public static IContainerNode insertArgumentsBefore(IContainerNode argumentsNode, IASNode... nodes)
+ {
+ int originalLength = argumentsNode.getChildCount();
+ int extraLength = nodes.length;
+ ContainerNode result = new ContainerNode(originalLength + extraLength);
+ result.setSourcePath(argumentsNode.getSourcePath());
+ result.span(argumentsNode);
+ result.setParent((NodeBase) argumentsNode.getParent());
+ for (int i = 0; i < extraLength; i++)
+ {
+ NodeBase node = (NodeBase) nodes[i];
+ node.setSourcePath(argumentsNode.getSourcePath());
+ result.addItem(node);
+ }
+ for (int i = 0; i < originalLength; i++)
+ {
+ result.addItem((NodeBase) argumentsNode.getChild(i));
+ }
+ return result;
+ }
+
+ public static IContainerNode insertArgumentsAfter(IContainerNode argumentsNode, IASNode... nodes)
+ {
+ int originalLength = argumentsNode.getChildCount();
+ int extraLength = nodes.length;
+ ContainerNode result = new ContainerNode(originalLength + extraLength);
+ result.setSourcePath(argumentsNode.getSourcePath());
+ result.span(argumentsNode);
+ result.setParent((NodeBase) argumentsNode.getParent());
+ for (int i = 0; i < originalLength; i++)
+ {
+ result.addItem((NodeBase) argumentsNode.getChild(i));
+ }
+ for (int i = 0; i < extraLength; i++)
+ {
+ NodeBase node = (NodeBase) nodes[i];
+ node.setSourcePath(argumentsNode.getSourcePath());
+ result.addItem(node);
+ }
+ return result;
+ }
+
+ public static IContainerNode insertArgumentsAt(IContainerNode argumentsNode, int index, IASNode... nodes)
+ {
+ int originalLength = argumentsNode.getChildCount();
+ int extraLength = nodes.length;
+ ContainerNode result = new ContainerNode(originalLength + extraLength);
+ result.setSourcePath(argumentsNode.getSourcePath());
+ result.span(argumentsNode);
+ result.setParent((NodeBase) argumentsNode.getParent());
+ for (int i = 0; i < originalLength; i++)
+ {
+ if(i < originalLength)
+ {
+ result.addItem((NodeBase) argumentsNode.getChild(i));
+ }
+ else
+ {
+ int j = i;
+ if (i >= index + extraLength)
+ {
+ j -= extraLength;
+ result.addItem((NodeBase) argumentsNode.getChild(j));
+ }
+ else
+ {
+ j -= originalLength;
+ NodeBase node = (NodeBase) nodes[j];
+ node.setSourcePath(argumentsNode.getSourcePath());
+ result.addItem(node);
+ }
+ }
+ }
+ return result;
+ }
+
+ public static boolean isImplicit(IContainerNode node)
+ {
+ return node.getContainerType() == IContainerNode.ContainerType.IMPLICIT
+ || node.getContainerType() == IContainerNode.ContainerType.SYNTHESIZED;
+ }
+
+}
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/de070636/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/mxml/MXMLWriter.java
----------------------------------------------------------------------
diff --cc compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/mxml/MXMLWriter.java
index afb45fd,0000000..454904d
mode 100644,000000..100644
--- a/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/mxml/MXMLWriter.java
+++ b/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/mxml/MXMLWriter.java
@@@ -1,84 -1,0 +1,85 @@@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+package org.apache.flex.compiler.internal.codegen.mxml;
+
+import java.io.File;
+import java.io.IOException;
+import java.io.OutputStream;
+import java.util.List;
+
+import org.apache.flex.compiler.codegen.js.IJSEmitter;
+import org.apache.flex.compiler.codegen.mxml.IMXMLEmitter;
+import org.apache.flex.compiler.driver.js.IJSBackend;
+import org.apache.flex.compiler.internal.codegen.js.JSFilterWriter;
+import org.apache.flex.compiler.internal.codegen.js.JSSharedData;
+import org.apache.flex.compiler.internal.codegen.js.JSWriter;
+import org.apache.flex.compiler.problems.ICompilerProblem;
+import org.apache.flex.compiler.projects.IASProject;
+import org.apache.flex.compiler.units.ICompilationUnit;
+import org.apache.flex.compiler.visitor.as.IASBlockWalker;
+import org.apache.flex.compiler.visitor.mxml.IMXMLBlockWalker;
+
+public class MXMLWriter extends JSWriter
+{
+ /**
+ * Create a JSApplication writer.
+ *
+ * @param application the JSApplication model to be encoded
+ * @param useCompression use ZLIB compression if true
+ */
+ public MXMLWriter(IASProject project, List<ICompilerProblem> problems,
+ ICompilationUnit compilationUnit, boolean enableDebug)
+ {
+ super(project, problems, compilationUnit, enableDebug);
+ }
+
+ @Override
+ public void writeTo(OutputStream out, File sourceMapOut)
+ {
+ IJSBackend backend = (IJSBackend) JSSharedData.backend;
+ JSFilterWriter writer = (JSFilterWriter) backend.createWriterBuffer(project);
+
+ IJSEmitter asEmitter = (IJSEmitter) backend.createEmitter(writer);
+ IASBlockWalker asBlockWalker = backend.createWalker(
+ project, problems, asEmitter);
+
+ IMXMLEmitter mxmlEmitter = backend.createMXMLEmitter(writer);
+ IMXMLBlockWalker mxmlBlockWalker = backend.createMXMLWalker(
+ project, problems, mxmlEmitter, asEmitter, asBlockWalker);
+
+ mxmlBlockWalker.visitCompilationUnit(compilationUnit);
+
+ try
+ {
+ out.write(mxmlEmitter.postProcess(writer.toString()).getBytes());
+ }
+ catch (IOException e)
+ {
+ e.printStackTrace();
+ }
+
+ if (sourceMapOut != null)
+ {
- throw new UnsupportedOperationException("Source maps not supported for MXML files");
++ String fileName = new File(compilationUnit.getAbsoluteFilename()).getName();
++ System.out.println("Source map cannot be generated for '" + fileName + "'.");
+ }
+ }
+
+}
[09/18] git commit: [flex-falcon]
[refs/heads/feature/maven-migration-test] - FalconJX now checks debug flag to
determine whether to generate the release build via Google Closure Compiler.
Also added -skip-transpile option so when debug==false, you can
Posted by cd...@apache.org.
FalconJX now checks debug flag to determine whether to generate the release build via Google Closure Compiler. Also added -skip-transpile option so when debug==false, you can skip the debug-mode transpilation. By default, when debug==false, the compiler wil first transpile into the js-debug folder then call GCC on that folder. If you set -skip-transpile, the copiler will not transpile into the js-debug folder and just hand the js-debug folder to GCC. This can come in handy if the compiler isn't generating the right code and you want to hand-edit it before sending it to GCC for optimization
Project: http://git-wip-us.apache.org/repos/asf/flex-falcon/repo
Commit: http://git-wip-us.apache.org/repos/asf/flex-falcon/commit/3357a102
Tree: http://git-wip-us.apache.org/repos/asf/flex-falcon/tree/3357a102
Diff: http://git-wip-us.apache.org/repos/asf/flex-falcon/diff/3357a102
Branch: refs/heads/feature/maven-migration-test
Commit: 3357a10216f66f0ef93630a8861c43f975f509da
Parents: fd87205
Author: Alex Harui <ah...@apache.org>
Authored: Wed Apr 13 12:07:52 2016 -0700
Committer: Alex Harui <ah...@apache.org>
Committed: Wed Apr 13 12:07:52 2016 -0700
----------------------------------------------------------------------
.../apache/flex/compiler/clients/MXMLJSC.java | 109 ++++++++-------
.../mxml/flexjs/MXMLFlexJSPublisher.java | 140 ++++++++++---------
.../driver/js/goog/JSGoogConfiguration.java | 20 +++
3 files changed, 154 insertions(+), 115 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/3357a102/compiler.jx/src/org/apache/flex/compiler/clients/MXMLJSC.java
----------------------------------------------------------------------
diff --git a/compiler.jx/src/org/apache/flex/compiler/clients/MXMLJSC.java b/compiler.jx/src/org/apache/flex/compiler/clients/MXMLJSC.java
index d324c9f..c6d9508 100644
--- a/compiler.jx/src/org/apache/flex/compiler/clients/MXMLJSC.java
+++ b/compiler.jx/src/org/apache/flex/compiler/clients/MXMLJSC.java
@@ -349,7 +349,7 @@ public class MXMLJSC implements JSCompilerEntryPoint, ProblemQueryProvider,
if (continueCompilation)
{
project.setProblems(problems.getProblems());
- compile();
+ compile();
if (problems.hasFilteredProblems())
{
if (problems.hasErrors())
@@ -410,12 +410,14 @@ public class MXMLJSC implements JSCompilerEntryPoint, ProblemQueryProvider,
{
project.getSourceCompilationUnitFactory().addHandler(asFileHandler);
- if (!setupTargetFile())
- return false;
-
- buildArtifact();
+ if (!((JSGoogConfiguration) config).getSkipTranspile())
+ {
+ if (!setupTargetFile())
+ return false;
- if (jsTarget != null)
+ buildArtifact();
+ }
+ if (jsTarget != null || ((JSGoogConfiguration) config).getSkipTranspile())
{
List<ICompilerProblem> errors = new ArrayList<ICompilerProblem>();
List<ICompilerProblem> warnings = new ArrayList<ICompilerProblem>();
@@ -432,54 +434,57 @@ public class MXMLJSC implements JSCompilerEntryPoint, ProblemQueryProvider,
File outputFolder = jsPublisher.getOutputFolder();
- ArrayList<ICompilationUnit> roots = new ArrayList<ICompilationUnit>();
- roots.add(mainCU);
- Set<ICompilationUnit> incs = target.getIncludesCompilationUnits();
- roots.addAll(incs);
- List<ICompilationUnit> reachableCompilationUnits = project.getReachableCompilationUnitsInSWFOrder(roots);
- for (final ICompilationUnit cu : reachableCompilationUnits)
+ if (!((JSGoogConfiguration) config).getSkipTranspile())
{
- ICompilationUnit.UnitType cuType = cu.getCompilationUnitType();
-
- if (cuType == ICompilationUnit.UnitType.AS_UNIT
- || cuType == ICompilationUnit.UnitType.MXML_UNIT)
- {
- final File outputClassFile = getOutputClassFile(
- cu.getQualifiedNames().get(0), outputFolder);
-
- System.out.println("Compiling file: " + outputClassFile);
-
- ICompilationUnit unit = cu;
-
- IJSWriter writer;
- if (cuType == ICompilationUnit.UnitType.AS_UNIT)
- {
- writer = (IJSWriter) JSSharedData.backend.createWriter(project,
- errors, unit, false);
- }
- else
- {
- writer = (IJSWriter) JSSharedData.backend.createMXMLWriter(
- project, errors, unit, false);
- }
-
- BufferedOutputStream out = new BufferedOutputStream(
- new FileOutputStream(outputClassFile));
-
- File outputSourceMapFile = null;
- if (project.config.getSourceMap())
- {
- outputSourceMapFile = getOutputSourceMapFile(
- cu.getQualifiedNames().get(0), outputFolder);
- }
-
- writer.writeTo(out, outputSourceMapFile);
- out.flush();
- out.close();
- writer.close();
- }
+ ArrayList<ICompilationUnit> roots = new ArrayList<ICompilationUnit>();
+ roots.add(mainCU);
+ Set<ICompilationUnit> incs = target.getIncludesCompilationUnits();
+ roots.addAll(incs);
+ List<ICompilationUnit> reachableCompilationUnits = project.getReachableCompilationUnitsInSWFOrder(roots);
+ for (final ICompilationUnit cu : reachableCompilationUnits)
+ {
+ ICompilationUnit.UnitType cuType = cu.getCompilationUnitType();
+
+ if (cuType == ICompilationUnit.UnitType.AS_UNIT
+ || cuType == ICompilationUnit.UnitType.MXML_UNIT)
+ {
+ final File outputClassFile = getOutputClassFile(
+ cu.getQualifiedNames().get(0), outputFolder);
+
+ System.out.println("Compiling file: " + outputClassFile);
+
+ ICompilationUnit unit = cu;
+
+ IJSWriter writer;
+ if (cuType == ICompilationUnit.UnitType.AS_UNIT)
+ {
+ writer = (IJSWriter) JSSharedData.backend.createWriter(project,
+ errors, unit, false);
+ }
+ else
+ {
+ writer = (IJSWriter) JSSharedData.backend.createMXMLWriter(
+ project, errors, unit, false);
+ }
+
+ BufferedOutputStream out = new BufferedOutputStream(
+ new FileOutputStream(outputClassFile));
+
+ File outputSourceMapFile = null;
+ if (project.config.getSourceMap())
+ {
+ outputSourceMapFile = getOutputSourceMapFile(
+ cu.getQualifiedNames().get(0), outputFolder);
+ }
+
+ writer.writeTo(out, outputSourceMapFile);
+ out.flush();
+ out.close();
+ writer.close();
+ }
+ }
}
-
+
if (jsPublisher != null)
{
compilationSuccess = jsPublisher.publish(problems);
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/3357a102/compiler.jx/src/org/apache/flex/compiler/internal/codegen/mxml/flexjs/MXMLFlexJSPublisher.java
----------------------------------------------------------------------
diff --git a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/mxml/flexjs/MXMLFlexJSPublisher.java b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/mxml/flexjs/MXMLFlexJSPublisher.java
index 5f5387c..170a24b 100644
--- a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/mxml/flexjs/MXMLFlexJSPublisher.java
+++ b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/mxml/flexjs/MXMLFlexJSPublisher.java
@@ -130,7 +130,7 @@ public class MXMLFlexJSPublisher extends JSGoogPublisher implements IJSPublisher
// (erikdebruin) Marmotinni handles file management, so we
// bypass the setup.
- if (!isMarmotinniRun)
+ if (!isMarmotinniRun && !((JSGoogConfiguration)configuration).getSkipTranspile())
setupOutputFolder();
return outputFolder;
@@ -162,12 +162,15 @@ public class MXMLFlexJSPublisher extends JSGoogPublisher implements IJSPublisher
org.apache.commons.io.FileUtils.deleteQuietly(releaseDir);
}
- if (!releaseDir.mkdirs())
- {
- throw new IOException("Unable to create release directory at " + releaseDir.getAbsolutePath());
- }
+ if (!configuration.debug())
+ {
+ if (!releaseDir.mkdirs())
+ {
+ throw new IOException("Unable to create release directory at " + releaseDir.getAbsolutePath());
+ }
+ }
}
-
+
// If the closure-lib parameter is empty we'll try to find the resources
// in the classpath, dump its content to the output directory and use
// this
@@ -222,7 +225,7 @@ public class MXMLFlexJSPublisher extends JSGoogPublisher implements IJSPublisher
closureLibDirPath = ((JSGoogConfiguration) configuration).getClosureLib();
}
}
-
+
// Dump FlexJS to the target directory.
@SuppressWarnings("unused")
String flexJsLibDirPath;
@@ -273,18 +276,21 @@ public class MXMLFlexJSPublisher extends JSGoogPublisher implements IJSPublisher
final String depsTgtFilePath = intermediateDirPath + "/deps.js";
final String projectIntermediateJSFilePath = intermediateDirPath + File.separator + outputFileName;
final String projectReleaseJSFilePath = releaseDirPath + File.separator + outputFileName;
-
- appendExportSymbol(projectIntermediateJSFilePath, projectName);
- appendEncodedCSS(projectIntermediateJSFilePath, projectName);
-
- // if (!subsetGoog)
- // {
- // (erikdebruin) We need to leave the 'goog' files and dependencies well
- // enough alone. We copy the entire library over so the
- // 'goog' dependencies will resolve without our help.
- FileUtils.copyDirectory(new File(closureGoogSrcLibDirPath), new File(closureGoogTgtLibDirPath));
- // }
-
+
+ if (!((JSGoogConfiguration)configuration).getSkipTranspile())
+ {
+ appendExportSymbol(projectIntermediateJSFilePath, projectName);
+ appendEncodedCSS(projectIntermediateJSFilePath, projectName);
+
+ // if (!subsetGoog)
+ // {
+ // (erikdebruin) We need to leave the 'goog' files and dependencies well
+ // enough alone. We copy the entire library over so the
+ // 'goog' dependencies will resolve without our help.
+ FileUtils.copyDirectory(new File(closureGoogSrcLibDirPath), new File(closureGoogTgtLibDirPath));
+ // }
+ }
+
JSClosureCompilerWrapper compilerWrapper = new JSClosureCompilerWrapper(((JSGoogConfiguration) configuration).getJSCompilerOptions());
List<ISWC> swcs = project.getLibraries();
@@ -407,56 +413,64 @@ public class MXMLFlexJSPublisher extends JSGoogPublisher implements IJSPublisher
IOFileFilter subdirs = FileFilterUtils.or(DirectoryFileFilter.DIRECTORY, assetFiles);
FileUtils.copyDirectory(srcDir, intermediateDir, subdirs);
- FileUtils.copyDirectory(srcDir, releaseDir, subdirs);
+ if (!configuration.debug())
+ FileUtils.copyDirectory(srcDir, releaseDir, subdirs);
- // File srcDeps = new File(depsSrcFilePath);
+ // File srcDeps = new File(depsSrcFilePath);
- writeHTML("intermediate", projectName, intermediateDirPath, depsFileData.toString(), gdw.additionalHTML);
- writeHTML("release", projectName, releaseDirPath, null, gdw.additionalHTML);
- if (project.needCSS)
+ if (!((JSGoogConfiguration)configuration).getSkipTranspile())
+ writeHTML("intermediate", projectName, intermediateDirPath, depsFileData.toString(), gdw.additionalHTML);
+ if (!configuration.debug())
+ writeHTML("release", projectName, releaseDirPath, null, gdw.additionalHTML);
+ if (project.needCSS || ((JSGoogConfiguration)configuration).getSkipTranspile())
{
- writeCSS(projectName, intermediateDirPath);
- writeCSS(projectName, releaseDirPath);
+ if (!((JSGoogConfiguration)configuration).getSkipTranspile())
+ writeCSS(projectName, intermediateDirPath);
+ if (!configuration.debug())
+ FileUtils.copyFile(new File(intermediateDirPath + File.separator + projectName + ".css"),
+ new File(releaseDirPath + File.separator + projectName + ".css"));
}
-
- /*
- * if (!subsetGoog) { // (erikdebruin) add 'goog' files Collection<File>
- * files = org.apache.commons.io.FileUtils.listFiles(new File(
- * closureGoogTgtLibDirPath), new RegexFileFilter("^.*(\\.js)"),
- * DirectoryFileFilter.DIRECTORY); for (File file : files) {
- * compilerWrapper.addJSSourceFile(file.getCanonicalPath()); } }
- */
- Collection<File> files = org.apache.commons.io.FileUtils.listFiles(new File(closureGoogSrcLibDirPath),
- new RegexFileFilter("^.*(\\.js)"), DirectoryFileFilter.DIRECTORY);
- for (File file : files)
+
+ if (!configuration.debug())
{
- compilerWrapper.addJSSourceFile(file.getCanonicalPath());
+ /*
+ * if (!subsetGoog) { // (erikdebruin) add 'goog' files Collection<File>
+ * files = org.apache.commons.io.FileUtils.listFiles(new File(
+ * closureGoogTgtLibDirPath), new RegexFileFilter("^.*(\\.js)"),
+ * DirectoryFileFilter.DIRECTORY); for (File file : files) {
+ * compilerWrapper.addJSSourceFile(file.getCanonicalPath()); } }
+ */
+ Collection<File> files = org.apache.commons.io.FileUtils.listFiles(new File(closureGoogSrcLibDirPath),
+ new RegexFileFilter("^.*(\\.js)"), DirectoryFileFilter.DIRECTORY);
+ for (File file : files)
+ {
+ compilerWrapper.addJSSourceFile(file.getCanonicalPath());
+ }
+
+ /*
+ * // (erikdebruin) add project files for (String filePath :
+ * gdw.filePathsInOrder) { compilerWrapper.addJSSourceFile( new
+ * File(filePath).getCanonicalPath()); }
+ */
+
+ compilerWrapper.setOptions(projectReleaseJSFilePath, useStrictPublishing, projectName);
+
+ /*
+ * // (erikdebruin) Include the 'goog' deps to allow the compiler to
+ * resolve // dependencies. compilerWrapper.addJSSourceFile(
+ * closureGoogSrcLibDirPath + File.separator + "deps.js");
+ */
+ List<String> externs = ((JSGoogConfiguration) configuration).getExternalJSLib();
+ for (String extern : externs)
+ {
+ compilerWrapper.addJSExternsFile(extern);
+ }
+
+ compilerWrapper.targetFilePath = projectReleaseJSFilePath;
+ compilerWrapper.compile();
+
+ appendSourceMapLocation(projectReleaseJSFilePath, projectName);
}
-
- /*
- * // (erikdebruin) add project files for (String filePath :
- * gdw.filePathsInOrder) { compilerWrapper.addJSSourceFile( new
- * File(filePath).getCanonicalPath()); }
- */
-
- compilerWrapper.setOptions(projectReleaseJSFilePath, useStrictPublishing, projectName);
-
- /*
- * // (erikdebruin) Include the 'goog' deps to allow the compiler to
- * resolve // dependencies. compilerWrapper.addJSSourceFile(
- * closureGoogSrcLibDirPath + File.separator + "deps.js");
- */
- List<String> externs = ((JSGoogConfiguration) configuration).getExternalJSLib();
- for (String extern : externs)
- {
- compilerWrapper.addJSExternsFile(extern);
- }
-
- compilerWrapper.targetFilePath = projectReleaseJSFilePath;
- compilerWrapper.compile();
-
- appendSourceMapLocation(projectReleaseJSFilePath, projectName);
-
/*
* if (!isMarmotinniRun) { String allDeps = ""; if (!subsetGoog) {
* allDeps += FileUtils.readFileToString(srcDeps); } allDeps +=
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/3357a102/compiler.jx/src/org/apache/flex/compiler/internal/driver/js/goog/JSGoogConfiguration.java
----------------------------------------------------------------------
diff --git a/compiler.jx/src/org/apache/flex/compiler/internal/driver/js/goog/JSGoogConfiguration.java b/compiler.jx/src/org/apache/flex/compiler/internal/driver/js/goog/JSGoogConfiguration.java
index 0f03323..6eb1037 100644
--- a/compiler.jx/src/org/apache/flex/compiler/internal/driver/js/goog/JSGoogConfiguration.java
+++ b/compiler.jx/src/org/apache/flex/compiler/internal/driver/js/goog/JSGoogConfiguration.java
@@ -256,6 +256,26 @@ public class JSGoogConfiguration extends JSConfiguration
}
+ //
+ // 'skip-transpile'
+ //
+
+ private boolean skipTranspile = false;
+
+ public boolean getSkipTranspile()
+ {
+ return skipTranspile;
+ }
+
+ @Config
+ @Mapping("skip-transpile")
+ public void setSkipTranspile(ConfigurationValue cv, boolean value)
+ throws ConfigurationException
+ {
+ skipTranspile = value;
+ }
+
+
protected String getAbsolutePathFromPathRelativeToMXMLC(String relativePath)
throws IOException
[16/18] git commit: [flex-falcon]
[refs/heads/feature/maven-migration-test] - Merge branch 'develop' of
https://git-wip-us.apache.org/repos/asf/flex-falcon into
feature/maven-migration-test
Posted by cd...@apache.org.
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/de070636/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/mxml/flexjs/MXMLFlexJSEmitter.java
----------------------------------------------------------------------
diff --cc compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/mxml/flexjs/MXMLFlexJSEmitter.java
index 094f5c7,0000000..8beba40
mode 100644,000000..100644
--- a/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/mxml/flexjs/MXMLFlexJSEmitter.java
+++ b/compiler-jx/src/main/java/org/apache/flex/compiler/internal/codegen/mxml/flexjs/MXMLFlexJSEmitter.java
@@@ -1,2320 -1,0 +1,2323 @@@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+package org.apache.flex.compiler.internal.codegen.mxml.flexjs;
+
+
+import java.io.File;
+import java.io.FilterWriter;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Map.Entry;
+import java.util.Set;
+
+import org.apache.flex.abc.semantics.MethodInfo;
+import org.apache.flex.abc.semantics.Name;
+import org.apache.flex.abc.semantics.Namespace;
+import org.apache.flex.compiler.codegen.as.IASEmitter;
+import org.apache.flex.compiler.codegen.mxml.flexjs.IMXMLFlexJSEmitter;
+import org.apache.flex.compiler.constants.IASKeywordConstants;
+import org.apache.flex.compiler.constants.IASLanguageConstants;
+import org.apache.flex.compiler.definitions.IClassDefinition;
+import org.apache.flex.compiler.definitions.IDefinition;
+import org.apache.flex.compiler.internal.codegen.as.ASEmitterTokens;
+import org.apache.flex.compiler.internal.codegen.databinding.BindingDatabase;
+import org.apache.flex.compiler.internal.codegen.databinding.BindingInfo;
+import org.apache.flex.compiler.internal.codegen.databinding.FunctionWatcherInfo;
+import org.apache.flex.compiler.internal.codegen.databinding.PropertyWatcherInfo;
+import org.apache.flex.compiler.internal.codegen.databinding.StaticPropertyWatcherInfo;
+import org.apache.flex.compiler.internal.codegen.databinding.WatcherInfoBase;
+import org.apache.flex.compiler.internal.codegen.databinding.WatcherInfoBase.WatcherType;
+import org.apache.flex.compiler.internal.codegen.databinding.XMLWatcherInfo;
+import org.apache.flex.compiler.internal.codegen.js.JSSessionModel.PropertyNodes;
+import org.apache.flex.compiler.internal.codegen.js.flexjs.JSFlexJSEmitter;
+import org.apache.flex.compiler.internal.codegen.js.flexjs.JSFlexJSEmitterTokens;
+import org.apache.flex.compiler.internal.codegen.js.goog.JSGoogEmitterTokens;
+import org.apache.flex.compiler.internal.codegen.js.jx.PackageFooterEmitter;
+import org.apache.flex.compiler.internal.codegen.js.utils.EmitterUtils;
+import org.apache.flex.compiler.internal.codegen.mxml.MXMLEmitter;
+import org.apache.flex.compiler.internal.projects.FlexJSProject;
+import org.apache.flex.compiler.internal.projects.FlexProject;
+import org.apache.flex.compiler.internal.scopes.ASProjectScope;
+import org.apache.flex.compiler.internal.tree.as.FunctionCallNode;
+import org.apache.flex.compiler.internal.tree.as.IdentifierNode;
+import org.apache.flex.compiler.internal.tree.as.MemberAccessExpressionNode;
+import org.apache.flex.compiler.projects.ICompilerProject;
+import org.apache.flex.compiler.tree.ASTNodeID;
+import org.apache.flex.compiler.tree.as.IASNode;
+import org.apache.flex.compiler.tree.as.IExpressionNode;
+import org.apache.flex.compiler.tree.as.IFunctionNode;
+import org.apache.flex.compiler.tree.as.IIdentifierNode;
+import org.apache.flex.compiler.tree.as.IImportNode;
+import org.apache.flex.compiler.tree.as.IVariableNode;
+import org.apache.flex.compiler.tree.metadata.IMetaTagNode;
+import org.apache.flex.compiler.tree.metadata.IMetaTagsNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLArrayNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLClassDefinitionNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLClassNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLComponentNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLDataBindingNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLDeclarationsNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLDocumentNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLEventSpecifierNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLFactoryNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLImplementsNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLInstanceNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLLiteralNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLMetadataNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLObjectNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLPropertySpecifierNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLScriptNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLSpecifierNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLStateNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLStringNode;
+import org.apache.flex.compiler.tree.mxml.IMXMLStyleSpecifierNode;
+import org.apache.flex.compiler.units.ICompilationUnit;
+import org.apache.flex.compiler.utils.NativeUtils;
+import org.apache.flex.compiler.visitor.mxml.IMXMLBlockWalker;
+
+import com.google.common.base.Joiner;
+
+/**
+ * @author Erik de Bruin
+ */
+public class MXMLFlexJSEmitter extends MXMLEmitter implements
+ IMXMLFlexJSEmitter
+{
+
+ // the instances in a container
+ private ArrayList<MXMLDescriptorSpecifier> currentInstances;
+ private ArrayList<MXMLDescriptorSpecifier> currentPropertySpecifiers;
+ private ArrayList<MXMLDescriptorSpecifier> descriptorTree;
+ private MXMLDescriptorSpecifier propertiesTree;
+ private MXMLDescriptorSpecifier currentStateOverrides;
+ private ArrayList<MXMLEventSpecifier> events;
+ // all instances in the current document or subdocument
+ private ArrayList<MXMLDescriptorSpecifier> instances;
+ // all instances in the document AND its subdocuments
+ private ArrayList<MXMLDescriptorSpecifier> allInstances = new ArrayList<MXMLDescriptorSpecifier>();
+ private ArrayList<MXMLScriptSpecifier> scripts;
+ //private ArrayList<MXMLStyleSpecifier> styles;
+ private IClassDefinition classDefinition;
+ private IClassDefinition documentDefinition;
+ private ArrayList<String> usedNames = new ArrayList<String>();
+ private ArrayList<IMXMLMetadataNode> metadataNodes = new ArrayList<IMXMLMetadataNode>();
+
+ private int eventCounter;
+ private int idCounter;
+ private int bindingCounter;
+
+ private boolean inMXMLContent;
+ private boolean inStatesOverride;
+ private boolean makingSimpleArray;
+
+ private StringBuilder subDocuments = new StringBuilder();
+ private ArrayList<String> subDocumentNames = new ArrayList<String>();
+ private String interfaceList;
+
+ /**
+ * This keeps track of the entries in our temporary array of
+ * DeferredInstanceFromFunction objects that we CG to help with
+ * State override CG.
+ *
+ * Keys are Instance nodes,
+ * values are the array index where the deferred instance is:
+ *
+ * deferred instance = local3[ nodeToIndexMap.get(an instance) ]
+ */
+ protected Map<IMXMLNode, Integer> nodeToIndexMap;
+
+ public MXMLFlexJSEmitter(FilterWriter out)
+ {
+ super(out);
+ }
+
+ @Override
+ public String postProcess(String output)
+ {
+ IASEmitter asEmitter = ((IMXMLBlockWalker) getMXMLWalker()).getASEmitter();
+ usedNames.addAll(((JSFlexJSEmitter)asEmitter).usedNames);
+
+ boolean foundXML = false;
+ String[] lines = output.split("\n");
+ ArrayList<String> finalLines = new ArrayList<String>();
+ int endRequires = -1;
+ boolean sawRequires = false;
+ boolean stillSearching = true;
+ for (String line : lines)
+ {
+ if (stillSearching)
+ {
+ int c = line.indexOf(JSGoogEmitterTokens.GOOG_REQUIRE.getToken());
+ if (c > -1)
+ {
+ int c2 = line.indexOf(")");
+ String s = line.substring(c + 14, c2 - 1);
+ if (s.equals(IASLanguageConstants.XML))
+ {
+ foundXML = true;
+ }
+ sawRequires = true;
+ if (!usedNames.contains(s))
+ continue;
+ }
+ else if (sawRequires)
+ {
+ stillSearching = false;
+ endRequires = finalLines.size();
+ }
+ }
+ finalLines.add(line);
+ }
+ boolean needXML = ((FlexJSProject)(((IMXMLBlockWalker) getMXMLWalker()).getProject())).needXML;
+ if (needXML && !foundXML)
+ {
+ StringBuilder appendString = new StringBuilder();
+ appendString.append(JSGoogEmitterTokens.GOOG_REQUIRE.getToken());
+ appendString.append(ASEmitterTokens.PAREN_OPEN.getToken());
+ appendString.append(ASEmitterTokens.SINGLE_QUOTE.getToken());
+ appendString.append(IASLanguageConstants.XML);
+ appendString.append(ASEmitterTokens.SINGLE_QUOTE.getToken());
+ appendString.append(ASEmitterTokens.PAREN_CLOSE.getToken());
+ appendString.append(ASEmitterTokens.SEMICOLON.getToken());
+ finalLines.add(endRequires, appendString.toString());
+ // TODO (aharui) addLineToMappings(finalLines.size());
+ }
+ // append info() structure if main CU
+ ICompilerProject project = getMXMLWalker().getProject();
+ if (project instanceof FlexJSProject)
+ {
+ FlexJSProject flexJSProject = (FlexJSProject) project;
- String mainDef = null;
- try {
- mainDef = flexJSProject.mainCU.getQualifiedNames().get(0);
- } catch (InterruptedException e) {
- // TODO Auto-generated catch block
- e.printStackTrace();
- }
- String thisDef = documentDefinition.getQualifiedName();
- if (mainDef != null && mainDef.equals(thisDef))
- {
- Set<String> mixins = flexJSProject.config.getIncludes();
- if (mixins.size() > 0)
- {
- String infoInject = "\n\n" + thisDef + ".prototype.info = function() {\n" +
- " return { mixins: [";
- boolean firstOne = true;
- for (String mixin : mixins)
++ if (flexJSProject.mainCU != null)
++ {
++ String mainDef = null;
++ try {
++ mainDef = flexJSProject.mainCU.getQualifiedNames().get(0);
++ } catch (InterruptedException e) {
++ // TODO Auto-generated catch block
++ e.printStackTrace();
++ }
++ String thisDef = documentDefinition.getQualifiedName();
++ if (mainDef != null && mainDef.equals(thisDef))
++ {
++ Set<String> mixins = flexJSProject.config.getIncludes();
++ if (mixins.size() > 0)
+ {
- if (!firstOne)
- infoInject += ", ";
- infoInject += mixin;
- firstOne = false;
- StringBuilder appendString = new StringBuilder();
- appendString.append(JSGoogEmitterTokens.GOOG_REQUIRE.getToken());
- appendString.append(ASEmitterTokens.PAREN_OPEN.getToken());
- appendString.append(ASEmitterTokens.SINGLE_QUOTE.getToken());
- appendString.append(mixin);
- appendString.append(ASEmitterTokens.SINGLE_QUOTE.getToken());
- appendString.append(ASEmitterTokens.PAREN_CLOSE.getToken());
- appendString.append(ASEmitterTokens.SEMICOLON.getToken());
- finalLines.add(endRequires, appendString.toString());
- //addLineToMappings(finalLines.size());
++ String infoInject = "\n\n" + thisDef + ".prototype.info = function() {\n" +
++ " return { mixins: [";
++ boolean firstOne = true;
++ for (String mixin : mixins)
++ {
++ if (!firstOne)
++ infoInject += ", ";
++ infoInject += mixin;
++ firstOne = false;
++ StringBuilder appendString = new StringBuilder();
++ appendString.append(JSGoogEmitterTokens.GOOG_REQUIRE.getToken());
++ appendString.append(ASEmitterTokens.PAREN_OPEN.getToken());
++ appendString.append(ASEmitterTokens.SINGLE_QUOTE.getToken());
++ appendString.append(mixin);
++ appendString.append(ASEmitterTokens.SINGLE_QUOTE.getToken());
++ appendString.append(ASEmitterTokens.PAREN_CLOSE.getToken());
++ appendString.append(ASEmitterTokens.SEMICOLON.getToken());
++ finalLines.add(endRequires, appendString.toString());
++ //addLineToMappings(finalLines.size());
++ }
++ infoInject += "]}};";
++ finalLines.add(infoInject);
++ //addLineToMappings(finalLines.size());
+ }
- infoInject += "]}};";
- finalLines.add(infoInject);
- //addLineToMappings(finalLines.size());
- }
++ }
+ }
+ }
+ return Joiner.on("\n").join(finalLines);
+ }
+
+ @Override
+ protected String getIndent(int numIndent)
+ {
+ final StringBuilder sb = new StringBuilder();
+ for (int i = 0; i < numIndent; i++)
+ sb.append(JSFlexJSEmitterTokens.INDENT.getToken());
+ return sb.toString();
+ }
+
+ //--------------------------------------------------------------------------
+
+ @Override
+ public void emitDeclarations(IMXMLDeclarationsNode node)
+ {
+ inMXMLContent = true;
+ MXMLDescriptorSpecifier currentInstance = getCurrentDescriptor("i");
+
+ MXMLDescriptorSpecifier currentPropertySpecifier = new MXMLDescriptorSpecifier();
+ currentPropertySpecifier.isProperty = true;
+ currentPropertySpecifier.name = "mxmlContent";
+ currentPropertySpecifier.parent = currentInstance;
+ descriptorTree.add(currentPropertySpecifier);
+ moveDown(false, currentInstance, currentPropertySpecifier);
+ super.emitDeclarations(node);
+ moveUp(false, false);
+ inMXMLContent = false;
+ }
+
+ @Override
+ public void emitDocument(IMXMLDocumentNode node)
+ {
+ descriptorTree = new ArrayList<MXMLDescriptorSpecifier>();
+ propertiesTree = new MXMLDescriptorSpecifier();
+
+ events = new ArrayList<MXMLEventSpecifier>();
+ instances = new ArrayList<MXMLDescriptorSpecifier>();
+ scripts = new ArrayList<MXMLScriptSpecifier>();
+ //styles = new ArrayList<MXMLStyleSpecifier>();
+
+ currentInstances = new ArrayList<MXMLDescriptorSpecifier>();
+ currentStateOverrides = new MXMLDescriptorSpecifier();
+ currentPropertySpecifiers = new ArrayList<MXMLDescriptorSpecifier>();
+
+ eventCounter = 0;
+ idCounter = 0;
+ bindingCounter = 0;
+
+ // visit MXML
+ IClassDefinition cdef = node.getClassDefinition();
+ classDefinition = cdef;
+ documentDefinition = cdef;
+
+ // TODO (mschmalle) will remove this cast as more things get abstracted
+ JSFlexJSEmitter fjs = (JSFlexJSEmitter) ((IMXMLBlockWalker) getMXMLWalker())
+ .getASEmitter();
+
+ fjs.getModel().setCurrentClass(cdef);
+
+ // visit tags
+ final int len = node.getChildCount();
+ for (int i = 0; i < len; i++)
+ {
+ getMXMLWalker().walk(node.getChild(i));
+ }
+
+ String cname = node.getFileNode().getName();
+
+ emitHeader(node);
+
+ emitClassDeclStart(cname, node.getBaseClassName(), false);
+
+ emitComplexInitializers(node);
+
+ emitPropertyDecls();
+
+ emitClassDeclEnd(cname, node.getBaseClassName());
+
+ emitMetaData(cdef);
+
+ write(subDocuments.toString());
+ writeNewline();
+
+ emitScripts();
+
+ fjs.getBindableEmitter().emit(cdef);
+ fjs.getAccessorEmitter().emit(cdef);
+
+ emitEvents(cname);
+
+ emitPropertyGetterSetters(cname);
+
+ emitMXMLDescriptorFuncs(cname);
+
+ emitBindingData(cname, cdef);
+ }
+
+ public void emitSubDocument(IMXMLComponentNode node)
+ {
+ ArrayList<MXMLDescriptorSpecifier> oldDescriptorTree;
+ MXMLDescriptorSpecifier oldPropertiesTree;
+ ArrayList<MXMLEventSpecifier> oldEvents;
+ ArrayList<MXMLScriptSpecifier> oldScripts;
+ ArrayList<MXMLDescriptorSpecifier> oldCurrentInstances;
+ ArrayList<MXMLDescriptorSpecifier> oldInstances;
+ ArrayList<MXMLDescriptorSpecifier> oldCurrentPropertySpecifiers;
+ int oldEventCounter;
+ int oldIdCounter;
+ boolean oldInMXMLContent;
+
+ oldDescriptorTree = descriptorTree;
+ descriptorTree = new ArrayList<MXMLDescriptorSpecifier>();
+ oldPropertiesTree = propertiesTree;
+ propertiesTree = new MXMLDescriptorSpecifier();
+
+ oldInMXMLContent = inMXMLContent;
+ inMXMLContent = false;
+ oldEvents = events;
+ events = new ArrayList<MXMLEventSpecifier>();
+ oldInstances = instances;
+ instances = new ArrayList<MXMLDescriptorSpecifier>();
+ oldScripts = scripts;
+ scripts = new ArrayList<MXMLScriptSpecifier>();
+ //styles = new ArrayList<MXMLStyleSpecifier>();
+
+ oldCurrentInstances = currentInstances;
+ currentInstances = new ArrayList<MXMLDescriptorSpecifier>();
+ oldCurrentPropertySpecifiers = currentPropertySpecifiers;
+ currentPropertySpecifiers = new ArrayList<MXMLDescriptorSpecifier>();
+
+ oldEventCounter = eventCounter;
+ eventCounter = 0;
+ oldIdCounter = idCounter;
+ idCounter = 0;
+
+ // visit MXML
+ IClassDefinition oldClassDef = classDefinition;
+ IClassDefinition cdef = node.getContainedClassDefinition();
+ classDefinition = cdef;
+ IASEmitter asEmitter = ((IMXMLBlockWalker) getMXMLWalker())
+ .getASEmitter();
+ ((JSFlexJSEmitter) asEmitter).getModel().pushClass(cdef);
+
+ IASNode classNode = node.getContainedClassDefinitionNode();
+ // visit tags
+ final int len = classNode.getChildCount();
+ for (int i = 0; i < len; i++)
+ {
+ getMXMLWalker().walk(classNode.getChild(i));
+ }
+
+ String cname = cdef.getQualifiedName();
+ subDocumentNames.add(cname);
+ ((JSFlexJSEmitter) asEmitter).mxmlEmitter = this;
+ String baseClassName = cdef.getBaseClassAsDisplayString();
+
+ emitClassDeclStart(cname, baseClassName, false);
+
+ emitComplexInitializers(classNode);
+
+ emitPropertyDecls();
+
+ emitClassDeclEnd(cname, baseClassName);
+
+ emitMetaData(cdef);
+
+ emitScripts();
+
+ emitEvents(cname);
+
+ emitPropertyGetterSetters(cname);
+
+ emitMXMLDescriptorFuncs(cname);
+
+ emitBindingData(cname, cdef);
+
+ write(((JSFlexJSEmitter) asEmitter).stringifyDefineProperties(cdef));
+
+ descriptorTree = oldDescriptorTree;
+ propertiesTree = oldPropertiesTree;
+ events = oldEvents;
+ scripts = oldScripts;
+ currentInstances = oldCurrentInstances;
+ allInstances.addAll(instances);
+ instances = oldInstances;
+ currentPropertySpecifiers = oldCurrentPropertySpecifiers;
+ eventCounter = oldEventCounter;
+ idCounter = oldIdCounter;
+ inMXMLContent = oldInMXMLContent;
+ classDefinition = oldClassDef;
+ ((JSFlexJSEmitter) asEmitter).getModel().popClass();
+ ((JSFlexJSEmitter) asEmitter).mxmlEmitter = null;
+
+ }
+
+ @Override
+ public void emitMetadata(IMXMLMetadataNode node)
+ {
+ metadataNodes.add(node);
+ }
+
+ //--------------------------------------------------------------------------
+
+ protected void emitClassDeclStart(String cname, String baseClassName,
+ boolean indent)
+ {
+ writeNewline();
+ writeNewline("/**");
+ writeNewline(" * @constructor");
+ writeNewline(" * @extends {" + formatQualifiedName(baseClassName) + "}");
+ writeNewline(" */");
+ writeToken(formatQualifiedName(cname));
+ writeToken(ASEmitterTokens.EQUAL);
+ write(ASEmitterTokens.FUNCTION);
+ write(ASEmitterTokens.PAREN_OPEN);
+ writeToken(ASEmitterTokens.PAREN_CLOSE);
+ if (indent)
+ indentPush();
+ writeNewline(ASEmitterTokens.BLOCK_OPEN, true);
+ write(formatQualifiedName(cname));
+ write(ASEmitterTokens.MEMBER_ACCESS);
+ write(JSGoogEmitterTokens.GOOG_BASE);
+ write(ASEmitterTokens.PAREN_OPEN);
+ write(ASEmitterTokens.THIS);
+ writeToken(ASEmitterTokens.COMMA);
+ write(ASEmitterTokens.SINGLE_QUOTE);
+ write(JSGoogEmitterTokens.GOOG_CONSTRUCTOR);
+ write(ASEmitterTokens.SINGLE_QUOTE);
+ write(ASEmitterTokens.PAREN_CLOSE);
+ writeNewline(ASEmitterTokens.SEMICOLON);
+ }
+
+ //--------------------------------------------------------------------------
+
+ protected void emitClassDeclEnd(String cname, String baseClassName)
+ {
+ writeNewline();
+ writeNewline("/**");
+ writeNewline(" * @private");
+ writeNewline(" * @type {Array}");
+ writeNewline(" */");
+ writeNewline("this.mxmldd;");
+
+ // top level is 'mxmlContent', skip it...
+ if (currentStateOverrides.propertySpecifiers.size() > 0)
+ {
+ MXMLDescriptorSpecifier root = currentStateOverrides;
+ root.isTopNode = true;
+
+ writeNewline("/**");
+ writeNewline(" * @export");
+ writeNewline(" * @type {Array}");
+ writeNewline(" */");
+ writeNewline("this.mxmlsd = " + ASEmitterTokens.SQUARE_OPEN.getToken());
+ indentPush();
+ write(root.outputStateDescriptors());
+ write("null");
+ write(ASEmitterTokens.SQUARE_CLOSE);
+ indentPop();
+ writeNewline(ASEmitterTokens.SEMICOLON);
+ }
+
+ writeNewline();
+ writeNewline("/**");
+ writeNewline(" * @private");
+ writeNewline(" * @type {Array}");
+ writeNewline(" */");
+
+ indentPop();
+ writeNewline("this.mxmldp;");
+
+ if (propertiesTree.propertySpecifiers.size() > 0 ||
+ propertiesTree.eventSpecifiers.size() > 0)
+ {
+ indentPush();
+ writeNewline();
+ writeNewline("this.generateMXMLAttributes");
+ write(ASEmitterTokens.PAREN_OPEN);
+ write(ASEmitterTokens.SQUARE_OPEN);
+
+ MXMLDescriptorSpecifier root = propertiesTree;
+ root.isTopNode = true;
+ writeNewline(root.output(true));
+
+ write(ASEmitterTokens.SQUARE_CLOSE);
+ write(ASEmitterTokens.PAREN_CLOSE);
+ writeNewline(ASEmitterTokens.SEMICOLON);
+ indentPop();
+ writeNewline();
+ }
+
+ write(ASEmitterTokens.BLOCK_CLOSE);
+ writeNewline(ASEmitterTokens.SEMICOLON);
+ write(JSGoogEmitterTokens.GOOG_INHERITS);
+ write(ASEmitterTokens.PAREN_OPEN);
+ write(formatQualifiedName(cname));
+ writeToken(ASEmitterTokens.COMMA);
+ write(formatQualifiedName(baseClassName));
+ write(ASEmitterTokens.PAREN_CLOSE);
+ writeNewline(ASEmitterTokens.SEMICOLON);
+ writeNewline();
+ writeNewline();
+ }
+
+ //--------------------------------------------------------------------------
+
+ protected void emitMetaData(IClassDefinition cdef)
+ {
+ String cname = cdef.getQualifiedName();
+
+ writeNewline("/**");
+ writeNewline(" * Metadata");
+ writeNewline(" *");
+ writeNewline(" * @type {Object.<string, Array.<Object>>}");
+ writeNewline(" */");
+ write(formatQualifiedName(cname) + ".prototype.FLEXJS_CLASS_INFO = { names: [{ name: '");
+ write(cdef.getBaseName());
+ write("', qName: '");
+ write(formatQualifiedName(cname));
+ write("' }]");
+ if (interfaceList != null)
+ {
+ write(", interfaces: [");
+ write(interfaceList);
+ write("]");
+ }
+ write(" };");
+
+ writeNewline();
+ writeNewline();
+ writeNewline();
+ writeNewline("/**");
+ writeNewline(" * Prevent renaming of class. Needed for reflection.");
+ writeNewline(" */");
+ write(JSFlexJSEmitterTokens.GOOG_EXPORT_SYMBOL);
+ write(ASEmitterTokens.PAREN_OPEN);
+ write(ASEmitterTokens.SINGLE_QUOTE);
+ write(formatQualifiedName(cname));
+ write(ASEmitterTokens.SINGLE_QUOTE);
+ write(ASEmitterTokens.COMMA);
+ write(ASEmitterTokens.SPACE);
+ write(formatQualifiedName(cname));
+ write(ASEmitterTokens.PAREN_CLOSE);
+ write(ASEmitterTokens.SEMICOLON);
+
+ emitReflectionData(cdef);
+ writeNewline();
+ writeNewline();
+
+ }
+
+ private void emitReflectionData(IClassDefinition cdef)
+ {
+ JSFlexJSEmitter asEmitter = (JSFlexJSEmitter)((IMXMLBlockWalker) getMXMLWalker()).getASEmitter();
+
+ ArrayList<PackageFooterEmitter.VariableData> varData = new ArrayList<PackageFooterEmitter.VariableData>();
+ // vars can only come from script blocks?
+ List<IVariableNode> vars = asEmitter.getModel().getVars();
+ for (IVariableNode varNode : vars)
+ {
+ String ns = varNode.getNamespace();
+ if (ns == IASKeywordConstants.PUBLIC)
+ {
+ PackageFooterEmitter.VariableData data = asEmitter.packageFooterEmitter.new VariableData();
+ varData.add(data);
+ data.name = varNode.getName();
+ data.type = formatQualifiedName(varNode.getVariableType());
+ IMetaTagsNode metaData = varNode.getMetaTags();
+ if (metaData != null)
+ {
+ IMetaTagNode[] tags = metaData.getAllTags();
+ if (tags.length > 0)
+ data.metaData = tags;
+ }
+ }
+ }
+
+ ArrayList<PackageFooterEmitter.MethodData> accessorData = new ArrayList<PackageFooterEmitter.MethodData>();
+ HashMap<String, PropertyNodes> accessors = asEmitter.getModel().getPropertyMap();
+ for (String propName : accessors.keySet())
+ {
+ PropertyNodes p = accessors.get(propName);
+ IFunctionNode accessorNode = p.getter;
+ if (accessorNode == null)
+ accessorNode = p.setter;
+ String ns = accessorNode.getNamespace();
+ if (ns == IASKeywordConstants.PUBLIC)
+ {
+ PackageFooterEmitter.MethodData data = asEmitter.packageFooterEmitter.new MethodData();
+ accessorData.add(data);
+ data.name = accessorNode.getName();
+ if (p.getter != null)
+ data.type = formatQualifiedName(p.getter.getReturnType());
+ else
+ data.type = formatQualifiedName(p.setter.getVariableType());
+ data.declaredBy = formatQualifiedName(cdef.getQualifiedName());
+ IMetaTagsNode metaData = accessorNode.getMetaTags();
+ if (metaData != null)
+ {
+ IMetaTagNode[] tags = metaData.getAllTags();
+ if (tags.length > 0)
+ data.metaData = tags;
+ }
+ }
+ }
+
+ for (MXMLDescriptorSpecifier instance : instances)
+ {
+ if (!instance.id.startsWith(MXMLFlexJSEmitterTokens.ID_PREFIX
+ .getToken()))
+ {
+ PackageFooterEmitter.MethodData data = asEmitter.packageFooterEmitter.new MethodData();
+ accessorData.add(data);
+ data.name = instance.id;
+ data.type = formatQualifiedName(instance.name);
+ data.declaredBy = formatQualifiedName(cdef.getQualifiedName());
+ }
+ }
+
+ ArrayList<PackageFooterEmitter.MethodData> methodData = new ArrayList<PackageFooterEmitter.MethodData>();
+ List<IFunctionNode> methods = asEmitter.getModel().getMethods();
+ for (IFunctionNode methodNode : methods)
+ {
+ String ns = methodNode.getNamespace();
+ if (ns == IASKeywordConstants.PUBLIC)
+ {
+ PackageFooterEmitter.MethodData data = asEmitter.packageFooterEmitter.new MethodData();
+ methodData.add(data);
+ data.name = methodNode.getName();
+ data.type = formatQualifiedName(methodNode.getReturnType());
+ data.declaredBy = formatQualifiedName(cdef.getQualifiedName());
+ IMetaTagsNode metaData = methodNode.getMetaTags();
+ if (metaData != null)
+ {
+ IMetaTagNode[] tags = metaData.getAllTags();
+ if (tags.length > 0)
+ data.metaData = tags;
+ }
+ }
+ }
+
+ for (MXMLEventSpecifier event : events)
+ {
+ PackageFooterEmitter.MethodData data = asEmitter.packageFooterEmitter.new MethodData();
+ methodData.add(data);
+ data.name = event.eventHandler;
+ data.type = ASEmitterTokens.VOID.getToken();
+ data.declaredBy = formatQualifiedName(cdef.getQualifiedName());
+ }
+
+ ArrayList<IMetaTagNode> metadataTagNodes = new ArrayList<IMetaTagNode>();
+ for (IMXMLMetadataNode metadataTag : metadataNodes)
+ {
+ IMetaTagNode[] tags = metadataTag.getMetaTagNodes();
+ for (IMetaTagNode tag : tags)
+ {
+ metadataTagNodes.add(tag);
+ }
+ }
+ IMetaTagNode[] metaDataTags = new IMetaTagNode[metadataTagNodes.size()];
+ asEmitter.packageFooterEmitter.emitReflectionData(formatQualifiedName(cdef.getQualifiedName()), varData,
+ accessorData, methodData, metadataTagNodes.toArray(metaDataTags));
+ }
+
+ //--------------------------------------------------------------------------
+
+ protected void emitPropertyDecls()
+ {
+ for (MXMLDescriptorSpecifier instance : instances)
+ {
+ writeNewline();
+ writeNewline("/**");
+ writeNewline(" * @private");
+ writeNewline(" * @type {" + instance.name + "}");
+ writeNewline(" */");
+ write(ASEmitterTokens.THIS);
+ write(ASEmitterTokens.MEMBER_ACCESS);
+ write(instance.id + "_");
+ writeNewline(ASEmitterTokens.SEMICOLON);
+ }
+ }
+
+ //--------------------------------------------------------------------------
+
+ protected void emitBindingData(String cname, IClassDefinition cdef)
+ {
+ BindingDatabase bd = BindingDatabase.bindingMap.get(cdef);
+ if (bd == null)
+ return;
+ if (bd.getBindingInfo().isEmpty())
+ return;
+
+ outputBindingInfoAsData(cname, bd);
+ }
+
+ private void outputBindingInfoAsData(String cname, BindingDatabase bindingDataBase)
+ {
+ IASEmitter asEmitter = ((IMXMLBlockWalker) getMXMLWalker())
+ .getASEmitter();
+
+ writeNewline("/**");
+ writeNewline(" * @export");
+ writeNewline(" */");
+ writeNewline(formatQualifiedName(cname)
+ + ".prototype._bindings = [");
+
+ Set<BindingInfo> bindingInfo = bindingDataBase.getBindingInfo();
+ writeNewline(bindingInfo.size() + ","); // number of bindings
+
+ for (BindingInfo bi : bindingInfo)
+ {
+ String s;
+ s = bi.getSourceString();
+ if (s == null)
+ s = getSourceStringFromGetter(bi.getExpressionNodesForGetter());
+ if (s.contains("."))
+ {
+ String[] parts = s.split("\\.");
+ write(ASEmitterTokens.SQUARE_OPEN.getToken() + ASEmitterTokens.DOUBLE_QUOTE.getToken() +
+ parts[0] + ASEmitterTokens.DOUBLE_QUOTE.getToken());
+ int n = parts.length;
+ for (int i = 1; i < n; i++)
+ {
+ String part = parts[i];
+ write(", " + ASEmitterTokens.DOUBLE_QUOTE.getToken() + part + ASEmitterTokens.DOUBLE_QUOTE.getToken());
+ }
+ writeNewline(ASEmitterTokens.SQUARE_CLOSE.getToken() + ASEmitterTokens.COMMA.getToken());
+ }
+ else if (s == null || s.length() == 0)
+ {
+ List<IExpressionNode> getterNodes = bi.getExpressionNodesForGetter();
+ StringBuilder sb = new StringBuilder();
+ sb.append("function() { return ");
+ int n = getterNodes.size();
+ for (int i = 0; i < n; i++)
+ {
+ IExpressionNode getterNode = getterNodes.get(i);
+ if (getterNode.getNodeID() == ASTNodeID.LiteralStringID)
+ {
+ sb.append(ASEmitterTokens.DOUBLE_QUOTE.getToken());
+ sb.append(asEmitter.stringifyNode(getterNode));
+ sb.append(ASEmitterTokens.DOUBLE_QUOTE.getToken());
+ }
+ else
+ sb.append(asEmitter.stringifyNode(getterNode));
+ if (i < n - 1)
+ sb.append(ASEmitterTokens.SPACE.getToken() + ASEmitterTokens.PLUS.getToken() + ASEmitterTokens.SPACE.getToken());
+ }
+ sb.append("; },");
+ writeNewline(sb.toString());
+ }
+ else
+ writeNewline(ASEmitterTokens.DOUBLE_QUOTE.getToken() + s +
+ ASEmitterTokens.DOUBLE_QUOTE.getToken() + ASEmitterTokens.COMMA.getToken());
+
+ IExpressionNode destNode = bi.getExpressionNodeForDestination();
+ if (destNode != null)
+ {
+ StringBuilder sb = new StringBuilder();
+ sb.append(generateSetterFunction(destNode));
+ writeNewline(sb.toString() + ASEmitterTokens.COMMA.getToken());
+ }
+ else
+ writeNewline(ASEmitterTokens.NULL.getToken() + ASEmitterTokens.COMMA.getToken());
+
+ s = bi.getDestinationString();
+ if (s == null)
+ {
+ writeNewline(ASEmitterTokens.NULL.getToken() + ASEmitterTokens.COMMA.getToken());
+ }
+ else if (s.contains("."))
+ {
+ String[] parts = s.split("\\.");
+ write(ASEmitterTokens.SQUARE_OPEN.getToken() + ASEmitterTokens.DOUBLE_QUOTE.getToken() +
+ parts[0] + ASEmitterTokens.DOUBLE_QUOTE.getToken());
+ int n = parts.length;
+ for (int i = 1; i < n; i++)
+ {
+ String part = parts[i];
+ write(", " + ASEmitterTokens.DOUBLE_QUOTE.getToken() + part + ASEmitterTokens.DOUBLE_QUOTE.getToken());
+ }
+ writeNewline(ASEmitterTokens.SQUARE_CLOSE.getToken() + ASEmitterTokens.COMMA.getToken());
+ }
+ else
+ writeNewline(ASEmitterTokens.DOUBLE_QUOTE.getToken() + s +
+ ASEmitterTokens.DOUBLE_QUOTE.getToken() + ASEmitterTokens.COMMA.getToken());
+ }
+ Set<Entry<Object, WatcherInfoBase>> watcherChains = bindingDataBase.getWatcherChains();
+ if (watcherChains != null)
+ {
+ for (Entry<Object, WatcherInfoBase> entry : watcherChains)
+ {
+ WatcherInfoBase watcherInfoBase = entry.getValue();
+ encodeWatcher(watcherInfoBase);
+ }
+ }
+ // add a trailing null for now so I don't have to have logic where the watcher figures out not to add
+ // a comma
+ writeNewline("null" + ASEmitterTokens.SQUARE_CLOSE.getToken() + ASEmitterTokens.SEMICOLON.getToken());
+ }
+
+ private String generateSetterFunction(IExpressionNode destNode) {
+ IASEmitter asEmitter = ((IMXMLBlockWalker) getMXMLWalker())
+ .getASEmitter();
+ String body = asEmitter.stringifyNode(destNode);
+
+ StringBuilder sb = new StringBuilder();
+ sb.append("function (value) { ");
+ int lastGet = body.lastIndexOf("get_");
+ int lastDot = body.lastIndexOf(".");
+ if (lastDot == lastGet - 1)
+ {
+ String object = body.substring(0, lastDot);
+ String getter = body.substring(lastDot);
+ String setter = getter.replace("get_", "set_");
+ setter = setter.replace("()", "(value)");
+ body = object + setter;
+ sb.append(body);
+ }
+ else
+ {
+ sb.append(body);
+ sb.append(" = value;");
+ }
+ sb.append(";}");
+ return sb.toString();
+ }
+
+ private void encodeWatcher(WatcherInfoBase watcherInfoBase)
+ {
+ IASEmitter asEmitter = ((IMXMLBlockWalker) getMXMLWalker())
+ .getASEmitter();
+
+ writeNewline(watcherInfoBase.getIndex() + ASEmitterTokens.COMMA.getToken());
+ WatcherType type = watcherInfoBase.getType();
+ if (type == WatcherType.FUNCTION)
+ {
+ writeNewline("0" + ASEmitterTokens.COMMA.getToken());
+
+ FunctionWatcherInfo functionWatcherInfo = (FunctionWatcherInfo)watcherInfoBase;
+
+ writeNewline(ASEmitterTokens.DOUBLE_QUOTE.getToken() + functionWatcherInfo.getFunctionName() +
+ ASEmitterTokens.DOUBLE_QUOTE.getToken());
+ IExpressionNode params[] = functionWatcherInfo.params;
+ StringBuilder sb = new StringBuilder();
+ sb.append("function() { return [");
+ boolean firstone = true;
+ for (IExpressionNode param : params)
+ {
+ if (firstone)
+ firstone = false;
+ sb.append(ASEmitterTokens.COMMA.getToken());
+ sb.append(asEmitter.stringifyNode(param));
+ }
+ sb.append("]; },");
+ outputEventNames(functionWatcherInfo.getEventNames());
+ outputBindings(functionWatcherInfo.getBindings());
+ }
+ else if ((type == WatcherType.STATIC_PROPERTY) || (type == WatcherType.PROPERTY))
+ {
+ writeNewline((type == WatcherType.STATIC_PROPERTY ? "1" : "2") +
+ ASEmitterTokens.COMMA.getToken());
+
+ PropertyWatcherInfo propertyWatcherInfo = (PropertyWatcherInfo)watcherInfoBase;
+
+ boolean makeStaticWatcher = (watcherInfoBase.getType() == WatcherType.STATIC_PROPERTY);
+
+ // round up the getter function for the watcher, or null if we don't need one
+ MethodInfo propertyGetterFunction = null;
+ if (watcherInfoBase.isRoot && !makeStaticWatcher)
+ {
+ // TODO: figure out what this looks like
+ // propertyGetterFunction = this.propertyGetter;
+ // assert propertyGetterFunction != null;
+ }
+ else if (watcherInfoBase.isRoot && makeStaticWatcher)
+ {
+ // TODO: implement getter func for static watcher.
+ }
+ writeNewline(ASEmitterTokens.DOUBLE_QUOTE.getToken() + propertyWatcherInfo.getPropertyName() +
+ ASEmitterTokens.DOUBLE_QUOTE.getToken() + ASEmitterTokens.COMMA.getToken());
+ outputEventNames(propertyWatcherInfo.getEventNames());
+ outputBindings(propertyWatcherInfo.getBindings());
+ if (propertyGetterFunction == null)
+ writeNewline("null" + ASEmitterTokens.COMMA.getToken()); // null is valid
+ if (type == WatcherType.STATIC_PROPERTY)
+ {
+ StaticPropertyWatcherInfo pwinfo = (StaticPropertyWatcherInfo)watcherInfoBase;
+ Name classMName = pwinfo.getContainingClass(getMXMLWalker().getProject());
+ writeNewline(nameToString(classMName));
+ }
+ }
+ else if (type == WatcherType.XML)
+ {
+ writeNewline("3" + ASEmitterTokens.COMMA.getToken());
+
+ XMLWatcherInfo xmlWatcherInfo = (XMLWatcherInfo)watcherInfoBase;
+ writeNewline(ASEmitterTokens.DOUBLE_QUOTE.getToken() + xmlWatcherInfo.getPropertyName() +
+ ASEmitterTokens.DOUBLE_QUOTE.getToken() + ASEmitterTokens.COMMA.getToken());
+ outputBindings(xmlWatcherInfo.getBindings());
+ }
+ else assert false;
+
+ // then recurse into children
+ Set<Entry<Object, WatcherInfoBase>> children = watcherInfoBase.getChildren();
+ if (children != null)
+ {
+ writeNewline(ASEmitterTokens.SQUARE_OPEN.getToken());
+ for ( Entry<Object, WatcherInfoBase> ent : children)
+ {
+ encodeWatcher(ent.getValue());
+ }
+ writeNewline("null" + ASEmitterTokens.SQUARE_CLOSE.getToken() + ASEmitterTokens.COMMA.getToken());
+ }
+ else
+ {
+ writeNewline("null" + ASEmitterTokens.COMMA.getToken());
+ }
+ }
+
+ private String getSourceStringFromMemberAccessExpressionNode(MemberAccessExpressionNode node)
+ {
+ String s = "";
+
+ IExpressionNode left = node.getLeftOperandNode();
+ if (left instanceof FunctionCallNode) // probably a cast
+ {
+ IASNode child = ((FunctionCallNode)left).getArgumentsNode().getChild(0);
+ if (child instanceof IdentifierNode)
+ s = getSourceStringFromIdentifierNode((IdentifierNode)child);
+ else if (child instanceof MemberAccessExpressionNode)
+ s = getSourceStringFromMemberAccessExpressionNode((MemberAccessExpressionNode)child);
+ }
+ else if (left instanceof MemberAccessExpressionNode)
+ s = getSourceStringFromMemberAccessExpressionNode((MemberAccessExpressionNode)left);
+ else if (left instanceof IdentifierNode)
+ s = getSourceStringFromIdentifierNode((IdentifierNode)left);
+ else
+ System.out.println("expected binding member access left node" + node.toString());
+ s += ".";
+
+ IExpressionNode right = node.getRightOperandNode();
+ if (right instanceof FunctionCallNode) // probably a cast
+ {
+ IASNode child = ((FunctionCallNode)right).getArgumentsNode().getChild(0);
+ if (child instanceof IdentifierNode)
+ s += getSourceStringFromIdentifierNode((IdentifierNode)child);
+ else if (child instanceof MemberAccessExpressionNode)
+ s += getSourceStringFromMemberAccessExpressionNode((MemberAccessExpressionNode)child);
+ }
+ else if (right instanceof MemberAccessExpressionNode)
+ s += getSourceStringFromMemberAccessExpressionNode((MemberAccessExpressionNode)right);
+ else if (right instanceof IdentifierNode)
+ s += getSourceStringFromIdentifierNode((IdentifierNode)right);
+ else
+ System.out.println("expected binding member access right node" + node.toString());
+
+ return s;
+ }
+
+ private String getSourceStringFromIdentifierNode(IdentifierNode node)
+ {
+ return node.getName();
+ }
+
+ private String getSourceStringFromGetter(List<IExpressionNode> nodes)
+ {
+ String s = "";
+ IExpressionNode node = nodes.get(0);
+ if (node instanceof MemberAccessExpressionNode)
+ {
+ s = getSourceStringFromMemberAccessExpressionNode((MemberAccessExpressionNode)node);
+ }
+ else if (node instanceof IdentifierNode)
+ {
+ s = ((IdentifierNode)node).getName();
+ }
+ return s;
+ }
+
+ private void outputEventNames(List<String> events)
+ {
+ if (events.size() > 1)
+ {
+ int n = events.size();
+ write(ASEmitterTokens.SQUARE_OPEN.getToken() + ASEmitterTokens.DOUBLE_QUOTE.getToken() +
+ events.get(0) + ASEmitterTokens.DOUBLE_QUOTE.getToken());
+ for (int i = 1; i < n; i++)
+ {
+ String event = events.get(i);
+ write(ASEmitterTokens.COMMA.getToken() + ASEmitterTokens.DOUBLE_QUOTE.getToken() +
+ event + ASEmitterTokens.DOUBLE_QUOTE.getToken());
+ }
+ writeNewline(ASEmitterTokens.SQUARE_CLOSE.getToken() + ASEmitterTokens.COMMA.getToken());
+ }
+ else if (events.size() == 1)
+ writeNewline(ASEmitterTokens.DOUBLE_QUOTE.getToken() + events.get(0) +
+ ASEmitterTokens.DOUBLE_QUOTE.getToken() + ASEmitterTokens.COMMA.getToken());
+ else
+ writeNewline("null" + ASEmitterTokens.COMMA.getToken());
+ }
+
+ private void outputBindings(List<BindingInfo> bindings)
+ {
+ if (bindings.size() > 1)
+ {
+ int n = bindings.size();
+ write(ASEmitterTokens.SQUARE_OPEN.getToken() + bindings.get(0).getIndex());
+ for (int i = 1; i < n; i++)
+ {
+ BindingInfo binding = bindings.get(i);
+ write(ASEmitterTokens.COMMA.getToken() + binding.getIndex());
+ }
+ writeNewline(ASEmitterTokens.SQUARE_CLOSE.getToken() + ASEmitterTokens.COMMA.getToken());
+ }
+ else if (bindings.size() == 1)
+ writeNewline(bindings.get(0).getIndex() + ASEmitterTokens.COMMA.getToken());
+ else
+ writeNewline("null" + ASEmitterTokens.COMMA.getToken());
+
+ }
+
+ //--------------------------------------------------------------------------
+
+ protected void emitScripts()
+ {
+ for (MXMLScriptSpecifier script : scripts)
+ {
+ String output = script.output();
+
+ if (!output.equals(""))
+ {
+ writeNewline(output);
+ }
+ }
+ }
+
+ //--------------------------------------------------------------------------
+
+ protected void emitEvents(String cname)
+ {
+ for (MXMLEventSpecifier event : events)
+ {
+ writeNewline("/**");
+ writeNewline(" * @export");
+ writeNewline(" * @param {" + formatQualifiedName(event.type) + "} event");
+ writeNewline(" */");
+ writeNewline(formatQualifiedName(cname)
+ + ".prototype." + event.eventHandler + " = function(event)");
+ writeNewline(ASEmitterTokens.BLOCK_OPEN, true);
+
+ writeNewline(event.value + ASEmitterTokens.SEMICOLON.getToken(),
+ false);
+
+ write(ASEmitterTokens.BLOCK_CLOSE);
+ writeNewline(";");
+ writeNewline();
+ writeNewline();
+ }
+ }
+
+ //--------------------------------------------------------------------------
+
+ protected void emitPropertyGetterSetters(String cname)
+ {
+ int n = 0;
+ for (MXMLDescriptorSpecifier instance : instances)
+ {
+ if (!instance.id.startsWith(MXMLFlexJSEmitterTokens.ID_PREFIX
+ .getToken()))
+ {
+ n++;
+ }
+ }
+ if (n == 0 && descriptorTree.size() == 0)
+ return;
+
+ String formattedCName = formatQualifiedName(cname);
+
+ write("Object.defineProperties(");
+ write(formattedCName);
+ writeNewline(".prototype, /** @lends {" + formattedCName + ".prototype} */ {");
+ indentPush();
+ int i = 0;
+ for (MXMLDescriptorSpecifier instance : instances)
+ {
+ if (!instance.id.startsWith(MXMLFlexJSEmitterTokens.ID_PREFIX
+ .getToken()))
+ {
+ indentPush();
+ writeNewline("/** @export */");
+ writeNewline(instance.id + ": {");
+ writeNewline("/** @this {" + formattedCName + "} */");
+ indentPush();
+ writeNewline("get: function() {");
+ indentPop();
+ writeNewline("return this." + instance.id + "_;");
+ writeNewline("},");
+ writeNewline("/** @this {" + formattedCName + "} */");
+ indentPush();
+ writeNewline("set: function(value) {");
+ indentPush();
+ writeNewline("if (value != this." + instance.id + "_) {");
+ writeNewline("this." + instance.id + "_ = value;");
+ write("this.dispatchEvent(org.apache.flex.events.ValueChangeEvent.createUpdateEvent(this, '");
+ indentPop();
+ writeNewline(instance.id + "', null, value));");
+ indentPop();
+ writeNewline("}");
+ indentPop();
+ writeNewline("}");
+ if (i < n - 1 || descriptorTree.size() > 0)
+ writeNewline("},");
+ else
+ {
+ indentPop();
+ writeNewline("}");
+ }
+ i++;
+ }
+ }
+ if (descriptorTree.size() == 0)
+ writeNewline("});");
+ }
+
+ //--------------------------------------------------------------------------
+
+ protected void emitMXMLDescriptorFuncs(String cname)
+ {
+ // top level is 'mxmlContent', skip it...
+ if (descriptorTree.size() > 0)
+ {
+ FlexJSProject project = (FlexJSProject) getMXMLWalker().getProject();
+ project.needLanguage = true;
+ MXMLDescriptorSpecifier root = descriptorTree.get(0);
+ root.isTopNode = false;
+
+ indentPush();
+ writeNewline("'MXMLDescriptor': {");
+ writeNewline("/** @this {" + formatQualifiedName(cname) + "} */");
+ indentPush();
+ writeNewline("get: function() {");
+ indentPush();
+ writeNewline("{");
+ writeNewline("if (this.mxmldd == undefined)");
+ indentPush();
+ writeNewline("{");
+ writeNewline("/** @type {Array} */");
+ writeNewline("var arr = org.apache.flex.utils.Language.superGetter(" + formatQualifiedName(cname) + ",this, 'MXMLDescriptor');");
+ writeNewline("/** @type {Array} */");
+ indentPop();
+ indentPop();
+ writeNewline("var data = [");
+
+ writeNewline(root.output(true));
+
+ indentPush();
+ writeNewline("];");
+ indentPush();
+ writeNewline("");
+ indentPush();
+ writeNewline("if (arr)");
+ indentPop();
+ writeNewline("this.mxmldd = arr.concat(data);");
+ indentPush();
+ writeNewline("else");
+ indentPop();
+ indentPop();
+ writeNewline("this.mxmldd = data;");
+ writeNewline("}");
+ indentPop();
+ writeNewline("return this.mxmldd;");
+ writeNewline("}");
+ indentPop();
+ writeNewline("}");
+ indentPop();
+ writeNewline("}");
+ writeNewline("});");
+ }
+
+ }
+
+ //--------------------------------------------------------------------------
+
+ private HashMap<IMXMLEventSpecifierNode, String> eventHandlerNameMap = new HashMap<IMXMLEventSpecifierNode, String>();
+
+ @Override
+ public void emitEventSpecifier(IMXMLEventSpecifierNode node)
+ {
+ if (isStateDependent(node) && !inStatesOverride)
+ return;
+
+ IDefinition cdef = node.getDefinition();
+
+ MXMLDescriptorSpecifier currentDescriptor = getCurrentDescriptor("i");
+
+ MXMLEventSpecifier eventSpecifier = new MXMLEventSpecifier();
+ eventSpecifier.eventHandler = MXMLFlexJSEmitterTokens.EVENT_PREFIX
+ .getToken() + eventCounter++;
+ eventSpecifier.name = cdef.getBaseName();
+ eventSpecifier.type = node.getEventParameterDefinition()
+ .getTypeAsDisplayString();
+
+ eventHandlerNameMap.put(node, eventSpecifier.eventHandler);
+
+ IASEmitter asEmitter = ((IMXMLBlockWalker) getMXMLWalker())
+ .getASEmitter();
+
+ StringBuilder sb = null;
+ int len = node.getChildCount();
+ if (len > 0)
+ {
+ sb = new StringBuilder();
+ for (int i = 0; i < len; i++)
+ {
+ sb.append(getIndent((i > 0) ? 1 : 0)
+ + asEmitter.stringifyNode(node.getChild(i)));
+ if (i < len - 1)
+ {
+ sb.append(ASEmitterTokens.SEMICOLON.getToken());
+ sb.append(ASEmitterTokens.NEW_LINE.getToken());
+ }
+ }
+ }
+ eventSpecifier.value = sb.toString();
+
+ if (currentDescriptor != null)
+ currentDescriptor.eventSpecifiers.add(eventSpecifier);
+ else if (!inStatesOverride) // in theory, if no currentdescriptor must be top tag event
+ propertiesTree.eventSpecifiers.add(eventSpecifier);
+ events.add(eventSpecifier);
+ }
+
+ @Override
+ public void emitInstance(IMXMLInstanceNode node)
+ {
+ if (isStateDependent(node) && !inStatesOverride)
+ return;
+
+ IClassDefinition cdef = node
+ .getClassReference((ICompilerProject) getMXMLWalker()
+ .getProject());
+
+ MXMLDescriptorSpecifier currentPropertySpecifier = getCurrentDescriptor("ps");
+
+ String id = node.getID();
+ if (id == null)
+ id = node.getEffectiveID();
+ if (id == null)
+ id = MXMLFlexJSEmitterTokens.ID_PREFIX.getToken() + idCounter++;
+
+ MXMLDescriptorSpecifier currentInstance = new MXMLDescriptorSpecifier();
+ currentInstance.isProperty = false;
+ currentInstance.id = id;
+ currentInstance.name = formatQualifiedName(cdef.getQualifiedName());
+ currentInstance.parent = currentPropertySpecifier;
+
+ if (currentPropertySpecifier != null)
+ currentPropertySpecifier.propertySpecifiers.add(currentInstance);
+ else if (inMXMLContent)
+ descriptorTree.add(currentInstance);
+ else
+ {
+ currentInstance.parent = propertiesTree;
+ propertiesTree.propertySpecifiers.add(currentInstance);
+ }
+
+ instances.add(currentInstance);
+
+ IMXMLPropertySpecifierNode[] pnodes = node.getPropertySpecifierNodes();
+ if (pnodes != null)
+ {
+ moveDown(false, currentInstance, null);
+
+ for (IMXMLPropertySpecifierNode pnode : pnodes)
+ {
+ getMXMLWalker().walk(pnode); // Property Specifier
+ }
+
+ moveUp(false, true);
+ }
+ else if (node instanceof IMXMLStateNode)
+ {
+ IMXMLStateNode stateNode = (IMXMLStateNode)node;
+ String name = stateNode.getStateName();
+ if (name != null)
+ {
+ MXMLDescriptorSpecifier stateName = new MXMLDescriptorSpecifier();
+ stateName.isProperty = true;
+ stateName.id = id;
+ stateName.name = "name";
+ stateName.value = ASEmitterTokens.SINGLE_QUOTE.getToken() + name + ASEmitterTokens.SINGLE_QUOTE.getToken();
+ stateName.parent = currentInstance;
+ currentInstance.propertySpecifiers.add(stateName);
+ }
+ MXMLDescriptorSpecifier overrides = new MXMLDescriptorSpecifier();
+ overrides.isProperty = true;
+ overrides.hasArray = true;
+ overrides.id = id;
+ overrides.name = "overrides";
+ overrides.parent = currentInstance;
+ currentInstance.propertySpecifiers.add(overrides);
+ moveDown(false, null, overrides);
+
+ IMXMLClassDefinitionNode classDefinitionNode = stateNode.getClassDefinitionNode();
+ List<IMXMLNode> snodes = classDefinitionNode.getNodesDependentOnState(stateNode.getStateName());
+ if (snodes != null)
+ {
+ for (int i=snodes.size()-1; i>=0; --i)
+ {
+ IMXMLNode inode = snodes.get(i);
+ if (inode.getNodeID() == ASTNodeID.MXMLInstanceID)
+ {
+ emitInstanceOverride((IMXMLInstanceNode)inode);
+ }
+ }
+ // Next process the non-instance overrides dependent on this state.
+ // Each one will generate code to push an IOverride instance.
+ for (IMXMLNode anode : snodes)
+ {
+ switch (anode.getNodeID())
+ {
+ case MXMLPropertySpecifierID:
+ {
+ emitPropertyOverride((IMXMLPropertySpecifierNode)anode);
+ break;
+ }
+ case MXMLStyleSpecifierID:
+ {
+ emitStyleOverride((IMXMLStyleSpecifierNode)anode);
+ break;
+ }
+ case MXMLEventSpecifierID:
+ {
+ emitEventOverride((IMXMLEventSpecifierNode)anode);
+ break;
+ }
+ default:
+ {
+ break;
+ }
+ }
+ }
+ }
+
+ moveUp(false, false);
+ }
+
+ IMXMLEventSpecifierNode[] enodes = node.getEventSpecifierNodes();
+ if (enodes != null)
+ {
+ moveDown(false, currentInstance, null);
+
+ for (IMXMLEventSpecifierNode enode : enodes)
+ {
+ getMXMLWalker().walk(enode); // Event Specifier
+ }
+
+ moveUp(false, true);
+ }
+ }
+
+ public void emitPropertyOverride(IMXMLPropertySpecifierNode propertyNode)
+ {
+ FlexProject project = (FlexProject) getMXMLWalker().getProject();
+ Name propertyOverride = project.getPropertyOverrideClassName();
+ emitPropertyOrStyleOverride(propertyOverride, propertyNode);
+ }
+
+ /**
+ * Generates instructions in the current context
+ * to create an instance of mx.states.SetStyle
+ * with its <code>target</code>, <code>name</code>,
+ * and <code>value</code> properties set.
+ */
+ void emitStyleOverride(IMXMLStyleSpecifierNode styleNode)
+ {
+ FlexProject project = (FlexProject) getMXMLWalker().getProject();
+ Name styleOverride = project.getStyleOverrideClassName();
+ emitPropertyOrStyleOverride(styleOverride, styleNode);
+ }
+
+ void emitPropertyOrStyleOverride(Name overrideName, IMXMLPropertySpecifierNode propertyOrStyleNode)
+ {
+ MXMLDescriptorSpecifier currentInstance = getCurrentDescriptor("ps");
+ IASNode parentNode = propertyOrStyleNode.getParent();
+ String id = parentNode instanceof IMXMLInstanceNode ?
+ ((IMXMLInstanceNode)parentNode).getEffectiveID() :
+ null;
+
+ String name = propertyOrStyleNode.getName();
+
+ boolean valueIsDataBound = isDataBindingNode(propertyOrStyleNode.getChild(0));
+ IMXMLInstanceNode propertyOrStyleValueNode = propertyOrStyleNode.getInstanceNode();
+
+ MXMLDescriptorSpecifier setProp = new MXMLDescriptorSpecifier();
+ setProp.isProperty = false;
+ setProp.name = formatQualifiedName(nameToString(overrideName));
+ setProp.parent = currentInstance;
+ currentInstance.propertySpecifiers.add(setProp);
+
+ if (id != null)
+ {
+ // Set its 'target' property to the id of the object
+ // whose property or style this override will set.
+ MXMLDescriptorSpecifier target = new MXMLDescriptorSpecifier();
+ target.isProperty = true;
+ target.name = "target";
+ target.parent = setProp;
+ target.value = ASEmitterTokens.SINGLE_QUOTE.getToken() + id + ASEmitterTokens.SINGLE_QUOTE.getToken();
+ setProp.propertySpecifiers.add(target);
+ }
+
+ // Set its 'name' property to the name of the property or style.
+ MXMLDescriptorSpecifier pname = new MXMLDescriptorSpecifier();
+ pname.isProperty = true;
+ pname.name = "name";
+ pname.parent = setProp;
+ pname.value = ASEmitterTokens.SINGLE_QUOTE.getToken() + name + ASEmitterTokens.SINGLE_QUOTE.getToken();
+ setProp.propertySpecifiers.add(pname);
+
+ if (!valueIsDataBound)
+ {
+ // Set its 'value' property to the value of the property or style.
+ MXMLDescriptorSpecifier value = new MXMLDescriptorSpecifier();
+ value.isProperty = true;
+ value.name = "value";
+ value.parent = setProp;
+ setProp.propertySpecifiers.add(value);
+ moveDown(false, null, value);
+ getMXMLWalker().walk(propertyOrStyleValueNode); // instance node
+ moveUp(false, false);
+ }
+ else
+ {
+ String overrideID = MXMLFlexJSEmitterTokens.BINDING_PREFIX.getToken() + bindingCounter++;
+ setProp.id = overrideID;
+ instances.add(setProp);
+ BindingDatabase bd = BindingDatabase.bindingMap.get(classDefinition);
+ Set<BindingInfo> bindingInfo = bd.getBindingInfo();
+ IMXMLDataBindingNode bindingNode = (IMXMLDataBindingNode)propertyOrStyleNode.getChild(0);
+ for (BindingInfo bi : bindingInfo)
+ {
+ if (bi.node == bindingNode)
+ {
+ bi.setDestinationString(overrideID + ".value");
+ break;
+ }
+ }
+ }
+ }
+
+ /**
+ * Generates instructions in the current context
+ * to create an instance of mx.states.SetEventHandler
+ * with its <code>target</code>, <code>name</code>,
+ * and <code>handlerFunction</code> properties set.
+ */
+ void emitEventOverride(IMXMLEventSpecifierNode eventNode)
+ {
+ inStatesOverride = true;
+
+ MXMLDescriptorSpecifier currentInstance = getCurrentDescriptor("ps");
+ FlexProject project = (FlexProject) getMXMLWalker().getProject();
+ Name eventOverride = project.getEventOverrideClassName();
+
+ IASNode parentNode = eventNode.getParent();
+ String id = parentNode instanceof IMXMLInstanceNode ?
+ ((IMXMLInstanceNode)parentNode).getEffectiveID() :
+ "";
+
+ String name = MXMLEventSpecifier.getJSEventName(eventNode.getName());
+
+ String eventHandler = eventHandlerNameMap.get(eventNode);
+ if (eventHandler == null)
+ {
+ emitEventSpecifier(eventNode);
+ eventHandler = eventHandlerNameMap.get(eventNode);
+ }
+
+ MXMLDescriptorSpecifier setEvent = new MXMLDescriptorSpecifier();
+ setEvent.isProperty = false;
+ setEvent.name = formatQualifiedName(nameToString(eventOverride));
+ setEvent.parent = currentInstance;
+ currentInstance.propertySpecifiers.add(setEvent);
+ // Set its 'target' property to the id of the object
+ // whose event this override will set.
+ MXMLDescriptorSpecifier target = new MXMLDescriptorSpecifier();
+ target.isProperty = true;
+ target.name = "target";
+ target.parent = setEvent;
+ target.value = ASEmitterTokens.SINGLE_QUOTE.getToken() + id + ASEmitterTokens.SINGLE_QUOTE.getToken();
+ setEvent.propertySpecifiers.add(target);
+
+ // Set its 'name' property to the name of the event.
+ MXMLDescriptorSpecifier pname = new MXMLDescriptorSpecifier();
+ pname.isProperty = true;
+ pname.name = "name";
+ pname.parent = setEvent;
+ pname.value = ASEmitterTokens.SINGLE_QUOTE.getToken() + name + ASEmitterTokens.SINGLE_QUOTE.getToken();
+ setEvent.propertySpecifiers.add(pname);
+
+ // Set its 'handlerFunction' property to the autogenerated event handler.
+ MXMLDescriptorSpecifier handler = new MXMLDescriptorSpecifier();
+ handler.isProperty = true;
+ handler.name = "handlerFunction";
+ handler.parent = setEvent;
+ handler.value = JSFlexJSEmitterTokens.CLOSURE_FUNCTION_NAME.getToken() + ASEmitterTokens.PAREN_OPEN.getToken() +
+ ASEmitterTokens.THIS.getToken() + ASEmitterTokens.MEMBER_ACCESS.getToken() + eventHandler +
+ ASEmitterTokens.COMMA.getToken() + ASEmitterTokens.SPACE.getToken() + ASEmitterTokens.THIS.getToken() +
+ ASEmitterTokens.COMMA.getToken() + ASEmitterTokens.SPACE.getToken() + ASEmitterTokens.SINGLE_QUOTE.getToken() +
+ eventHandler + ASEmitterTokens.SINGLE_QUOTE.getToken() +
+ ASEmitterTokens.PAREN_CLOSE.getToken();
+ setEvent.propertySpecifiers.add(handler);
+
+ inStatesOverride = false;
+ }
+
+ public void emitInstanceOverride(IMXMLInstanceNode instanceNode)
+ {
+ inStatesOverride = true;
+
+ MXMLDescriptorSpecifier currentInstance = getCurrentDescriptor("ps");
+ FlexProject project = (FlexProject) getMXMLWalker().getProject();
+ Name instanceOverrideName = project.getInstanceOverrideClassName();
+
+ MXMLDescriptorSpecifier overrideInstances = getCurrentDescriptor("so");
+ int index = overrideInstances.propertySpecifiers.size();
+ if (nodeToIndexMap == null)
+ nodeToIndexMap = new HashMap<IMXMLNode, Integer>();
+ if (nodeToIndexMap.containsKey(instanceNode))
+ {
+ index = nodeToIndexMap.get(instanceNode);
+ }
+ else
+ {
+ nodeToIndexMap.put(instanceNode, index);
+ MXMLDescriptorSpecifier itemsDesc = new MXMLDescriptorSpecifier();
+ itemsDesc.isProperty = true;
+ itemsDesc.hasArray = true;
+ itemsDesc.name = "itemsDescriptor";
+ itemsDesc.parent = overrideInstances;
+ overrideInstances.propertySpecifiers.add(itemsDesc);
+ boolean oldInMXMLContent = inMXMLContent;
+ moveDown(false, null, itemsDesc);
+ inMXMLContent = true;
+ getMXMLWalker().walk(instanceNode); // instance node
+ inMXMLContent = oldInMXMLContent;
+ moveUp(false, false);
+ }
+
+ MXMLDescriptorSpecifier addItems = new MXMLDescriptorSpecifier();
+ addItems.isProperty = false;
+ addItems.name = formatQualifiedName(nameToString(instanceOverrideName));
+ addItems.parent = currentInstance;
+ currentInstance.propertySpecifiers.add(addItems);
+ MXMLDescriptorSpecifier itemsDescIndex = new MXMLDescriptorSpecifier();
+ itemsDescIndex.isProperty = true;
+ itemsDescIndex.hasArray = true;
+ itemsDescIndex.name = "itemsDescriptorIndex";
+ itemsDescIndex.parent = addItems;
+ itemsDescIndex.value = Integer.toString(index);
+ addItems.propertySpecifiers.add(itemsDescIndex);
+
+ //-----------------------------------------------------------------------------
+ // Second property set: maybe set destination and propertyName
+
+ // get the property specifier node for the property the instanceNode represents
+ IMXMLPropertySpecifierNode propertySpecifier = (IMXMLPropertySpecifierNode)
+ instanceNode.getAncestorOfType( IMXMLPropertySpecifierNode.class);
+
+ if (propertySpecifier == null)
+ {
+ assert false; // I think this indicates an invalid tree...
+ }
+ else
+ {
+ // Check the parent - if it's an instance then we want to use these
+ // nodes to get our property values from. If not, then it's the root
+ // and we don't need to specify destination
+
+ IASNode parent = propertySpecifier.getParent();
+ if (parent instanceof IMXMLInstanceNode)
+ {
+ IMXMLInstanceNode parentInstance = (IMXMLInstanceNode)parent;
+ String parentId = parentInstance.getEffectiveID();
+ assert parentId != null;
+ String propName = propertySpecifier.getName();
+
+ MXMLDescriptorSpecifier dest = new MXMLDescriptorSpecifier();
+ dest.isProperty = true;
+ dest.name = "destination";
+ dest.parent = addItems;
+ dest.value = ASEmitterTokens.SINGLE_QUOTE.getToken() + parentId + ASEmitterTokens.SINGLE_QUOTE.getToken();
+ addItems.propertySpecifiers.add(dest);
+
+ MXMLDescriptorSpecifier prop = new MXMLDescriptorSpecifier();
+ prop.isProperty = true;
+ prop.name = "propertyName";
+ prop.parent = addItems;
+ prop.value = ASEmitterTokens.SINGLE_QUOTE.getToken() + propName + ASEmitterTokens.SINGLE_QUOTE.getToken();
+ addItems.propertySpecifiers.add(prop);
+ }
+ }
+
+ //---------------------------------------------------------------
+ // Third property set: position and relativeTo
+ String positionPropertyValue = null;
+ String relativeToPropertyValue = null;
+
+ // look to see if we have any sibling nodes that are not state dependent
+ // that come BEFORE us
+ IASNode instanceParent = instanceNode.getParent();
+ IASNode prevStatelessSibling=null;
+ for (int i=0; i< instanceParent.getChildCount(); ++i)
+ {
+ IASNode sib = instanceParent.getChild(i);
+ assert sib instanceof IMXMLInstanceNode; // surely our siblings are also instances?
+
+ // stop looking for previous nodes when we find ourself
+ if (sib == instanceNode)
+ break;
+
+ if (sib instanceof IMXMLInstanceNode && !isStateDependent(sib))
+ {
+ prevStatelessSibling = sib;
+ }
+ }
+
+ if (prevStatelessSibling == null) {
+ positionPropertyValue = "first"; // TODO: these should be named constants
+ }
+ else {
+ positionPropertyValue = "after";
+ relativeToPropertyValue = ((IMXMLInstanceNode)prevStatelessSibling).getEffectiveID();
+ }
+
+ MXMLDescriptorSpecifier pos = new MXMLDescriptorSpecifier();
+ pos.isProperty = true;
+ pos.name = "position";
+ pos.parent = addItems;
+ pos.value = ASEmitterTokens.SINGLE_QUOTE.getToken() + positionPropertyValue + ASEmitterTokens.SINGLE_QUOTE.getToken();
+ addItems.propertySpecifiers.add(pos);
+
+ if (relativeToPropertyValue != null)
+ {
+ MXMLDescriptorSpecifier rel = new MXMLDescriptorSpecifier();
+ rel.isProperty = true;
+ rel.name = "relativeTo";
+ rel.parent = addItems;
+ rel.value = ASEmitterTokens.SINGLE_QUOTE.getToken() + relativeToPropertyValue + ASEmitterTokens.SINGLE_QUOTE.getToken();
+ addItems.propertySpecifiers.add(rel);
+ }
+
+ inStatesOverride = false;
+ }
+
+ private String nameToString(Name name)
+ {
+ String s = "";
+ Namespace ns = name.getSingleQualifier();
+ s = ns.getName() + ASEmitterTokens.MEMBER_ACCESS.getToken() + name.getBaseName();
+ return s;
+ }
+ /**
+ * Determines whether a node is state-dependent.
+ * TODO: we should move to IMXMLNode
+ */
+ protected boolean isStateDependent(IASNode node)
+ {
+ if (node instanceof IMXMLSpecifierNode)
+ {
+ String suffix = ((IMXMLSpecifierNode)node).getSuffix();
+ return suffix != null && suffix.length() > 0;
+ }
+ else if (isStateDependentInstance(node))
+ return true;
+ return false;
+ }
+
+ /**
+ * Determines whether the geven node is an instance node, as is state dependent
+ */
+ protected boolean isStateDependentInstance(IASNode node)
+ {
+ if (node instanceof IMXMLInstanceNode)
+ {
+ String[] includeIn = ((IMXMLInstanceNode)node).getIncludeIn();
+ String[] excludeFrom = ((IMXMLInstanceNode)node).getExcludeFrom();
+ return includeIn != null || excludeFrom != null;
+ }
+ return false;
+ }
+
+ /**
+ * Is a give node a "databinding node"?
+ */
+ public static boolean isDataBindingNode(IASNode node)
+ {
+ return node instanceof IMXMLDataBindingNode;
+ }
+
+ protected static boolean isDataboundProp(IMXMLPropertySpecifierNode propertyNode)
+ {
+ boolean ret = propertyNode.getChildCount() > 0 && isDataBindingNode(propertyNode.getInstanceNode());
+
+ // Sanity check that we based our conclusion about databinding on the correct node.
+ // (code assumes only one child if databinding)
+ int n = propertyNode.getChildCount();
+ for (int i = 0; i < n; i++)
+ {
+ boolean db = isDataBindingNode(propertyNode.getChild(i));
+ assert db == ret;
+ }
+
+ return ret;
+ }
+
+ @Override
+ public void emitPropertySpecifier(IMXMLPropertySpecifierNode node)
+ {
+ if (isDataboundProp(node))
+ return;
+
+ if (isStateDependent(node))
+ return;
+
+ IDefinition cdef = node.getDefinition();
+
+ IASNode cnode = node.getChild(0);
+
+ MXMLDescriptorSpecifier currentInstance = getCurrentDescriptor("i");
+
+ MXMLDescriptorSpecifier currentPropertySpecifier = new MXMLDescriptorSpecifier();
+ currentPropertySpecifier.isProperty = true;
+ currentPropertySpecifier.name = cdef.getQualifiedName();
+ currentPropertySpecifier.parent = currentInstance;
+
+ boolean oldInMXMLContent = inMXMLContent;
+ boolean reusingDescriptor = false;
+ if (currentPropertySpecifier.name.equals("mxmlContent"))
+ {
+ inMXMLContent = true;
+ ArrayList<MXMLDescriptorSpecifier> specList =
+ (currentInstance == null) ? descriptorTree : currentInstance.propertySpecifiers;
+ for (MXMLDescriptorSpecifier ds : specList)
+ {
+ if (ds.name.equals("mxmlContent"))
+ {
+ currentPropertySpecifier = ds;
+ reusingDescriptor = true;
+ break;
+ }
+ }
+ }
+
+ if (currentInstance != null)
+ {
+ // we end up here for children of tags
+ if (!reusingDescriptor)
+ currentInstance.propertySpecifiers.add(currentPropertySpecifier);
+ }
+ else if (inMXMLContent)
+ {
+ // we end up here for top tags?
+ if (!reusingDescriptor)
+ descriptorTree.add(currentPropertySpecifier);
+ }
+ else
+ {
+ currentPropertySpecifier.parent = propertiesTree;
+ propertiesTree.propertySpecifiers.add(currentPropertySpecifier);
+ }
+
+ boolean valueIsArray = cnode != null && cnode instanceof IMXMLArrayNode;
+ boolean valueIsObject = cnode != null && cnode instanceof IMXMLObjectNode;
+
+ currentPropertySpecifier.hasArray = valueIsArray;
+ currentPropertySpecifier.hasObject = valueIsObject;
+
+ moveDown(valueIsArray || valueIsObject, null, currentPropertySpecifier);
+
+ getMXMLWalker().walk(cnode); // Array or Instance
+
+ moveUp(valueIsArray || valueIsObject, false);
+
+ inMXMLContent = oldInMXMLContent;
+ }
+
+ @Override
+ public void emitScript(IMXMLScriptNode node)
+ {
+ IASEmitter asEmitter = ((IMXMLBlockWalker) getMXMLWalker())
+ .getASEmitter();
+
+ String nl = ASEmitterTokens.NEW_LINE.getToken();
+
+ StringBuilder sb = null;
+ MXMLScriptSpecifier scriptSpecifier = null;
+
+ int len = node.getChildCount();
+ if (len > 0)
+ {
+ for (int i = 0; i < len; i++)
+ {
+ IASNode cnode = node.getChild(i);
+
+ if (!(cnode instanceof IImportNode))
+ {
+ sb = new StringBuilder();
+ scriptSpecifier = new MXMLScriptSpecifier();
+
+ sb.append(asEmitter.stringifyNode(cnode));
+
+ sb.append(ASEmitterTokens.SEMICOLON.getToken());
+
+ if (i == len - 1)
+ indentPop();
+
+ sb.append(nl);
+ sb.append(nl);
+
+ scriptSpecifier.fragment = sb.toString();
+
+ scripts.add(scriptSpecifier);
+ }
+ }
+ }
+ }
+
+ @Override
+ public void emitStyleSpecifier(IMXMLStyleSpecifierNode node)
+ {
+ }
+
+ //--------------------------------------------------------------------------
+
+ @Override
+ public void emitObject(IMXMLObjectNode node)
+ {
+ final int len = node.getChildCount();
+ if (!makingSimpleArray)
+ {
+ for (int i = 0; i < len; i++)
+ {
+ getMXMLWalker().walk(node.getChild(i)); // props in object
+ }
+ }
+ else
+ {
+ MXMLDescriptorSpecifier ps = getCurrentDescriptor("ps");
+ if (ps.value == null)
+ ps.value = "";
+ ps.value += "{";
+ for (int i = 0; i < len; i++)
+ {
+ IMXMLPropertySpecifierNode propName = (IMXMLPropertySpecifierNode)node.getChild(i);
+ ps.value += propName.getName() + ": ";
+ getMXMLWalker().walk(propName.getChild(0));
+ if (i < len - 1)
+ ps.value += ", ";
+ }
+ ps.value += "}";
+ }
+ }
+
+ @Override
+ public void emitArray(IMXMLArrayNode node)
+ {
+ moveDown(false, null, null);
+
+ boolean isSimple = true;
+ final int len = node.getChildCount();
+ for (int i = 0; i < len; i++)
+ {
+ final IASNode child = node.getChild(i);
+ ASTNodeID nodeID = child.getNodeID();
+ if (nodeID == ASTNodeID.MXMLArrayID || nodeID == ASTNodeID.MXMLInstanceID || nodeID == ASTNodeID.MXMLStateID)
+ {
+ isSimple = false;
+ break;
+ }
+ }
+ boolean oldMakingSimpleArray = makingSimpleArray;
+ MXMLDescriptorSpecifier ps = getCurrentDescriptor("ps");
+ if (isSimple)
+ {
+ makingSimpleArray = true;
+ ps.value = ASEmitterTokens.SQUARE_OPEN.getToken();
+ }
+ for (int i = 0; i < len; i++)
+ {
+ getMXMLWalker().walk(node.getChild(i)); // Instance
+ if (isSimple && i < len - 1)
+ ps.value += ASEmitterTokens.COMMA.getToken();
+ }
+ if (isSimple)
+ {
+ ps.value += ASEmitterTokens.SQUARE_CLOSE.getToken();
+ }
+ makingSimpleArray = oldMakingSimpleArray;
+
+ moveUp(false, false);
+ }
+
+ @Override
+ public void emitString(IMXMLStringNode node)
+ {
+ getCurrentDescriptor("ps").valueNeedsQuotes = true;
+
+ emitAttributeValue(node);
+ }
+
+ //--------------------------------------------------------------------------
+
+ @Override
+ public void emitLiteral(IMXMLLiteralNode node)
+ {
+ MXMLDescriptorSpecifier ps = getCurrentDescriptor("ps");
+ if (ps.value == null) // might be non-null if makingSimpleArray
+ ps.value = "";
+
+ if (ps.valueNeedsQuotes)
+ ps.value += ASEmitterTokens.SINGLE_QUOTE.getToken();
+
+ String s = node.getValue().toString();
+ if (ps.valueNeedsQuotes)
+ {
+ // escape all single quotes found within the string
+ s = s.replace(ASEmitterTokens.SINGLE_QUOTE.getToken(),
+ "\\" + ASEmitterTokens.SINGLE_QUOTE.getToken());
+ }
+ ps.value += s;
+
+ if (ps.valueNeedsQuotes)
+ ps.value += ASEmitterTokens.SINGLE_QUOTE.getToken();
+ }
+
+ //--------------------------------------------------------------------------
+
+ @Override
+ public void emitFactory(IMXMLFactoryNode node)
+ {
+ MXMLDescriptorSpecifier ps = getCurrentDescriptor("ps");
+ ps.value = "new " + formatQualifiedName("org.apache.flex.core.ClassFactory") + "(";
+
+ IASNode cnode = node.getChild(0);
+ if (cnode instanceof IMXMLClassNode)
+ {
+ ps.value += formatQualifiedName(((IMXMLClassNode)cnode).getValue(getMXMLWalker().getProject()).getQualifiedName());
+ }
+ ps.value += ")";
+ }
+
+ //--------------------------------------------------------------------------
+
+ @Override
+ public void emitComponent(IMXMLComponentNode node)
+ {
+ MXMLDescriptorSpecifier ps = getCurrentDescriptor("ps");
+ ps.value = "new " + formatQualifiedName("org.apache.flex.core.ClassFactory") + "(";
+
+ ps.value += formatQualifiedName(documentDefinition.getQualifiedName()) + ".";
+ ps.value += formatQualifiedName(node.getName());
+ ps.value += ")";
+
+ setBufferWrite(true);
+ emitSubDocument(node);
+ subDocuments.append(getBuilder().toString());
+ getBuilder().setLength(0);
+ setBufferWrite(false);
+ }
+
+ @Override
+ protected void setBufferWrite(boolean value)
+ {
+ super.setBufferWrite(value);
+ IASEmitter asEmitter = ((IMXMLBlockWalker) getMXMLWalker()).getASEmitter();
+ ((JSFlexJSEmitter)asEmitter).setBufferWrite(value);
+ }
+
+ //--------------------------------------------------------------------------
+ // JS output
+ //--------------------------------------------------------------------------
+
+ private void emitHeader(IMXMLDocumentNode node)
+ {
+ String cname = node.getFileNode().getName();
+ String bcname = node.getBaseClassName();
+
+ FlexJSProject project = (FlexJSProject) getMXMLWalker().getProject();
+ List<File> sourcePaths = project.getSourcePath();
+ String sourceName = node.getSourcePath();
+ for (File sourcePath : sourcePaths)
+ {
+ if (sourceName.startsWith(sourcePath.getAbsolutePath()))
+ {
+ sourceName = sourceName.substring(sourcePath.getAbsolutePath().length() + 1);
+ }
+ }
+ writeNewline("/**");
+ writeNewline(" * Generated by Apache Flex Cross-Compiler from " + sourceName);
+ writeNewline(" * " + cname);
+ writeNewline(" *");
+ writeNewline(" * @fileoverview");
+ writeNewline(" *");
+ writeNewline(" * @suppress {checkTypes|accessControls}");
+ writeNewline(" */");
+ writeNewline();
+
+ ArrayList<String> writtenInstances = new ArrayList<String>();
+ emitHeaderLine(cname, true); // provide
+ for (String subDocumentName : subDocumentNames)
+ {
+ emitHeaderLine(subDocumentName, true);
+ writtenInstances.add(formatQualifiedName(subDocumentName));
+ }
+ writeNewline();
+ emitHeaderLine(bcname);
+ writtenInstances.add(formatQualifiedName(cname)); // make sure we don't add ourselves
+ writtenInstances.add(formatQualifiedName(bcname)); // make sure we don't add the baseclass twice
+ allInstances.addAll(0, instances);
+ for (MXMLDescriptorSpecifier instance : allInstances)
+ {
+ String name = instance.name;
+ if (writtenInstances.indexOf(name) == -1)
+ {
+ emitHeaderLine(name);
+ writtenInstances.add(name);
+ }
+ }
+ ASProjectScope projectScope = (ASProjectScope) project.getScope();
+ IDefinition cdef = node.getDefinition();
+ ICompilationUnit cu = projectScope
+ .getCompilationUnitForDefinition(cdef);
+ ArrayList<String> deps = project.getRequires(cu);
+
+ if (interfaceList != null)
+ {
+ String[] interfaces = interfaceList.split(", ");
+ for (String iface : interfaces)
+ {
+ deps.add(iface);
+ usedNames.add(iface);
+ }
+ }
+ if (deps != null)
+ {
+ Collections.sort(deps);
+ for (String imp : deps)
+ {
+ if (imp.indexOf(JSGoogEmitterTokens.AS3.getToken()) != -1)
+ continue;
+
+ if (imp.equals(cname))
+ continue;
+
+ if (imp.equals("mx.binding.Binding"))
+ continue;
+ if (imp.equals("mx.binding.BindingManager"))
+ continue;
+ if (imp.equals("mx.binding.FunctionReturnWatcher"))
+ continue;
+ if (imp.equals
<TRUNCATED>
[12/18] git commit: [flex-falcon]
[refs/heads/feature/maven-migration-test] - Merge branch 'develop' of
https://git-wip-us.apache.org/repos/asf/flex-falcon into develop
Posted by cd...@apache.org.
Merge branch 'develop' of https://git-wip-us.apache.org/repos/asf/flex-falcon into develop
Project: http://git-wip-us.apache.org/repos/asf/flex-falcon/repo
Commit: http://git-wip-us.apache.org/repos/asf/flex-falcon/commit/b0fcbced
Tree: http://git-wip-us.apache.org/repos/asf/flex-falcon/tree/b0fcbced
Diff: http://git-wip-us.apache.org/repos/asf/flex-falcon/diff/b0fcbced
Branch: refs/heads/feature/maven-migration-test
Commit: b0fcbced0e378bc34ddd1302a0a57de4386de1e8
Parents: b524221 00a7085
Author: Josh Tynjala <jo...@apache.org>
Authored: Wed Apr 13 15:31:11 2016 -0700
Committer: Josh Tynjala <jo...@apache.org>
Committed: Wed Apr 13 15:31:11 2016 -0700
----------------------------------------------------------------------
.../flex/compiler/internal/codegen/js/utils/EmitterUtils.java | 6 ++++++
1 file changed, 6 insertions(+)
----------------------------------------------------------------------
[04/18] git commit: [flex-falcon]
[refs/heads/feature/maven-migration-test] - quick fix for simple e4x filters
Posted by cd...@apache.org.
quick fix for simple e4x filters
Project: http://git-wip-us.apache.org/repos/asf/flex-falcon/repo
Commit: http://git-wip-us.apache.org/repos/asf/flex-falcon/commit/a56951bb
Tree: http://git-wip-us.apache.org/repos/asf/flex-falcon/tree/a56951bb
Diff: http://git-wip-us.apache.org/repos/asf/flex-falcon/diff/a56951bb
Branch: refs/heads/feature/maven-migration-test
Commit: a56951bbe452a761fe96391f121fe70d6aecf6c3
Parents: 12b3247
Author: Alex Harui <ah...@apache.org>
Authored: Tue Apr 12 11:29:30 2016 -0700
Committer: Alex Harui <ah...@apache.org>
Committed: Tue Apr 12 11:29:30 2016 -0700
----------------------------------------------------------------------
.../codegen/js/flexjs/TestFlexJSGlobalClasses.java | 10 ++++++++++
.../internal/codegen/js/jx/IdentifierEmitter.java | 12 ++++++++++++
2 files changed, 22 insertions(+)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/a56951bb/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
----------------------------------------------------------------------
diff --git a/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java b/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
index 0edd621..295d636 100644
--- a/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
+++ b/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
@@ -515,6 +515,16 @@ public class TestFlexJSGlobalClasses extends TestGoogGlobalClasses
}
@Test
+ public void testXMLFilterForChild()
+ {
+ IVariableNode node = getVariable("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");var b:XMLList = a..grandchild.(year == '2016');");
+ IASNode parentNode = node.getParent();
+ node = (IVariableNode) parentNode.getChild(1);
+ asBlockWalker.visitVariable(node);
+ assertOut("var /** @type {XMLList} */ b = a.descendants('grandchild').filter(function(node){return (node.child('year') == '2016')})");
+ }
+
+ @Test
public void testXMLSetAttribute()
{
IBinaryOperatorNode node = getBinaryNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");a.@bar = 'foo'");
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/a56951bb/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/IdentifierEmitter.java
----------------------------------------------------------------------
diff --git a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/IdentifierEmitter.java b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/IdentifierEmitter.java
index 0d91fcf..0e849ef 100644
--- a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/IdentifierEmitter.java
+++ b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/IdentifierEmitter.java
@@ -36,6 +36,7 @@ import org.apache.flex.compiler.internal.definitions.TypeDefinitionBase;
import org.apache.flex.compiler.internal.tree.as.NonResolvingIdentifierNode;
import org.apache.flex.compiler.tree.ASTNodeID;
import org.apache.flex.compiler.tree.as.IASNode;
+import org.apache.flex.compiler.tree.as.IBinaryOperatorNode;
import org.apache.flex.compiler.tree.as.IFunctionObjectNode;
import org.apache.flex.compiler.tree.as.IIdentifierNode;
import org.apache.flex.compiler.tree.as.IMemberAccessExpressionNode;
@@ -64,6 +65,8 @@ public class IdentifierEmitter extends JSSubEmitter implements
IASNode parentNode = node.getParent();
ASTNodeID parentNodeId = parentNode.getNodeID();
+ IASNode grandparentNode = parentNode.getParent();
+ ASTNodeID grandparentNodeId = (parentNode != null) ? grandparentNode.getNodeID() : null;
boolean identifierIsAccessorFunction = nodeDef instanceof AccessorDefinition;
boolean identifierIsPlainFunction = nodeDef instanceof FunctionDefinition
@@ -245,6 +248,15 @@ public class IdentifierEmitter extends JSSubEmitter implements
write(qname);
endMapping(node);
}
+ else if (grandparentNodeId == ASTNodeID.E4XFilterID &&
+ (!(parentNodeId == ASTNodeID.MemberAccessExpressionID || parentNodeId == ASTNodeID.Op_DescendantsID)))
+ {
+ startMapping(node);
+ write("child('");
+ write(node.getName());
+ write("')");
+ endMapping(node);
+ }
else
{
startMapping(node);
[10/18] git commit: [flex-falcon]
[refs/heads/feature/maven-migration-test] - MXMLWriter: only prints a warning
when source maps requested
Posted by cd...@apache.org.
MXMLWriter: only prints a warning when source maps requested
Project: http://git-wip-us.apache.org/repos/asf/flex-falcon/repo
Commit: http://git-wip-us.apache.org/repos/asf/flex-falcon/commit/b5242218
Tree: http://git-wip-us.apache.org/repos/asf/flex-falcon/tree/b5242218
Diff: http://git-wip-us.apache.org/repos/asf/flex-falcon/diff/b5242218
Branch: refs/heads/feature/maven-migration-test
Commit: b5242218ae07926df9ebf6f6ed3e4e5b43879402
Parents: 3357a10
Author: Josh Tynjala <jo...@apache.org>
Authored: Wed Apr 13 15:20:02 2016 -0700
Committer: Josh Tynjala <jo...@apache.org>
Committed: Wed Apr 13 15:20:02 2016 -0700
----------------------------------------------------------------------
.../apache/flex/compiler/internal/codegen/mxml/MXMLWriter.java | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/b5242218/compiler.jx/src/org/apache/flex/compiler/internal/codegen/mxml/MXMLWriter.java
----------------------------------------------------------------------
diff --git a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/mxml/MXMLWriter.java b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/mxml/MXMLWriter.java
index afb45fd..454904d 100644
--- a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/mxml/MXMLWriter.java
+++ b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/mxml/MXMLWriter.java
@@ -77,7 +77,8 @@ public class MXMLWriter extends JSWriter
if (sourceMapOut != null)
{
- throw new UnsupportedOperationException("Source maps not supported for MXML files");
+ String fileName = new File(compilationUnit.getAbsoluteFilename()).getName();
+ System.out.println("Source map cannot be generated for '" + fileName + "'.");
}
}
[11/18] git commit: [flex-falcon]
[refs/heads/feature/maven-migration-test] - handle MXML case
Posted by cd...@apache.org.
handle MXML case
Project: http://git-wip-us.apache.org/repos/asf/flex-falcon/repo
Commit: http://git-wip-us.apache.org/repos/asf/flex-falcon/commit/00a7085f
Tree: http://git-wip-us.apache.org/repos/asf/flex-falcon/tree/00a7085f
Diff: http://git-wip-us.apache.org/repos/asf/flex-falcon/diff/00a7085f
Branch: refs/heads/feature/maven-migration-test
Commit: 00a7085f2c29aa32867e6cdca0dba1d13fcf5fc6
Parents: 3357a10
Author: Alex Harui <ah...@apache.org>
Authored: Wed Apr 13 15:24:45 2016 -0700
Committer: Alex Harui <ah...@apache.org>
Committed: Wed Apr 13 15:24:45 2016 -0700
----------------------------------------------------------------------
.../flex/compiler/internal/codegen/js/utils/EmitterUtils.java | 6 ++++++
1 file changed, 6 insertions(+)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/00a7085f/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/utils/EmitterUtils.java
----------------------------------------------------------------------
diff --git a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/utils/EmitterUtils.java b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/utils/EmitterUtils.java
index eb09a06..1180476 100644
--- a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/utils/EmitterUtils.java
+++ b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/utils/EmitterUtils.java
@@ -294,6 +294,12 @@ public class EmitterUtils
if (classNode == null) // script in MXML and AS interface definitions
{
+ if (parentNodeId == ASTNodeID.FunctionCallID && model.inE4xFilter)
+ {
+ // instance methods must be qualified with 'this'?
+ // or maybe we need to test if identifier exists on XML/XMLList
+ return false;
+ }
if (nodeDef instanceof VariableDefinition)
{
IDefinition pdef = ((VariableDefinition) nodeDef).getParent();
[06/18] git commit: [flex-falcon]
[refs/heads/feature/maven-migration-test] - FLEX-35072 handle XMLList as
identifiers
Posted by cd...@apache.org.
FLEX-35072 handle XMLList as identifiers
Project: http://git-wip-us.apache.org/repos/asf/flex-falcon/repo
Commit: http://git-wip-us.apache.org/repos/asf/flex-falcon/commit/395863b0
Tree: http://git-wip-us.apache.org/repos/asf/flex-falcon/tree/395863b0
Diff: http://git-wip-us.apache.org/repos/asf/flex-falcon/diff/395863b0
Branch: refs/heads/feature/maven-migration-test
Commit: 395863b005e7cd35e077c303cb9fd73d6d7f1802
Parents: f05ad76
Author: Alex Harui <ah...@apache.org>
Authored: Tue Apr 12 16:06:21 2016 -0700
Committer: Alex Harui <ah...@apache.org>
Committed: Tue Apr 12 16:06:21 2016 -0700
----------------------------------------------------------------------
.../codegen/js/flexjs/TestFlexJSGlobalClasses.java | 8 ++++++++
.../codegen/js/jx/BinaryOperatorEmitter.java | 17 +++++++++++++++++
2 files changed, 25 insertions(+)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/395863b0/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
----------------------------------------------------------------------
diff --git a/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java b/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
index 6536414..3fb8e67 100644
--- a/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
+++ b/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
@@ -565,6 +565,14 @@ public class TestFlexJSGlobalClasses extends TestGoogGlobalClasses
}
@Test
+ public void testXMLListConcat2()
+ {
+ IBinaryOperatorNode node = getBinaryNode("var a:XMLList; var b:XMLList; a += b");
+ asBlockWalker.visitBinaryOperator(node);
+ assertOut("a.concat(b)");
+ }
+
+ @Test
public void testXMLListAddAndAssign()
{
IBinaryOperatorNode node = getBinaryNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");a.foo = a.child + a..grandchild");
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/395863b0/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/BinaryOperatorEmitter.java
----------------------------------------------------------------------
diff --git a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/BinaryOperatorEmitter.java b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/BinaryOperatorEmitter.java
index 6e5cc75..aab9712 100644
--- a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/BinaryOperatorEmitter.java
+++ b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/BinaryOperatorEmitter.java
@@ -28,6 +28,7 @@ import org.apache.flex.compiler.internal.codegen.js.flexjs.JSFlexJSEmitter;
import org.apache.flex.compiler.internal.codegen.js.flexjs.JSFlexJSEmitterTokens;
import org.apache.flex.compiler.internal.definitions.AccessorDefinition;
import org.apache.flex.compiler.internal.projects.FlexJSProject;
+import org.apache.flex.compiler.internal.tree.as.IdentifierNode;
import org.apache.flex.compiler.internal.tree.as.MemberAccessExpressionNode;
import org.apache.flex.compiler.internal.tree.as.UnaryOperatorAtNode;
import org.apache.flex.compiler.projects.ICompilerProject;
@@ -225,6 +226,22 @@ public class BinaryOperatorEmitter extends JSSubEmitter implements
return;
}
}
+ else if (leftSide.getNodeID() == ASTNodeID.IdentifierID)
+ {
+ IDefinition leftDef = leftSide.resolveType(getWalker().getProject());
+ if ((leftDef != null)
+ && IdentifierNode.isXMLish(leftDef, getWalker().getProject()))
+ {
+ if (node.getNodeID() == ASTNodeID.Op_AddAssignID)
+ {
+ getWalker().walk(leftSide);
+ write(".concat(");
+ getWalker().walk(node.getRightOperandNode());
+ write(ASEmitterTokens.PAREN_CLOSE);
+ return;
+ }
+ }
+ }
super_emitBinaryOperator(node);
/*
[05/18] git commit: [flex-falcon]
[refs/heads/feature/maven-migration-test] - add test for FLEX-35071
Posted by cd...@apache.org.
add test for FLEX-35071
Project: http://git-wip-us.apache.org/repos/asf/flex-falcon/repo
Commit: http://git-wip-us.apache.org/repos/asf/flex-falcon/commit/f05ad766
Tree: http://git-wip-us.apache.org/repos/asf/flex-falcon/tree/f05ad766
Diff: http://git-wip-us.apache.org/repos/asf/flex-falcon/diff/f05ad766
Branch: refs/heads/feature/maven-migration-test
Commit: f05ad766828ac63ee22af80505b58d63342f5814
Parents: a56951b
Author: Alex Harui <ah...@apache.org>
Authored: Tue Apr 12 14:28:40 2016 -0700
Committer: Alex Harui <ah...@apache.org>
Committed: Tue Apr 12 14:28:40 2016 -0700
----------------------------------------------------------------------
.../internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java | 8 ++++++++
1 file changed, 8 insertions(+)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/f05ad766/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
----------------------------------------------------------------------
diff --git a/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java b/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
index 295d636..6536414 100644
--- a/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
+++ b/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
@@ -525,6 +525,14 @@ public class TestFlexJSGlobalClasses extends TestGoogGlobalClasses
}
@Test
+ public void testXMLFilterWithAttribute()
+ {
+ IBinaryOperatorNode node = getBinaryNode("var a:XMLList; a = a.(attribute('name').length());");
+ asBlockWalker.visitBinaryOperator(node);
+ assertOut("a = a.filter(function(node){return (node.attribute('name').length())})");
+ }
+
+ @Test
public void testXMLSetAttribute()
{
IBinaryOperatorNode node = getBinaryNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");a.@bar = 'foo'");
[13/18] git commit: [flex-falcon]
[refs/heads/feature/maven-migration-test] - IndentifierEmitter: source map
for 'this.' in front of identifier when it is omitted in AS
Posted by cd...@apache.org.
IndentifierEmitter: source map for 'this.' in front of identifier when it is omitted in AS
Project: http://git-wip-us.apache.org/repos/asf/flex-falcon/repo
Commit: http://git-wip-us.apache.org/repos/asf/flex-falcon/commit/e395dcdf
Tree: http://git-wip-us.apache.org/repos/asf/flex-falcon/tree/e395dcdf
Diff: http://git-wip-us.apache.org/repos/asf/flex-falcon/diff/e395dcdf
Branch: refs/heads/feature/maven-migration-test
Commit: e395dcdfc1ceb3a41099344d7a78646d95178da6
Parents: b0fcbce
Author: Josh Tynjala <jo...@apache.org>
Authored: Wed Apr 13 16:00:22 2016 -0700
Committer: Josh Tynjala <jo...@apache.org>
Committed: Wed Apr 13 16:00:22 2016 -0700
----------------------------------------------------------------------
.../flex/compiler/internal/codegen/js/jx/IdentifierEmitter.java | 2 ++
1 file changed, 2 insertions(+)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/e395dcdf/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/IdentifierEmitter.java
----------------------------------------------------------------------
diff --git a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/IdentifierEmitter.java b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/IdentifierEmitter.java
index 0e849ef..24df201 100644
--- a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/IdentifierEmitter.java
+++ b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/jx/IdentifierEmitter.java
@@ -169,12 +169,14 @@ public class IdentifierEmitter extends JSSubEmitter implements
.getParent().getAncestorOfType(
IFunctionObjectNode.class);
+ startMapping(node);
if (functionObjectNode != null)
write(JSGoogEmitterTokens.SELF);
else
write(ASEmitterTokens.THIS);
write(ASEmitterTokens.MEMBER_ACCESS);
+ endMapping(node);
}
if (generateClosure)
[02/18] git commit: [flex-falcon]
[refs/heads/feature/maven-migration-test] - fix one more test
Posted by cd...@apache.org.
fix one more test
Project: http://git-wip-us.apache.org/repos/asf/flex-falcon/repo
Commit: http://git-wip-us.apache.org/repos/asf/flex-falcon/commit/33821939
Tree: http://git-wip-us.apache.org/repos/asf/flex-falcon/tree/33821939
Diff: http://git-wip-us.apache.org/repos/asf/flex-falcon/diff/33821939
Branch: refs/heads/feature/maven-migration-test
Commit: 33821939f86c74e15f591badeb8eb76bf4a9df0c
Parents: 11e5390
Author: Alex Harui <ah...@apache.org>
Authored: Tue Apr 12 09:51:11 2016 -0700
Committer: Alex Harui <ah...@apache.org>
Committed: Tue Apr 12 09:51:11 2016 -0700
----------------------------------------------------------------------
.../test-files/flexjs/projects/xml_requires/XMLRequire_result.js | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/33821939/compiler.jx.tests/test-files/flexjs/projects/xml_requires/XMLRequire_result.js
----------------------------------------------------------------------
diff --git a/compiler.jx.tests/test-files/flexjs/projects/xml_requires/XMLRequire_result.js b/compiler.jx.tests/test-files/flexjs/projects/xml_requires/XMLRequire_result.js
index d6affbe..3f8722a 100644
--- a/compiler.jx.tests/test-files/flexjs/projects/xml_requires/XMLRequire_result.js
+++ b/compiler.jx.tests/test-files/flexjs/projects/xml_requires/XMLRequire_result.js
@@ -31,7 +31,7 @@ goog.require('XML');
* @constructor
*/
XMLRequire = function() {
- var /** @type {XML} */ myXML = new XML( '<node />') ;
+ var /** @type {XML} */ myXML = new XML( '<node />');
};
[08/18] git commit: [flex-falcon]
[refs/heads/feature/maven-migration-test] - FLEX-35071 some XML method names
resolve against instance methods and add an extra 'this'
Posted by cd...@apache.org.
FLEX-35071 some XML method names resolve against instance methods and add an extra 'this'
Project: http://git-wip-us.apache.org/repos/asf/flex-falcon/repo
Commit: http://git-wip-us.apache.org/repos/asf/flex-falcon/commit/fd872052
Tree: http://git-wip-us.apache.org/repos/asf/flex-falcon/tree/fd872052
Diff: http://git-wip-us.apache.org/repos/asf/flex-falcon/diff/fd872052
Branch: refs/heads/feature/maven-migration-test
Commit: fd872052619305dcb4498eef5207f2b36c595d64
Parents: 0b74b6a
Author: Alex Harui <ah...@apache.org>
Authored: Wed Apr 13 09:40:00 2016 -0700
Committer: Alex Harui <ah...@apache.org>
Committed: Wed Apr 13 09:40:00 2016 -0700
----------------------------------------------------------------------
.../internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java | 2 +-
.../flex/compiler/internal/codegen/js/JSSessionModel.java | 2 ++
.../compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java | 2 ++
.../flex/compiler/internal/codegen/js/utils/EmitterUtils.java | 6 ++++++
4 files changed, 11 insertions(+), 1 deletion(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/fd872052/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
----------------------------------------------------------------------
diff --git a/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java b/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
index de10f74..ba03b6d 100644
--- a/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
+++ b/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
@@ -527,7 +527,7 @@ public class TestFlexJSGlobalClasses extends TestGoogGlobalClasses
@Test
public void testXMLFilterWithAttribute()
{
- IBinaryOperatorNode node = getBinaryNode("var a:XMLList; a = a.(attribute('name').length());");
+ IBinaryOperatorNode node = (IBinaryOperatorNode)getNode("private var attribute:Function; private function test() {var a:XMLList; a = a.(attribute('name').length())};", IBinaryOperatorNode.class, WRAP_LEVEL_CLASS);
asBlockWalker.visitBinaryOperator(node);
assertOut("a = a.filter(function(node){return (node.attribute('name').length())})");
}
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/fd872052/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/JSSessionModel.java
----------------------------------------------------------------------
diff --git a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/JSSessionModel.java b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/JSSessionModel.java
index 5c45227..acd8232 100644
--- a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/JSSessionModel.java
+++ b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/JSSessionModel.java
@@ -60,6 +60,8 @@ public class JSSessionModel
}
private Stack<Context> stack = new Stack<Context>();
+ public boolean inE4xFilter = false;
+
private LinkedHashMap<String, PropertyNodes> propertyMap = new LinkedHashMap<String, PropertyNodes>();
private List<String> interfacePropertyMap = new ArrayList<String>();
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/fd872052/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java
----------------------------------------------------------------------
diff --git a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java
index 99114b3..c954e2c 100644
--- a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java
+++ b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java
@@ -658,6 +658,7 @@ public class JSFlexJSEmitter extends JSGoogEmitter implements IJSFlexJSEmitter
@Override
public void emitE4XFilter(IMemberAccessExpressionNode node)
{
+ getModel().inE4xFilter = true;
getWalker().walk(node.getLeftOperandNode());
write(".filter(function(node){return (node.");
String s = stringifyNode(node.getRightOperandNode());
@@ -665,6 +666,7 @@ public class JSFlexJSEmitter extends JSGoogEmitter implements IJSFlexJSEmitter
s = s.substring(1, s.length() - 1);
write(s);
write(")})");
+ getModel().inE4xFilter = false;
}
@Override
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/fd872052/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/utils/EmitterUtils.java
----------------------------------------------------------------------
diff --git a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/utils/EmitterUtils.java b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/utils/EmitterUtils.java
index ebe21ee..eb09a06 100644
--- a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/utils/EmitterUtils.java
+++ b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/utils/EmitterUtils.java
@@ -345,6 +345,12 @@ public class EmitterUtils
}
else
{
+ if (parentNodeId == ASTNodeID.FunctionCallID && model.inE4xFilter)
+ {
+ // instance methods must be qualified with 'this'?
+ // or maybe we need to test if identifier exists on XML/XMLList
+ return false;
+ }
if (nodeDef != null && !nodeDef.isInternal()
&& isClassMember(project, nodeDef, classNode))
{
[14/18] git commit: [flex-falcon]
[refs/heads/feature/maven-migration-test] - mainCU can be null in compc
Posted by cd...@apache.org.
mainCU can be null in compc
Project: http://git-wip-us.apache.org/repos/asf/flex-falcon/repo
Commit: http://git-wip-us.apache.org/repos/asf/flex-falcon/commit/bc19c66a
Tree: http://git-wip-us.apache.org/repos/asf/flex-falcon/tree/bc19c66a
Diff: http://git-wip-us.apache.org/repos/asf/flex-falcon/diff/bc19c66a
Branch: refs/heads/feature/maven-migration-test
Commit: bc19c66a4bc47b366aeb5d158402c4ab91b27c24
Parents: e395dcd
Author: Alex Harui <ah...@apache.org>
Authored: Wed Apr 13 16:47:15 2016 -0700
Committer: Alex Harui <ah...@apache.org>
Committed: Wed Apr 13 17:11:04 2016 -0700
----------------------------------------------------------------------
.../codegen/mxml/flexjs/MXMLFlexJSEmitter.java | 73 ++++++++++----------
1 file changed, 38 insertions(+), 35 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/bc19c66a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/mxml/flexjs/MXMLFlexJSEmitter.java
----------------------------------------------------------------------
diff --git a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/mxml/flexjs/MXMLFlexJSEmitter.java b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/mxml/flexjs/MXMLFlexJSEmitter.java
index 094f5c7..8beba40 100644
--- a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/mxml/flexjs/MXMLFlexJSEmitter.java
+++ b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/mxml/flexjs/MXMLFlexJSEmitter.java
@@ -208,43 +208,46 @@ public class MXMLFlexJSEmitter extends MXMLEmitter implements
if (project instanceof FlexJSProject)
{
FlexJSProject flexJSProject = (FlexJSProject) project;
- String mainDef = null;
- try {
- mainDef = flexJSProject.mainCU.getQualifiedNames().get(0);
- } catch (InterruptedException e) {
- // TODO Auto-generated catch block
- e.printStackTrace();
- }
- String thisDef = documentDefinition.getQualifiedName();
- if (mainDef != null && mainDef.equals(thisDef))
- {
- Set<String> mixins = flexJSProject.config.getIncludes();
- if (mixins.size() > 0)
- {
- String infoInject = "\n\n" + thisDef + ".prototype.info = function() {\n" +
- " return { mixins: [";
- boolean firstOne = true;
- for (String mixin : mixins)
+ if (flexJSProject.mainCU != null)
+ {
+ String mainDef = null;
+ try {
+ mainDef = flexJSProject.mainCU.getQualifiedNames().get(0);
+ } catch (InterruptedException e) {
+ // TODO Auto-generated catch block
+ e.printStackTrace();
+ }
+ String thisDef = documentDefinition.getQualifiedName();
+ if (mainDef != null && mainDef.equals(thisDef))
+ {
+ Set<String> mixins = flexJSProject.config.getIncludes();
+ if (mixins.size() > 0)
{
- if (!firstOne)
- infoInject += ", ";
- infoInject += mixin;
- firstOne = false;
- StringBuilder appendString = new StringBuilder();
- appendString.append(JSGoogEmitterTokens.GOOG_REQUIRE.getToken());
- appendString.append(ASEmitterTokens.PAREN_OPEN.getToken());
- appendString.append(ASEmitterTokens.SINGLE_QUOTE.getToken());
- appendString.append(mixin);
- appendString.append(ASEmitterTokens.SINGLE_QUOTE.getToken());
- appendString.append(ASEmitterTokens.PAREN_CLOSE.getToken());
- appendString.append(ASEmitterTokens.SEMICOLON.getToken());
- finalLines.add(endRequires, appendString.toString());
- //addLineToMappings(finalLines.size());
+ String infoInject = "\n\n" + thisDef + ".prototype.info = function() {\n" +
+ " return { mixins: [";
+ boolean firstOne = true;
+ for (String mixin : mixins)
+ {
+ if (!firstOne)
+ infoInject += ", ";
+ infoInject += mixin;
+ firstOne = false;
+ StringBuilder appendString = new StringBuilder();
+ appendString.append(JSGoogEmitterTokens.GOOG_REQUIRE.getToken());
+ appendString.append(ASEmitterTokens.PAREN_OPEN.getToken());
+ appendString.append(ASEmitterTokens.SINGLE_QUOTE.getToken());
+ appendString.append(mixin);
+ appendString.append(ASEmitterTokens.SINGLE_QUOTE.getToken());
+ appendString.append(ASEmitterTokens.PAREN_CLOSE.getToken());
+ appendString.append(ASEmitterTokens.SEMICOLON.getToken());
+ finalLines.add(endRequires, appendString.toString());
+ //addLineToMappings(finalLines.size());
+ }
+ infoInject += "]}};";
+ finalLines.add(infoInject);
+ //addLineToMappings(finalLines.size());
}
- infoInject += "]}};";
- finalLines.add(infoInject);
- //addLineToMappings(finalLines.size());
- }
+ }
}
}
return Joiner.on("\n").join(finalLines);
[03/18] git commit: [flex-falcon]
[refs/heads/feature/maven-migration-test] - FLEX-35074 handle more XML cases
Posted by cd...@apache.org.
FLEX-35074 handle more XML cases
Project: http://git-wip-us.apache.org/repos/asf/flex-falcon/repo
Commit: http://git-wip-us.apache.org/repos/asf/flex-falcon/commit/12b32476
Tree: http://git-wip-us.apache.org/repos/asf/flex-falcon/tree/12b32476
Diff: http://git-wip-us.apache.org/repos/asf/flex-falcon/diff/12b32476
Branch: refs/heads/feature/maven-migration-test
Commit: 12b32476756adffee98a89c0efb65c03750e75aa
Parents: 3382193
Author: Alex Harui <ah...@apache.org>
Authored: Tue Apr 12 10:44:17 2016 -0700
Committer: Alex Harui <ah...@apache.org>
Committed: Tue Apr 12 10:44:17 2016 -0700
----------------------------------------------------------------------
.../internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java | 8 ++++++++
.../compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java | 8 ++++++++
2 files changed, 16 insertions(+)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/12b32476/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
----------------------------------------------------------------------
diff --git a/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java b/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
index d219506..0edd621 100644
--- a/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
+++ b/compiler.jx.tests/src/org/apache/flex/compiler/internal/codegen/js/flexjs/TestFlexJSGlobalClasses.java
@@ -523,6 +523,14 @@ public class TestFlexJSGlobalClasses extends TestGoogGlobalClasses
}
@Test
+ public void testXMLListSetAttribute()
+ {
+ IBinaryOperatorNode node = getBinaryNode("var a:XMLList;a[1].@bar = 'foo'");
+ asBlockWalker.visitBinaryOperator(node);
+ assertOut("a[1].setAttribute('bar', 'foo')");
+ }
+
+ @Test
public void testXMLSetChild()
{
IBinaryOperatorNode node = getBinaryNode("var a:XML = new XML(\"<top attr1='cat'><child attr2='dog'><grandchild attr3='fish'>text</grandchild></child></top>\");a.foo = a.child");
http://git-wip-us.apache.org/repos/asf/flex-falcon/blob/12b32476/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java
----------------------------------------------------------------------
diff --git a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java
index cde30e8..d345277 100644
--- a/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java
+++ b/compiler.jx/src/org/apache/flex/compiler/internal/codegen/js/flexjs/JSFlexJSEmitter.java
@@ -909,6 +909,14 @@ public class JSFlexJSEmitter extends JSGoogEmitter implements IJSFlexJSEmitter
if (fname.equals("XML") || fname.equals("XMLList"))
return true;
}
+ else if (leftID == ASTNodeID.ArrayIndexExpressionID)
+ {
+ leftNode = (IExpressionNode)(leftNode.getChild(0));
+ IDefinition leftDef = leftNode.resolveType(getWalker().getProject());
+ if (leftDef != null)
+ return IdentifierNode.isXMLish(leftDef, getWalker().getProject());
+
+ }
return false;
}