private void WriteElements(string source, string enumSource, ElementAccessor[] elements, TextAccessor text, ChoiceIdentifierAccessor choice, string arrayName, bool writeAccessors, bool isNullable)
{
if (elements.Length == 0 && text == null) return;
if (elements.Length == 1 && text == null)
{
TypeDesc td = elements[0].IsUnbounded ? elements[0].Mapping.TypeDesc.CreateArrayTypeDesc() : elements[0].Mapping.TypeDesc;
if (!elements[0].Any && !elements[0].Mapping.TypeDesc.UseReflection && !elements[0].Mapping.TypeDesc.IsOptionalValue)
source = "((" + td.CSharpName + ")" + source + ")";
WriteElement(source, elements[0], arrayName, writeAccessors);
}
else
{
if (isNullable && choice == null)
{
Writer.Write("if ((object)(");
Writer.Write(source);
Writer.Write(") != null)");
}
Writer.WriteLine("{");
Writer.Indent++;
int anyCount = 0;
ArrayList namedAnys = new ArrayList();
ElementAccessor unnamedAny = null; // can only have one
bool wroteFirstIf = false;
string enumTypeName = choice == null ? null : choice.Mapping.TypeDesc.FullName;
for (int i = 0; i < elements.Length; i++)
{
ElementAccessor element = elements[i];
if (element.Any)
{
anyCount++;
if (element.Name != null && element.Name.Length > 0)
namedAnys.Add(element);
else if (unnamedAny == null)
unnamedAny = element;
}
else if (choice != null)
{
bool useReflection = element.Mapping.TypeDesc.UseReflection;
string fullTypeName = element.Mapping.TypeDesc.CSharpName;
bool enumUseReflection = choice.Mapping.TypeDesc.UseReflection;
string enumFullName = (enumUseReflection ? "" : enumTypeName + ".@") + FindChoiceEnumValue(element, (EnumMapping)choice.Mapping, enumUseReflection);
if (wroteFirstIf) Writer.Write("else ");
else wroteFirstIf = true;
Writer.Write("if (");
Writer.Write(enumUseReflection ? RaCodeGen.GetStringForEnumLongValue(enumSource, enumUseReflection) : enumSource);
Writer.Write(" == ");
Writer.Write(enumFullName);
if (isNullable && !element.IsNullable)
{
Writer.Write(" && ((object)(");
Writer.Write(source);
Writer.Write(") != null)");
}
Writer.WriteLine(") {");
Writer.Indent++;
WriteChoiceTypeCheck(source, fullTypeName, useReflection, choice, enumFullName, element.Mapping.TypeDesc);
string castedSource = source;
if (!useReflection)
castedSource = "((" + fullTypeName + ")" + source + ")";
WriteElement(element.Any ? source : castedSource, element, arrayName, writeAccessors);
Writer.Indent--;
Writer.WriteLine("}");
}
else
{
bool useReflection = element.Mapping.TypeDesc.UseReflection;
TypeDesc td = element.IsUnbounded ? element.Mapping.TypeDesc.CreateArrayTypeDesc() : element.Mapping.TypeDesc;
string fullTypeName = td.CSharpName;
if (wroteFirstIf) Writer.Write("else ");
else wroteFirstIf = true;
Writer.Write("if (");
WriteInstanceOf(source, fullTypeName, useReflection);
Writer.WriteLine(") {");
Writer.Indent++;
string castedSource = source;
if (!useReflection)
castedSource = "((" + fullTypeName + ")" + source + ")";
WriteElement(element.Any ? source : castedSource, element, arrayName, writeAccessors);
Writer.Indent--;
Writer.WriteLine("}");
}
}
if (anyCount > 0)
{
if (elements.Length - anyCount > 0) Writer.Write("else ");
string fullTypeName = typeof(XmlElement).FullName;
Writer.Write("if (");
Writer.Write(source);
Writer.Write(" is ");
Writer.Write(fullTypeName);
Writer.WriteLine(") {");
Writer.Indent++;
Writer.Write(fullTypeName);
Writer.Write(" elem = (");
Writer.Write(fullTypeName);
Writer.Write(")");
Writer.Write(source);
Writer.WriteLine(";");
int c = 0;
foreach (ElementAccessor element in namedAnys)
{
if (c++ > 0) Writer.Write("else ");
string enumFullName = null;
bool useReflection = element.Mapping.TypeDesc.UseReflection;
if (choice != null)
{
bool enumUseReflection = choice.Mapping.TypeDesc.UseReflection;
enumFullName = (enumUseReflection ? "" : enumTypeName + ".@") + FindChoiceEnumValue(element, (EnumMapping)choice.Mapping, enumUseReflection);
Writer.Write("if (");
Writer.Write(enumUseReflection ? RaCodeGen.GetStringForEnumLongValue(enumSource, enumUseReflection) : enumSource);
Writer.Write(" == ");
Writer.Write(enumFullName);
if (isNullable && !element.IsNullable)
{
Writer.Write(" && ((object)(");
Writer.Write(source);
Writer.Write(") != null)");
}
Writer.WriteLine(") {");
Writer.Indent++;
}
Writer.Write("if (elem.Name == ");
WriteQuotedCSharpString(element.Name);
Writer.Write(" && elem.NamespaceURI == ");
WriteQuotedCSharpString(element.Namespace);
Writer.WriteLine(") {");
Writer.Indent++;
WriteElement("elem", element, arrayName, writeAccessors);
if (choice != null)
{
Writer.Indent--;
Writer.WriteLine("}");
Writer.WriteLine("else {");
Writer.Indent++;
Writer.WriteLine("// throw Value '{0}' of the choice identifier '{1}' does not match element '{2}' from namespace '{3}'.");
Writer.Write("throw CreateChoiceIdentifierValueException(");
WriteQuotedCSharpString(enumFullName);
Writer.Write(", ");
WriteQuotedCSharpString(choice.MemberName);
Writer.WriteLine(", elem.Name, elem.NamespaceURI);");
Writer.Indent--;
Writer.WriteLine("}");
}
Writer.Indent--;
Writer.WriteLine("}");
}
if (c > 0)
{
Writer.WriteLine("else {");
Writer.Indent++;
}
if (unnamedAny != null)
{
WriteElement("elem", unnamedAny, arrayName, writeAccessors);
}
else
{
Writer.WriteLine("throw CreateUnknownAnyElementException(elem.Name, elem.NamespaceURI);");
}
if (c > 0)
{
Writer.Indent--;
Writer.WriteLine("}");
}
Writer.Indent--;
Writer.WriteLine("}");
}
if (text != null)
{
bool useReflection = text.Mapping.TypeDesc.UseReflection;
string fullTypeName = text.Mapping.TypeDesc.CSharpName;
if (elements.Length > 0)
{
Writer.Write("else ");
Writer.Write("if (");
WriteInstanceOf(source, fullTypeName, useReflection);
Writer.WriteLine(") {");
Writer.Indent++;
string castedSource = source;
if (!useReflection)
castedSource = "((" + fullTypeName + ")" + source + ")";
WriteText(castedSource, text);
Writer.Indent--;
Writer.WriteLine("}");
}
else
{
string castedSource = source;
if (!useReflection)
castedSource = "((" + fullTypeName + ")" + source + ")";
WriteText(castedSource, text);
}
}
if (elements.Length > 0)
{
Writer.Write("else ");
if (isNullable)
{
Writer.Write(" if ((object)(");
Writer.Write(source);
Writer.Write(") != null)");
}
Writer.WriteLine("{");
Writer.Indent++;
Writer.Write("throw CreateUnknownTypeException(");
Writer.Write(source);
Writer.WriteLine(");");
Writer.Indent--;
Writer.WriteLine("}");
}
Writer.Indent--;
Writer.WriteLine("}");
}
}