diff --git a/Documentation/docs-mobile/TOC.yml b/Documentation/docs-mobile/TOC.yml index 964ff75e542..dad3d7a2b3a 100644 --- a/Documentation/docs-mobile/TOC.yml +++ b/Documentation/docs-mobile/TOC.yml @@ -240,6 +240,8 @@ href: messages/xa1036.md - name: XA1037 href: messages/xa1037.md + - name: XA1038 + href: messages/xa1038.md - name: "XA2xxx: Linker" items: - name: "XA2xxx: Linker" diff --git a/Documentation/docs-mobile/building-apps/build-properties.md b/Documentation/docs-mobile/building-apps/build-properties.md index c5c59caeaa3..fef97ccc1f9 100644 --- a/Documentation/docs-mobile/building-apps/build-properties.md +++ b/Documentation/docs-mobile/building-apps/build-properties.md @@ -1100,6 +1100,15 @@ Specifies the name of the Resource file to generate. The default template sets this to `Resource.designer.cs`. +## AndroidResourceDesignerClassModifier + +Specifies the class modifier for the intermediate `Resource` class which is +generated. Valid values are `public` and `internal`. + +By default this will be `public`. + +Added in .NET 9. + ## AndroidSdkBuildToolsVersion The Android SDK diff --git a/Documentation/docs-mobile/messages/index.md b/Documentation/docs-mobile/messages/index.md index 50879eb2d28..059e70f039b 100644 --- a/Documentation/docs-mobile/messages/index.md +++ b/Documentation/docs-mobile/messages/index.md @@ -144,6 +144,7 @@ or 'Help->Report a Problem' in Visual Studio for Mac. + [XA1036](xa1036.md): AndroidManifest.xml //uses-sdk/@android:minSdkVersion '29' does not match the $(SupportedOSPlatformVersion) value '21' in the project file (if there is no $(SupportedOSPlatformVersion) value in the project file, then a default value has been assumed). Either change the value in the AndroidManifest.xml to match the $(SupportedOSPlatformVersion) value, or remove the value in the AndroidManifest.xml (and add a $(SupportedOSPlatformVersion) value to the project file if it doesn't already exist). + [XA1037](xa1037.md): The '{0}' MSBuild property is deprecated and will be removed in .NET {1}. See https://aka.ms/net-android-deprecations for more details. ++ [XA1038](xa1038.md): The '{0}' MSBuild property has an invalid value. Value values are {1}. ## XA2xxx: Linker diff --git a/Documentation/docs-mobile/messages/xa1038.md b/Documentation/docs-mobile/messages/xa1038.md new file mode 100644 index 00000000000..c2badffd43e --- /dev/null +++ b/Documentation/docs-mobile/messages/xa1038.md @@ -0,0 +1,21 @@ +--- +title: .NET for Android error XA1038 +description: XA1038 error code +ms.date: 06/27/2024 +--- +# .NET for Android error XA1038 + +## Example messages + +``` +The 'AndroidResourceDesignerClassModifier' MSBuild property has an invalid value of 'foo'. A valid value is one of: 'public', 'internal'. +``` + +## Solution + +Edit your csproj directly and remove the referenced MSBuild property. + +Test your project to ensure the new behavior is functionally equivalent. + +If not, file an [issue](https://github.com/xamarin/xamarin-android/issues) so a +solution can be found before the deprecated flag is removed. diff --git a/src/Xamarin.Android.Build.Tasks/MSBuild/Xamarin/Android/Xamarin.Android.Resource.Designer.targets b/src/Xamarin.Android.Build.Tasks/MSBuild/Xamarin/Android/Xamarin.Android.Resource.Designer.targets index 389d1857e65..3fa46d4a2b9 100644 --- a/src/Xamarin.Android.Build.Tasks/MSBuild/Xamarin/Android/Xamarin.Android.Resource.Designer.targets +++ b/src/Xamarin.Android.Build.Tasks/MSBuild/Xamarin/Android/Xamarin.Android.Resource.Designer.targets @@ -50,6 +50,7 @@ Copyright (C) 2016 Xamarin. All rights reserved. <_GenerateResourceDesignerClassFile Condition=" '$(Language)' == 'F#' ">$(_DesignerIntermediateOutputPath)_$(_DesignerAssemblyName).fs <_GenerateResourceDesignerClassFile Condition=" '$(_GenerateResourceDesignerClassFile)' == '' ">$(_DesignerIntermediateOutputPath)_$(_DesignerAssemblyName).cs <_GenerateResourceCaseMapFile>$(_DesignerIntermediateOutputPath)case_map.txt + public @@ -100,9 +101,18 @@ Copyright (C) 2016 Xamarin. All rights reserved. + diff --git a/src/Xamarin.Android.Build.Tasks/Properties/Resources.resx b/src/Xamarin.Android.Build.Tasks/Properties/Resources.resx index 4b884c849a0..5703c402b83 100644 --- a/src/Xamarin.Android.Build.Tasks/Properties/Resources.resx +++ b/src/Xamarin.Android.Build.Tasks/Properties/Resources.resx @@ -1013,6 +1013,13 @@ To use a custom JDK path for a command line build, set the 'JavaSdkDirectory' MS The following are literal names and should not be translated: MSBuild, .NET. {0} - The deprecated MSBuild property name {1} - The numeric version of .NET + + + The '{0}' MSBuild property has an invalid value of '{1}'. A valid value is one of: {2}. + The following are literal names and should not be translated: MSBuild. +{0} - The MSBuild property name which has invalid values. +{1} - The current value of the property +{2} - The list of valid values for the property these can be Comma-separated. The Android Support libraries are not supported in .NET 9 and later, please migrate to AndroidX. See https://aka.ms/net-android/androidx for more details. diff --git a/src/Xamarin.Android.Build.Tasks/Tasks/GenerateResourceDesignerIntermediateClass.cs b/src/Xamarin.Android.Build.Tasks/Tasks/GenerateResourceDesignerIntermediateClass.cs index 7308996b863..0a8d84f66d3 100644 --- a/src/Xamarin.Android.Build.Tasks/Tasks/GenerateResourceDesignerIntermediateClass.cs +++ b/src/Xamarin.Android.Build.Tasks/Tasks/GenerateResourceDesignerIntermediateClass.cs @@ -29,8 +29,7 @@ namespace %NAMESPACE% { /// Android Resource Designer class. /// Exposes the Android Resource designer assembly into the project Namespace. /// - [GeneratedCode(""%TOOL%"", ""%VERSION%"")] - public partial class Resource : %BASECLASS% { + %MODIFIER% partial class Resource : %BASECLASS% { } #pragma warning restore IDE0002 } @@ -42,16 +41,16 @@ public partial class Resource : %BASECLASS% { //------------------------------------------------------------------------------ namespace %NAMESPACE% -[] -type Resource = %BASECLASS% +type %MODIFIER% Resource = %BASECLASS% "; public string Namespace { get; set; } + public string Modifier { get; set; } = "public"; public bool IsApplication { get; set; } = false; public ITaskItem OutputFile { get; set; } public override bool RunTask () { - string ns = IsApplication ? ResourceDesignerConstants : ResourceDesigner; + string baseClass = IsApplication ? ResourceDesignerConstants : ResourceDesigner; var extension = Path.GetExtension (OutputFile.ItemSpec); var language = string.Compare (extension, ".fs", StringComparison.OrdinalIgnoreCase) == 0 ? "F#" : CodeDomProvider.GetLanguageFromExtension (extension); //bool isVB = string.Equals (extension, ".vb", StringComparison.OrdinalIgnoreCase); @@ -61,14 +60,12 @@ public override bool RunTask () string template = ""; if (isCSharp) { template = CSharpTemplate.Replace ("%NAMESPACE%", Namespace) - .Replace ("%BASECLASS%", ns) - .Replace ("%VERSION%", version.ToString ()) - .Replace ("%TOOL%", nameof (GenerateResourceDesignerIntermediateClass)); + .Replace ("%BASECLASS%", baseClass) + .Replace ("%MODIFIER%", Modifier.ToLower ()); } else if (isFSharp) { template = FSharpTemplate.Replace ("%NAMESPACE%", Namespace) - .Replace ("%BASECLASS%", ns) - .Replace ("%VERSION%", version.ToString ()) - .Replace ("%TOOL%", nameof (GenerateResourceDesignerIntermediateClass)); + .Replace ("%BASECLASS%", baseClass) + .Replace ("%MODIFIER%", Modifier.ToLower ()); } Files.CopyIfStringChanged (template, OutputFile.ItemSpec); diff --git a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.Android.Build.Tests/BuildTest.cs b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.Android.Build.Tests/BuildTest.cs index 2441716dde3..47602ce7249 100644 --- a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.Android.Build.Tests/BuildTest.cs +++ b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.Android.Build.Tests/BuildTest.cs @@ -44,10 +44,10 @@ public void DotNetBuild (string runtimeIdentifiers, bool isRelease, bool aot, bo new Package { Id = "System.Text.Json", Version = "8.0.*" }, }, Sources = { - new BuildItem ("EmbeddedResource", "Foo.resx") { - TextContent = () => InlineData.ResxWithContents ("Cancel") + new BuildItem ("EmbeddedResource", "Resource.resx") { + TextContent = () => InlineData.ResxWithContents ("Cancel"), }, - new BuildItem ("EmbeddedResource", "Foo.es.resx") { + new BuildItem ("EmbeddedResource", "Resource.es.resx") { TextContent = () => InlineData.ResxWithContents ("Cancelar") }, new AndroidItem.TransformFile ("Transforms.xml") { @@ -61,7 +61,8 @@ public void DotNetBuild (string runtimeIdentifiers, bool isRelease, bool aot, bo }, } }; - proj.MainActivity = proj.DefaultMainActivity.Replace (": Activity", ": AndroidX.AppCompat.App.AppCompatActivity"); + proj.MainActivity = proj.DefaultMainActivity.Replace (": Activity", ": AndroidX.AppCompat.App.AppCompatActivity") + .Replace ("//${AFTER_ONCREATE}", @"button.Text = Resource.CancelButton;"); proj.SetProperty ("AndroidUseAssemblyStore", usesAssemblyStore.ToString ()); proj.SetProperty ("RunAOTCompilation", aot.ToString ()); proj.OtherBuildItems.Add (new AndroidItem.InputJar ("javaclasses.jar") { @@ -70,6 +71,21 @@ public void DotNetBuild (string runtimeIdentifiers, bool isRelease, bool aot, bo proj.OtherBuildItems.Add (new BuildItem ("JavaSourceJar", "javaclasses-sources.jar") { BinaryContent = () => ResourceData.JavaSourceJarTestSourcesJar, }); + proj.OtherBuildItems.Add (new BuildItem ("EmbeddedResource", default (Func)) { + Update = () => "Resource.resx", + TextContent = () => InlineData.ResxWithContents ("Cancel"), + Metadata = { + { "Generator", "ResXFileCodeGenerator" }, + { "LastGenOutput", "Resource.designer.cs" } + }, + }); + proj.OtherBuildItems.Add (new BuildItem ("Compile", default (Func)) { + TextContent = () => InlineData.DesignerWithContents (proj.ProjectName, "Resource", "public partial", new string[] {"CancelButton"}), + Update = () => "Resource.designer.cs", + Metadata = { + { "DependentUpon", "Resource.resx" }, + }, + }); proj.AndroidJavaSources.Add (new AndroidItem.AndroidJavaSource ("JavaSourceTestExtension.java") { Encoding = Encoding.ASCII, TextContent = () => ResourceData.JavaSourceTestExtension, diff --git a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.Android.Build.Tests/Utilities/InlineData.cs b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.Android.Build.Tests/Utilities/InlineData.cs index b9b49d4d5a4..7b53d675680 100644 --- a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.Android.Build.Tests/Utilities/InlineData.cs +++ b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.Android.Build.Tests/Utilities/InlineData.cs @@ -37,7 +37,7 @@ namespace @projectName@ [System.CodeDom.Compiler.GeneratedCodeAttribute(""System.Resources.Tools.StronglyTypedResourceBuilder"", ""4.0.0.0"")] [System.Diagnostics.DebuggerNonUserCodeAttribute()] [System.Runtime.CompilerServices.CompilerGeneratedAttribute()] - internal class @className@ { + @modifier@ class @className@ { private static System.Resources.ResourceManager resourceMan; @@ -87,7 +87,7 @@ public static void AddCultureResourcesToProject (IShortFormProject proj, string } } - public static string DesignerWithContents (string projectName, string className, string[] dataNames) + public static string DesignerWithContents (string projectName, string className, string modifier, string[] dataNames) { var content = new StringBuilder (); foreach (string data in dataNames) { @@ -97,7 +97,8 @@ public static string DesignerWithContents (string projectName, string className, }} }}" + Environment.NewLine, data); } - return Designer.Replace ("@className@", className) + return Designer.Replace ("@modifier@", modifier) + .Replace ("@className@", className) .Replace ("@projectName@", projectName) .Replace ("@content@", content.ToString ()); } @@ -105,7 +106,7 @@ public static string DesignerWithContents (string projectName, string className, public static void AddCultureResourceDesignerToProject (IShortFormProject proj, string projectName, string className, params string[] dataNames) { proj.OtherBuildItems.Add (new BuildItem.Source ($"{className}.Designer.cs") { - TextContent = () => InlineData.DesignerWithContents (projectName, className, dataNames) + TextContent = () => InlineData.DesignerWithContents (projectName, className, "internal", dataNames) }); } } diff --git a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Utilities/XmlUtils.cs b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Utilities/XmlUtils.cs index f73aa9ffa5e..c051a841dfa 100644 --- a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Utilities/XmlUtils.cs +++ b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Utilities/XmlUtils.cs @@ -41,7 +41,8 @@ public static string ToXml (IShortFormProject project) if (project.OtherBuildItems.Count > 0) { sb.AppendLine ("\t"); foreach (var bi in project.OtherBuildItems) { - if (bi.BuildAction != BuildActions.EmbeddedResource) { + // If its an EmbeddedResource ignore it, unless it has an Update method set. + if (bi.BuildAction != BuildActions.EmbeddedResource || bi.Update != null) { AppendBuildItem (sb, bi); } } diff --git a/src/Xamarin.Android.Build.Tasks/Xamarin.Android.Common.targets b/src/Xamarin.Android.Build.Tasks/Xamarin.Android.Common.targets index ec20854ee9f..58616a3ddfc 100644 --- a/src/Xamarin.Android.Build.Tasks/Xamarin.Android.Common.targets +++ b/src/Xamarin.Android.Build.Tasks/Xamarin.Android.Common.targets @@ -571,7 +571,7 @@ Copyright (C) 2011-2012 Xamarin. All rights reserved. - +