public virtual void Generate(GenerationInfo gen_info, string indent) { if (Ignored || Hidden) { return; } CheckGlue(); if ((getterName != null || setterName != null || getOffsetName != null) && gen_info.GlueWriter == null) { Console.WriteLine("No glue-filename specified, can't create glue for {0}.{1}", container_type.Name, Name); return; } GenerateImports(gen_info, indent); SymbolTable table = SymbolTable.Table; StreamWriter sw = gen_info.Writer; string modifiers = elem.HasAttribute("new_flag") ? "new " : ""; bool is_struct = table.IsStruct(CType) || table.IsBoxed(CType); sw.WriteLine(indent + "public " + modifiers + CSType + " " + Name + " {"); if (Getter != null) { sw.Write(indent + "\tget "); Getter.GenerateBody(gen_info, container_type, "\t"); sw.WriteLine(""); } else if (getterName != null) { sw.WriteLine(indent + "\tget {"); container_type.Prepare(sw, indent + "\t\t"); sw.WriteLine(indent + "\t\t" + CSType + " result = " + table.FromNativeReturn(ctype, getterName + " (" + container_type.CallByName() + ")") + ";"); container_type.Finish(sw, indent + "\t\t"); sw.WriteLine(indent + "\t\treturn result;"); sw.WriteLine(indent + "\t}"); } else if (Readable && offsetName != null) { sw.WriteLine(indent + "\tget {"); sw.WriteLine(indent + "\t\tunsafe {"); if (is_struct) { sw.WriteLine(indent + "\t\t\t" + CSType + "* raw_ptr = (" + CSType + "*)(((byte*)" + container_type.CallByName() + ") + " + offsetName + ");"); sw.WriteLine(indent + "\t\t\treturn *raw_ptr;"); } else { sw.WriteLine(indent + "\t\t\t" + table.GetMarshalReturnType(CType) + "* raw_ptr = (" + table.GetMarshalReturnType(CType) + "*)(((byte*)" + container_type.CallByName() + ") + " + offsetName + ");"); sw.WriteLine(indent + "\t\t\treturn " + table.FromNativeReturn(ctype, "(*raw_ptr)") + ";"); } sw.WriteLine(indent + "\t\t}"); sw.WriteLine(indent + "\t}"); } if (Setter != null) { sw.Write(indent + "\tset "); Setter.GenerateBody(gen_info, container_type, "\t"); sw.WriteLine(""); } else if (setterName != null) { sw.WriteLine(indent + "\tset {"); container_type.Prepare(sw, indent + "\t\t"); sw.WriteLine(indent + "\t\t" + setterName + " (" + container_type.CallByName() + ", " + table.CallByName(ctype, "value") + ");"); container_type.Finish(sw, indent + "\t\t"); sw.WriteLine(indent + "\t}"); } else if (Writable && offsetName != null) { sw.WriteLine(indent + "\tset {"); sw.WriteLine(indent + "\t\tunsafe {"); if (is_struct) { sw.WriteLine(indent + "\t\t\t" + CSType + "* raw_ptr = (" + CSType + "*)(((byte*)" + container_type.CallByName() + ") + " + offsetName + ");"); sw.WriteLine(indent + "\t\t\t*raw_ptr = value;"); } else { sw.WriteLine(indent + "\t\t\t" + table.GetMarshalReturnType(CType) + "* raw_ptr = (" + table.GetMarshalReturnType(CType) + "*)(((byte*)" + container_type.CallByName() + ") + " + offsetName + ");"); sw.WriteLine(indent + "\t\t\t*raw_ptr = " + table.ToNativeReturn(ctype, "value") + ";"); } sw.WriteLine(indent + "\t\t}"); sw.WriteLine(indent + "\t}"); } sw.WriteLine(indent + "}"); sw.WriteLine(""); if (getterName != null || setterName != null || getOffsetName != null) { GenerateGlue(gen_info); } }
public void Generate(GenerationInfo gen_info, string indent, ClassBase implementor) { var table = SymbolTable.Table; var sw = gen_info.Writer; if (Hidden || (!Readable && !Writable)) { return; } string modifiers = ""; if (IsNew || (container_type.Parent != null && container_type.Parent.GetPropertyRecursively(Name) != null)) { modifiers = "new "; } else if (implementor != null && implementor.Parent != null && implementor.Parent.GetPropertyRecursively(Name) != null) { modifiers = "new "; } string name = Name; if (name == container_type.Name) { name += "Prop"; } string qpname = "\"" + CName + "\""; string v_type = ""; if (table.IsInterface(CType)) { v_type = "(GLib.Object)"; } else if (table.IsOpaque(CType)) { v_type = "(GLib.Opaque)"; } else if (table.IsEnum(CType)) { v_type = "(Enum)"; } GenerateImports(gen_info, indent); if (IsDeprecated || (Getter != null && Getter.IsDeprecated) || (Setter != null && Setter.IsDeprecated)) { sw.WriteLine(indent + "[Obsolete]"); } sw.WriteLine(indent + PropertyAttribute(qpname)); sw.WriteLine(indent + "public " + modifiers + CSType + " " + name + " {"); indent += "\t"; if (Getter != null) { sw.Write(indent + "get "); Getter.GenerateBody(gen_info, implementor, "\t"); sw.WriteLine(); } else if (Readable) { sw.WriteLine(indent + "get {"); sw.WriteLine(indent + "\tGLib.Value val = " + RawGetter(qpname) + ";"); if (table.IsOpaque(CType) || table.IsBoxed(CType)) { sw.WriteLine(indent + "\t" + CSType + " ret = (" + CSType + ") val;"); } else if (table.IsInterface(CType)) { // Do we have to dispose the GLib.Object from the GLib.Value? sw.WriteLine(indent + "\t{0} ret = {0}Adapter.GetObject ((GLib.Object) val);", CSType); } else { sw.Write(indent + "\t" + CSType + " ret = "); sw.Write("(" + CSType + ") "); if (v_type != "") { sw.Write(v_type + " "); } sw.WriteLine("val;"); } sw.WriteLine(indent + "\tval.Dispose ();"); sw.WriteLine(indent + "\treturn ret;"); sw.WriteLine(indent + "}"); } if (Setter != null) { sw.Write(indent + "set "); Setter.GenerateBody(gen_info, implementor, "\t"); sw.WriteLine(); } else if (Writable) { sw.WriteLine(indent + "set {"); sw.Write(indent + "\tGLib.Value val = "); if (table.IsBoxed(CType)) { sw.WriteLine("(GLib.Value) value;"); } else if (table.IsOpaque(CType)) { sw.WriteLine("new GLib.Value(value, \"{0}\");", CType); } else { sw.Write("new GLib.Value("); if (v_type != "" && !(table.IsObject(CType) || table.IsInterface(CType) || table.IsOpaque(CType))) { sw.Write(v_type + " "); } sw.WriteLine("value);"); } sw.WriteLine(indent + "\t" + RawSetter(qpname) + ";"); sw.WriteLine(indent + "\tval.Dispose ();"); sw.WriteLine(indent + "}"); } sw.WriteLine(indent.Substring(1) + "}"); sw.WriteLine(); Statistics.PropCount++; }
public virtual void Generate(GenerationInfo gen_info, string indent) { if (Ignored || Hidden) { return; } CheckGlue(); if ((getterName != null || setterName != null || getOffsetName != null) && gen_info.GlueWriter == null) { LogWriter log = new LogWriter(container_type.QualifiedName); log.Member = Name; log.Warn("needs glue for field access. Specify --glue-filename"); return; } GenerateImports(gen_info, indent); SymbolTable table = SymbolTable.Table; StreamWriter sw = gen_info.Writer; string modifiers = elem.HasAttribute("new_flag") ? "new " : ""; bool is_struct = table.IsStruct(CType) || table.IsBoxed(CType); sw.WriteLine(indent + "public " + modifiers + CSType + " " + Name + " {"); if (Getter != null) { sw.Write(indent + "\tget "); Getter.GenerateBody(gen_info, container_type, "\t"); sw.WriteLine(""); } else if (getterName != null) { sw.WriteLine(indent + "\tget {"); container_type.Prepare(sw, indent + "\t\t"); sw.WriteLine(indent + "\t\t" + CSType + " result = " + table.FromNative(ctype, getterName + " (" + container_type.CallByName() + ")") + ";"); container_type.Finish(sw, indent + "\t\t"); sw.WriteLine(indent + "\t\treturn result;"); sw.WriteLine(indent + "\t}"); } else if (Readable && offsetName != null) { sw.WriteLine(indent + "\tget {"); sw.WriteLine(indent + "\t\tunsafe {"); if (is_struct) { sw.WriteLine(indent + "\t\t\t" + CSType + "* raw_ptr = (" + CSType + "*)(((byte*)" + container_type.CallByName() + ") + " + offsetName + ");"); sw.WriteLine(indent + "\t\t\treturn *raw_ptr;"); } else { sw.WriteLine(indent + "\t\t\t" + table.GetMarshalType(CType) + "* raw_ptr = (" + table.GetMarshalType(CType) + "*)(((byte*)" + container_type.CallByName() + ") + " + offsetName + ");"); sw.WriteLine(indent + "\t\t\treturn " + table.FromNative(ctype, "(*raw_ptr)") + ";"); } sw.WriteLine(indent + "\t\t}"); sw.WriteLine(indent + "\t}"); } IGeneratable gen = table [CType]; string to_native = (gen is IManualMarshaler) ? (gen as IManualMarshaler).AllocNative("value") : gen.CallByName("value"); if (Setter != null) { sw.Write(indent + "\tset "); Setter.GenerateBody(gen_info, container_type, "\t"); sw.WriteLine(""); } else if (setterName != null) { sw.WriteLine(indent + "\tset {"); container_type.Prepare(sw, indent + "\t\t"); sw.WriteLine(indent + "\t\t" + setterName + " (" + container_type.CallByName() + ", " + to_native + ");"); container_type.Finish(sw, indent + "\t\t"); sw.WriteLine(indent + "\t}"); } else if (Writable && offsetName != null) { sw.WriteLine(indent + "\tset {"); sw.WriteLine(indent + "\t\tunsafe {"); if (is_struct) { sw.WriteLine(indent + "\t\t\t" + CSType + "* raw_ptr = (" + CSType + "*)(((byte*)" + container_type.CallByName() + ") + " + offsetName + ");"); sw.WriteLine(indent + "\t\t\t*raw_ptr = value;"); } else { sw.WriteLine(indent + "\t\t\t" + table.GetMarshalType(CType) + "* raw_ptr = (" + table.GetMarshalType(CType) + "*)(((byte*)" + container_type.CallByName() + ") + " + offsetName + ");"); sw.WriteLine(indent + "\t\t\t*raw_ptr = " + to_native + ";"); } sw.WriteLine(indent + "\t\t}"); sw.WriteLine(indent + "\t}"); } sw.WriteLine(indent + "}"); sw.WriteLine(""); if (getterName != null || setterName != null || getOffsetName != null) { GenerateGlue(gen_info); } }
public virtual void Generate(GenerationInfo generationInfo, string indent) { if (Ignored || Hidden) { return; } CheckGlue(generationInfo); GenerateImports(generationInfo, indent); if (Getter == null && _getterName == null && _offsetName == null && Setter == null && _setterName == null) { return; } var streamWriter = generationInfo.Writer; var modifiers = Element.GetAttributeAsBoolean("new_flag") ? "new " : ""; streamWriter.WriteLine($"{indent}public {modifiers}{CsType} {Name} {{"); var table = SymbolTable.Table; var generatable = table[CType]; if (Getter != null) { streamWriter.Write($"{indent}\tget "); Getter.GenerateBody(generationInfo, ContainerType, "\t"); streamWriter.WriteLine(""); } else if (_getterName != null) { streamWriter.WriteLine($"{indent}\tget {{"); ContainerType.Prepare(streamWriter, $"{indent}\t\t"); streamWriter.WriteLine(indent + "\t\t" + CsType + " result = " + table.FromNative(CType, _getterName + " (" + ContainerType.CallByName() + ")") + ";"); ContainerType.Finish(streamWriter, $"{indent}\t\t"); streamWriter.WriteLine($"{indent}\t\treturn result;"); streamWriter.WriteLine($"{indent}\t}}"); } else if (Readable && _offsetName != null) { streamWriter.WriteLine($"{indent}\tget {{"); streamWriter.WriteLine($"{indent}\t\tunsafe {{"); if (generatable is CallbackGen) { streamWriter.WriteLine(indent + "\t\t\tIntPtr* raw_ptr = (IntPtr*)(((byte*)" + ContainerType.CallByName() + ") + " + _offsetName + ");"); streamWriter.WriteLine( indent + "\t\t\t {0} del = ({0})Marshal.GetDelegateForFunctionPointer(*raw_ptr, typeof({0}));", table.GetMarshalType(CType)); streamWriter.WriteLine($"{indent}\t\t\treturn {table.FromNative(CType, "(del)")};"); } else { streamWriter.WriteLine(indent + "\t\t\t" + table.GetMarshalType(CType) + "* raw_ptr = (" + table.GetMarshalType(CType) + "*)(((byte*)" + ContainerType.CallByName() + ") + " + _offsetName + ");"); streamWriter.WriteLine($"{indent}\t\t\treturn {table.FromNative(CType, "(*raw_ptr)")};"); } streamWriter.WriteLine($"{indent}\t\t}}"); streamWriter.WriteLine($"{indent}\t}}"); } var toNative = generatable is IManualMarshaler marshaler ? marshaler.AllocNative("value") : generatable.CallByName("value"); if (Setter != null) { streamWriter.Write($"{indent}\tset "); Setter.GenerateBody(generationInfo, ContainerType, "\t"); streamWriter.WriteLine(""); } else if (_setterName != null) { streamWriter.WriteLine($"{indent}\tset {{"); ContainerType.Prepare(streamWriter, $"{indent}\t\t"); streamWriter.WriteLine( $"{indent}\t\t{_setterName} ({ContainerType.CallByName()}, {toNative});"); ContainerType.Finish(streamWriter, $"{indent}\t\t"); streamWriter.WriteLine($"{indent}\t}}"); } else if (Writeable && _offsetName != null) { streamWriter.WriteLine($"{indent}\tset {{"); streamWriter.WriteLine($"{indent}\t\tunsafe {{"); if (generatable is CallbackGen callbackGen) { streamWriter.WriteLine(indent + "\t\t\t{0} wrapper = new {0} (value);", callbackGen.WrapperName); streamWriter.WriteLine( $"{indent}\t\t\tIntPtr* raw_ptr = (IntPtr*)(((byte*){ContainerType.CallByName()}) + {_offsetName});"); streamWriter.WriteLine( $"{indent}\t\t\t*raw_ptr = Marshal.GetFunctionPointerForDelegate (wrapper.NativeDelegate);"); } else { streamWriter.WriteLine(indent + "\t\t\t" + table.GetMarshalType(CType) + "* raw_ptr = (" + table.GetMarshalType(CType) + "*)(((byte*)" + ContainerType.CallByName() + ") + " + _offsetName + ");"); streamWriter.WriteLine($"{indent}\t\t\t*raw_ptr = {toNative};"); } streamWriter.WriteLine($"{indent}\t\t}}"); streamWriter.WriteLine($"{indent}\t}}"); } streamWriter.WriteLine($"{indent}}}"); streamWriter.WriteLine(""); if ((_getterName != null || _setterName != null || GetOffsetName != null) && generationInfo.GlueWriter != null) { GenerateGlue(generationInfo); } }
public virtual void Generate(GenerationInfo gen_info, string indent) { if (Ignored || Hidden) { return; } CheckGlue(); if ((getterName != null || setterName != null || getOffsetName != null) && gen_info.GlueWriter == null) { LogWriter log = new LogWriter(container_type.QualifiedName); log.Member = Name; log.Warn("needs glue for field access. Specify --glue-filename"); return; } GenerateImports(gen_info, indent); SymbolTable table = SymbolTable.Table; IGeneratable gen = table [CType]; StreamWriter sw = gen_info.Writer; string modifiers = elem.GetAttributeAsBoolean("new_flag") ? "new " : ""; sw.WriteLine(indent + "public " + modifiers + CSType + " " + Name + " {"); if (Getter != null) { sw.Write(indent + "\tget "); Getter.GenerateBody(gen_info, container_type, "\t"); sw.WriteLine(""); } else if (getterName != null) { sw.WriteLine(indent + "\tget {"); container_type.Prepare(sw, indent + "\t\t"); sw.WriteLine(indent + "\t\t" + CSType + " result = " + table.FromNative(ctype, getterName + " (" + container_type.CallByName() + ")") + ";"); container_type.Finish(sw, indent + "\t\t"); sw.WriteLine(indent + "\t\treturn result;"); sw.WriteLine(indent + "\t}"); } else if (Readable && offsetName != null) { sw.WriteLine(indent + "\tget {"); sw.WriteLine(indent + "\t\tunsafe {"); if (gen is CallbackGen) { sw.WriteLine(indent + "\t\t\tIntPtr* raw_ptr = (IntPtr*)(((byte*)" + container_type.CallByName() + ") + " + offsetName + ");"); sw.WriteLine(indent + "\t\t\t {0} del = ({0})Marshal.GetDelegateForFunctionPointer(*raw_ptr, typeof({0}));", table.GetMarshalType(CType)); sw.WriteLine(indent + "\t\t\treturn " + table.FromNative(ctype, "(del)") + ";"); } else { sw.WriteLine(indent + "\t\t\t" + table.GetMarshalType(CType) + "* raw_ptr = (" + table.GetMarshalType(CType) + "*)(((byte*)" + container_type.CallByName() + ") + " + offsetName + ");"); sw.WriteLine(indent + "\t\t\treturn " + table.FromNative(ctype, "(*raw_ptr)") + ";"); } sw.WriteLine(indent + "\t\t}"); sw.WriteLine(indent + "\t}"); } string to_native = (gen is IManualMarshaler) ? (gen as IManualMarshaler).AllocNative("value") : gen.CallByName("value"); if (Setter != null) { sw.Write(indent + "\tset "); Setter.GenerateBody(gen_info, container_type, "\t"); sw.WriteLine(""); } else if (setterName != null) { sw.WriteLine(indent + "\tset {"); container_type.Prepare(sw, indent + "\t\t"); sw.WriteLine(indent + "\t\t" + setterName + " (" + container_type.CallByName() + ", " + to_native + ");"); container_type.Finish(sw, indent + "\t\t"); sw.WriteLine(indent + "\t}"); } else if (Writable && offsetName != null) { sw.WriteLine(indent + "\tset {"); sw.WriteLine(indent + "\t\tunsafe {"); if (gen is CallbackGen) { sw.WriteLine(indent + "\t\t\t{0} wrapper = new {0} (value);", ((CallbackGen)gen).WrapperName); sw.WriteLine(indent + "\t\t\tIntPtr* raw_ptr = (IntPtr*)(((byte*)" + container_type.CallByName() + ") + " + offsetName + ");"); sw.WriteLine(indent + "\t\t\t*raw_ptr = Marshal.GetFunctionPointerForDelegate (wrapper.NativeDelegate);"); } else { sw.WriteLine(indent + "\t\t\t" + table.GetMarshalType(CType) + "* raw_ptr = (" + table.GetMarshalType(CType) + "*)(((byte*)" + container_type.CallByName() + ") + " + offsetName + ");"); sw.WriteLine(indent + "\t\t\t*raw_ptr = " + to_native + ";"); } sw.WriteLine(indent + "\t\t}"); sw.WriteLine(indent + "\t}"); } sw.WriteLine(indent + "}"); sw.WriteLine(""); if (getterName != null || setterName != null || getOffsetName != null) { GenerateGlue(gen_info); } }
public void Generate(GenerationInfo generationInfo, string indent, ClassBase implementor) { if (Hidden || !Readable && !Writeable) { return; } var name = Name; if (name == ContainerType.Name) { name += "Prop"; } GenerateImports(generationInfo, indent); var streamWriter = generationInfo.Writer; var qpname = $"\"{CName}\""; var modifiers = ""; if (IsNew || ContainerType.Parent?.GetPropertyRecursively(Name) != null || implementor?.Parent?.GetPropertyRecursively(Name) != null) { modifiers = "new "; } if (IsDeprecated || Getter != null && Getter.IsDeprecated || Setter != null && Setter.IsDeprecated) { streamWriter.WriteLine($"{indent}[Obsolete]"); } streamWriter.WriteLine("{0}{1}", indent, PropertyAttribute(qpname)); streamWriter.WriteLine($"{indent}public {modifiers}{CsType} {name} {{"); indent += "\t"; var table = SymbolTable.Table; var vType = ""; if (table.IsInterface(CType)) { vType = "(GLib.Object)"; } else if (table.IsOpaque(CType)) { vType = "(GLib.Opaque)"; } else if (table.IsEnum(CType)) { vType = "(Enum)"; } if (Getter != null) { streamWriter.Write($"{indent}get "); Getter.GenerateBody(generationInfo, implementor, "\t"); streamWriter.WriteLine(); } else if (Readable) { streamWriter.WriteLine($"{indent}get {{"); streamWriter.WriteLine($"{indent}\tGLib.Value val = {RawGetter(qpname)};"); if (table.IsOpaque(CType) || table.IsBoxed(CType)) { streamWriter.WriteLine($"{indent}\t{CsType} ret = ({CsType})val;"); } else if (table.IsInterface(CType)) { var interfaceGen = table.GetInterfaceGen(CType); // Do we have to dispose the GLib.Object from the GLib.Value? streamWriter.WriteLine("{2}\t{0} ret = {1}.GetObject((GLib.Object)val);", interfaceGen.QualifiedName, interfaceGen.QualifiedAdapterName, indent); } else { streamWriter.Write($"{indent}\t{CsType} ret = "); streamWriter.Write($"({CsType}) "); if (vType != "") { streamWriter.Write($"{vType} "); } streamWriter.WriteLine("val;"); } streamWriter.WriteLine($"{indent}\tval.Dispose();"); streamWriter.WriteLine($"{indent}\treturn ret;"); streamWriter.WriteLine($"{indent}}}"); } if (Setter != null) { streamWriter.Write($"{indent}set "); Setter.GenerateBody(generationInfo, implementor, "\t"); streamWriter.WriteLine(); } else if (Writeable) { streamWriter.WriteLine($"{indent}set {{"); streamWriter.Write($"{indent}\tGLib.Value val = "); if (table.IsBoxed(CType)) { streamWriter.WriteLine("(GLib.Value)value;"); } else if (table.IsOpaque(CType)) { streamWriter.WriteLine("new GLib.Value(value, \"{0}\");", CType); } else { streamWriter.Write("new GLib.Value("); if (vType != "" && !(table.IsObject(CType) || table.IsInterface(CType) || table.IsOpaque(CType))) { streamWriter.Write($"{vType} "); } streamWriter.WriteLine("value);"); } streamWriter.WriteLine($"{indent}\t{RawSetter(qpname)};"); streamWriter.WriteLine($"{indent}\tval.Dispose();"); streamWriter.WriteLine($"{indent}}}"); } streamWriter.WriteLine($"{indent.Substring(1)}}}"); streamWriter.WriteLine(); Statistics.PropCount++; }
public void Generate(GenBase gen, StreamWriter sw, string indent, CodeGenerationOptions opt, bool with_callbacks, bool force_override) { // <TechnicalDebt> // This is a special workaround for AdapterView inheritance. // (How it is special? They have hand-written bindings AND brings generic // version of AdapterView<T> in the inheritance, also added by metadata!) // // They are on top of fragile hand-bound code, and when we are making changes // in generator, they bite. Since we are not going to bring API breakage // right now, we need special workarounds to get things working. // // So far, what we need here is to have AbsSpinner.Adapter compile. // // > platforms/*/src/generated/Android.Widget.AbsSpinner.cs(156,56): error CS0533: // > `Android.Widget.AbsSpinner.Adapter' hides inherited abstract member // > `Android.Widget.AdapterView<Android.Widget.ISpinnerAdapter>.Adapter // // It is because the AdapterView<T>.Adapter is hand-bound and cannot be // detected by generator! // // So, we explicitly treat it as a special-case. // // Then, Spinner, ListView and GridView instantiate them, so they are also special cases. // </TechnicalDebt> if (Name == "Adapter" && (Getter.DeclaringType.BaseGen.FullName == "Android.Widget.AdapterView" || Getter.DeclaringType.BaseGen.BaseGen != null && Getter.DeclaringType.BaseGen.BaseGen.FullName == "Android.Widget.AdapterView")) { force_override = true; } // ... and the above breaks generator tests... if (Name == "Adapter" && (Getter.DeclaringType.BaseGen.FullName == "Xamarin.Test.AdapterView" || Getter.DeclaringType.BaseGen.BaseGen != null && Getter.DeclaringType.BaseGen.BaseGen.FullName == "Xamarin.Test.AdapterView")) { force_override = true; } string decl_name = AdjustedName; string virtual_override = String.Empty; bool is_virtual = Getter.IsVirtual && (Setter == null || Setter.IsVirtual); if (with_callbacks && is_virtual) { virtual_override = " virtual"; Getter.GenerateCallback(sw, indent, opt, gen, AdjustedName); } if (with_callbacks && is_virtual && Setter != null) { virtual_override = " virtual"; Setter.GenerateCallback(sw, indent, opt, gen, AdjustedName); } virtual_override = force_override ? " override" : virtual_override; if ((Getter ?? Setter).IsStatic) { virtual_override = " static"; } // It should be using AdjustedName instead of Name, but ICharSequence ("Formatted") properties are not caught by this... else if (gen.BaseSymbol != null && gen.BaseSymbol.GetPropertyByName(Name, true) != null) { virtual_override = " override"; } Getter.GenerateIdField(sw, indent, opt); if (Setter != null) { Setter.GenerateIdField(sw, indent, opt); } string visibility = Getter.IsAbstract && Getter.RetVal.IsGeneric ? "protected" : (Setter ?? Getter).Visibility; // Unlike [Register], mcs does not allow applying [Obsolete] on property accessors, so we can apply them only under limited condition... if (Getter.Deprecated != null && (Setter == null || Setter.Deprecated != null)) { sw.WriteLine("{0}[Obsolete (@\"{1}\")]", indent, Getter.Deprecated.Replace("\"", "\"\"").Trim() + (Setter != null && Setter.Deprecated != Getter.Deprecated ? " " + Setter.Deprecated.Replace("\"", "\"\"").Trim() : null)); } Getter.GenerateCustomAttributes(sw, indent); sw.WriteLine("{0}{1}{2} unsafe {3} {4} {{", indent, visibility, virtual_override, opt.GetOutputName(Getter.ReturnType), decl_name); sw.WriteLine("{0}\t// Metadata.xml XPath method reference: path=\"{1}/method[@name='{2}'{3}]\"", indent, gen.MetadataXPathReference, Getter.JavaName, Getter.Parameters.GetMethodXPathPredicate()); sw.WriteLine("{0}\t[Register (\"{1}\", \"{2}\", \"{3}\"{4})]", indent, Getter.JavaName, Getter.JniSignature, Getter.ConnectorName, Getter.AdditionalAttributeString()); sw.WriteLine("{0}\tget {{", indent); Getter.GenerateBody(sw, indent + "\t\t", opt); sw.WriteLine("{0}\t}}", indent); if (Setter != null) { sw.WriteLine("{0}\t// Metadata.xml XPath method reference: path=\"{1}/method[@name='{2}'{3}]\"", indent, gen.MetadataXPathReference, Setter.JavaName, Setter.Parameters.GetMethodXPathPredicate()); Setter.GenerateCustomAttributes(sw, indent); sw.WriteLine("{0}\t[Register (\"{1}\", \"{2}\", \"{3}\"{4})]", indent, Setter.JavaName, Setter.JniSignature, Setter.ConnectorName, Setter.AdditionalAttributeString()); sw.WriteLine("{0}\tset {{", indent); string pname = Setter.Parameters [0].Name; Setter.Parameters [0].Name = "value"; Setter.GenerateBody(sw, indent + "\t\t", opt); Setter.Parameters [0].Name = pname; sw.WriteLine("{0}\t}}", indent); } else if (GenerateDispatchingSetter) { sw.WriteLine("{0}// This is a dispatching setter", indent + "\t"); sw.WriteLine("{0}set {{ Set{1} (value); }}", indent + "\t", Name); } sw.WriteLine("{0}}}", indent); sw.WriteLine(); if (Type.StartsWith("Java.Lang.ICharSequence") && virtual_override != " override") { GenerateStringVariant(sw, indent); } }