in compiler-jx/src/main/java/org/apache/royale/compiler/internal/codegen/js/jx/PackageFooterEmitter.java [619:921]
public void emitReflectionData(
String typeName,
ReflectionKind outputType,
List<VariableData> varData,
List<AccessorData> accessorData,
List<MethodData> methodData,
IMetaTagNode[] metaData
)
{
emitReflectionDataStart(typeName);
boolean indented = false;
boolean continueContent = false;
int count;
if (outputType == ReflectionKind.CLASS) {
if (varData.size() > 0) {
indentPush();
writeNewline();
indented = true;
write("variables");
writeToken(ASEmitterTokens.COLON);
writeToken(ASEmitterTokens.FUNCTION);
write(ASEmitterTokens.PAREN_OPEN);
writeToken(ASEmitterTokens.PAREN_CLOSE);
write(ASEmitterTokens.BLOCK_OPEN);
indentPush();
writeNewline();
// return {
writeToken(ASEmitterTokens.RETURN);
write(ASEmitterTokens.BLOCK_OPEN);
indentPush();
count = 0;
for (VariableData var : varData) {
if (count > 0)
write(ASEmitterTokens.COMMA);
writeNewline();
count++;
// varname: { type: typename
write(ASEmitterTokens.SINGLE_QUOTE);
//prefix static var names with |
if (var.isStatic) {
write("|");
}
if (var.customNS != null) {
write(var.customNS);
write("::");
}
write(var.name);
write(ASEmitterTokens.SINGLE_QUOTE);
writeToken(ASEmitterTokens.COLON);
writeToken(ASEmitterTokens.BLOCK_OPEN);
write("type");
writeToken(ASEmitterTokens.COLON);
write(ASEmitterTokens.SINGLE_QUOTE);
write(var.type);
write(ASEmitterTokens.SINGLE_QUOTE);
//provide a get_set function that works in release build with public vars
writeToken(ASEmitterTokens.COMMA);
write(JSRoyaleEmitterTokens.ROYALE_REFLECTION_INFO_GET_SET);
writeToken(ASEmitterTokens.COLON);
writeToken(ASEmitterTokens.FUNCTION);
boolean valueIsUntyped = var.type.equals("*");
if (valueIsUntyped) {
//give the function a local name because a self-reference argument will be used to signify that
//it is not being used as a setter (because 'undefined' is a valid possible value to set)
write("f");
}
write(ASEmitterTokens.PAREN_OPEN);
if (!var.isStatic) {
//instance type parameter
writeToken("/** " + typeName + " */");
write("inst");
writeToken(ASEmitterTokens.COMMA);
}
//any type for value
write("/** * */ v");
writeToken(ASEmitterTokens.PAREN_CLOSE);
write(ASEmitterTokens.BLOCK_OPEN);
String getterSetter;
String varName;
if (var.customNS != null) {
varName = JSRoyaleEmitter.formatNamespacedProperty(var.customNS, var.name, false);
} else varName = var.name;
String field = var.isStatic ? typeName + "." + varName : "inst." + varName;
if (valueIsUntyped) {
//to avoid setting when type is '*' set the 'value' param to the function being called, which
//causes a 'getter only' result
//In the case of no parameter or literal undefined being passed, it will be treated as the value
//of undefined to be assigned to the variable field
getterSetter = "return v !== f ? "+ field + " = v : " + field + ";";
} else {
getterSetter = "return v !== undefined ? " + field + " = v : " + field + ";";
}
write(getterSetter);
write(ASEmitterTokens.BLOCK_CLOSE);
IMetaTagNode[] tags = var.metaData;
if (tags != null) {
//writeToken(ASEmitterTokens.COMMA);
writeMetaData(tags, true, false);
}
// close object
write(ASEmitterTokens.BLOCK_CLOSE);
}
indentPop();
writeNewline();
write(ASEmitterTokens.BLOCK_CLOSE);
write(ASEmitterTokens.SEMICOLON);
indentPop();
writeNewline();
// close variable function
write(ASEmitterTokens.BLOCK_CLOSE);
continueContent = true;
}
}
if (accessorData.size() > 0) {
if (continueContent) {
write(ASEmitterTokens.COMMA);
writeNewline();
}
// accessors: function() {
if (!indented) {
indentPush();
writeNewline();
indented = true;
}
write("accessors");
writeToken(ASEmitterTokens.COLON);
writeToken(ASEmitterTokens.FUNCTION);
write(ASEmitterTokens.PAREN_OPEN);
writeToken(ASEmitterTokens.PAREN_CLOSE);
write(ASEmitterTokens.BLOCK_OPEN);
indentPush();
writeNewline();
// return {
writeToken(ASEmitterTokens.RETURN);
write(ASEmitterTokens.BLOCK_OPEN);
indentPush();
count = 0;
for (AccessorData accessor : accessorData)
{
if (count > 0)
write(ASEmitterTokens.COMMA);
writeNewline();
count++;
// accessorname: { type: typename
write(ASEmitterTokens.SINGLE_QUOTE);
//prefix static accessor names with |
if (accessor.isStatic) {
write("|");
}
if (accessor.customNS != null) {
write(accessor.customNS);
write("::");
}
write(accessor.name);
write(ASEmitterTokens.SINGLE_QUOTE);
writeToken(ASEmitterTokens.COLON);
writeToken(ASEmitterTokens.BLOCK_OPEN);
write("type");
writeToken(ASEmitterTokens.COLON);
write(ASEmitterTokens.SINGLE_QUOTE);
write(accessor.type);
write(ASEmitterTokens.SINGLE_QUOTE);
writeToken(ASEmitterTokens.COMMA);
write("access");
writeToken(ASEmitterTokens.COLON);
write(ASEmitterTokens.SINGLE_QUOTE);
write(accessor.access);
write(ASEmitterTokens.SINGLE_QUOTE);
writeToken(ASEmitterTokens.COMMA);
write("declaredBy");
writeToken(ASEmitterTokens.COLON);
write(ASEmitterTokens.SINGLE_QUOTE);
write(accessor.declaredBy);
write(ASEmitterTokens.SINGLE_QUOTE);
IMetaTagNode[] tags = accessor.metaData;
if (tags != null)
{
//writeToken(ASEmitterTokens.COMMA);
writeMetaData(tags, true, false);
}
// close object
write(ASEmitterTokens.BLOCK_CLOSE);
}
indentPop();
writeNewline();
write(ASEmitterTokens.BLOCK_CLOSE);
write(ASEmitterTokens.SEMICOLON);
indentPop();
writeNewline();
// close accessor function
write(ASEmitterTokens.BLOCK_CLOSE);
continueContent = true;
}
if (methodData.size() > 0) {
if (continueContent){
write(ASEmitterTokens.COMMA);
writeNewline();
}
if (!indented) {
indentPush();
writeNewline();
indented = true;
}
write("methods");
writeToken(ASEmitterTokens.COLON);
writeToken(ASEmitterTokens.FUNCTION);
write(ASEmitterTokens.PAREN_OPEN);
writeToken(ASEmitterTokens.PAREN_CLOSE);
write(ASEmitterTokens.BLOCK_OPEN);
indentPush();
writeNewline();
// return {
writeToken(ASEmitterTokens.RETURN);
write(ASEmitterTokens.BLOCK_OPEN);
indentPush();
count = 0;
for (MethodData method : methodData)
{
if (count > 0)
write(ASEmitterTokens.COMMA);
writeNewline();
count++;
// methodname: { type: typename
write(ASEmitterTokens.SINGLE_QUOTE);
//prefix static method names with |
if (method.isStatic) {
write("|");
}
if (method.customNS != null) {
write(method.customNS);
write("::");
}
write(method.name);
write(ASEmitterTokens.SINGLE_QUOTE);
writeToken(ASEmitterTokens.COLON);
writeToken(ASEmitterTokens.BLOCK_OPEN);
write("type");
writeToken(ASEmitterTokens.COLON);
write(ASEmitterTokens.SINGLE_QUOTE);
write(method.type);
write(ASEmitterTokens.SINGLE_QUOTE);
writeToken(ASEmitterTokens.COMMA);
write("declaredBy");
writeToken(ASEmitterTokens.COLON);
write(ASEmitterTokens.SINGLE_QUOTE);
write(method.declaredBy);
write(ASEmitterTokens.SINGLE_QUOTE);
IParameterNode[] params = method.parameters;
//only output params if there are any
if (params!=null && params.length > 0) {
writeToken(ASEmitterTokens.COMMA);
writeParameters(params);
}
IMetaTagNode[] metas = method.metaData;
if (metas != null)
{
writeMetaData(metas, true, false);
}
// close object
write(ASEmitterTokens.BLOCK_CLOSE);
}
// close return
indentPop();
writeNewline();
write(ASEmitterTokens.BLOCK_CLOSE);
write(ASEmitterTokens.SEMICOLON);
indentPop();
writeNewline();
// close method function
write(ASEmitterTokens.BLOCK_CLOSE);
continueContent = true;
}
if (metaData != null && metaData.length > 0)
{
writeMetaData(metaData, continueContent, continueContent);
}
if (indented)
indentPop();
emitReflectionDataEnd(typeName, indented);
}