Merge branch '4.7.0'
This commit is contained in:
Коммит
227dd98ff6
|
@ -19,11 +19,11 @@
|
|||
<dependency id="Xamarin.Android.Support.v4" version="28.0.0.3"/>
|
||||
</group>
|
||||
<group targetFramework="MonoAndroid10.0">
|
||||
<dependency id="Xamarin.AndroidX.Migration" version="1.0.0"/>
|
||||
<dependency id="Xamarin.AndroidX.Migration" version="1.0.0.1"/>
|
||||
<dependency id="Xamarin.Firebase.AppIndexing" version="71.1602.0"/>
|
||||
<dependency id="Xamarin.Android.Support.v4" version="28.0.0.3"/>
|
||||
<dependency id="Xamarin.AndroidX.Lifecycle.LiveData" version="2.1.0"/>
|
||||
<dependency id="Xamarin.AndroidX.Legacy.Support.V4" version="1.0.0"/>
|
||||
<dependency id="Xamarin.AndroidX.Lifecycle.LiveData" version="2.1.0.1"/>
|
||||
<dependency id="Xamarin.AndroidX.Legacy.Support.V4" version="1.0.0.1"/>
|
||||
</group>
|
||||
</dependencies>
|
||||
<references>
|
||||
|
|
|
@ -18,11 +18,11 @@
|
|||
<dependency id="Xamarin.Forms" version="$version$"/>
|
||||
</group>
|
||||
<group targetFramework="MonoAndroid10.0">
|
||||
<dependency id="Xamarin.AndroidX.Migration" version="1.0.0"/>
|
||||
<dependency id="Xamarin.AndroidX.Lifecycle.LiveData" version="2.1.0"/>
|
||||
<dependency id="Xamarin.AndroidX.Legacy.Support.V4" version="1.0.0"/>
|
||||
<dependency id="Xamarin.AndroidX.Legacy.Support.Core.UI" version="1.0.0"/>
|
||||
<dependency id="Xamarin.AndroidX.AppCompat" version="1.1.0"/>
|
||||
<dependency id="Xamarin.AndroidX.Migration" version="1.0.0.1"/>
|
||||
<dependency id="Xamarin.AndroidX.Lifecycle.LiveData" version="2.1.0.1"/>
|
||||
<dependency id="Xamarin.AndroidX.Legacy.Support.V4" version="1.0.0.1"/>
|
||||
<dependency id="Xamarin.AndroidX.Legacy.Support.Core.UI" version="1.0.0.1"/>
|
||||
<dependency id="Xamarin.AndroidX.AppCompat" version="1.1.0.1"/>
|
||||
<dependency id="Xamarin.GooglePlayServices.Maps" version="71.1610.0"/>
|
||||
<dependency id="Xamarin.Forms" version="$version$"/>
|
||||
<dependency id="Xamarin.Android.Support.v4" version="28.0.0.3"/>
|
||||
|
|
|
@ -25,8 +25,8 @@
|
|||
<dependency id="Xamarin.Android.Support.v7.AppCompat" version="28.0.0.3"/>
|
||||
</group>
|
||||
<group targetFramework="MonoAndroid10.0">
|
||||
<dependency id="Xamarin.AndroidX.Lifecycle.LiveData" version="2.1.0" />
|
||||
<dependency id="Xamarin.Google.Android.Material" version="1.0.0" />
|
||||
<dependency id="Xamarin.AndroidX.Lifecycle.LiveData" version="2.1.0.1" />
|
||||
<dependency id="Xamarin.Google.Android.Material" version="1.0.0.1" />
|
||||
</group>
|
||||
<group targetFramework="Xamarin.iOS10">
|
||||
<dependency id="Xamarin.iOS.MaterialComponents" version="92.0.0"/>
|
||||
|
|
|
@ -15,10 +15,10 @@
|
|||
<copyright>© Microsoft Corporation. All rights reserved.</copyright>
|
||||
<dependencies>
|
||||
<group targetFramework="MonoAndroid10.0">
|
||||
<dependency id="Xamarin.AndroidX.Lifecycle.LiveData" version="2.1.0" />
|
||||
<dependency id="Xamarin.Google.Android.Material" version="1.0.0" />
|
||||
<dependency id="Xamarin.AndroidX.Legacy.Support.V4" version="1.0.0" />
|
||||
<dependency id="Xamarin.AndroidX.Browser" version="1.0.0" />
|
||||
<dependency id="Xamarin.AndroidX.Lifecycle.LiveData" version="2.1.0.1" />
|
||||
<dependency id="Xamarin.Google.Android.Material" version="1.0.0.1" />
|
||||
<dependency id="Xamarin.AndroidX.Legacy.Support.V4" version="1.0.0.1" />
|
||||
<dependency id="Xamarin.AndroidX.Browser" version="1.0.0.1" />
|
||||
</group>
|
||||
<group targetFramework="MonoAndroid90">
|
||||
<dependency id="Xamarin.Android.Support.v4" version="28.0.0.3"/>
|
||||
|
|
|
@ -119,8 +119,8 @@
|
|||
</ProjectReference>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Xamarin.AndroidX.MediaRouter" Version="1.1.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.MediaRouter" Version="1.1.0.1" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0.1" />
|
||||
<PackageReference Include="Xamarin.Google.Android.Material" Version="1.1.0-rc3" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(MSBuildExtensionsPath)\Xamarin\Android\Xamarin.Android.CSharp.targets" />
|
||||
|
|
|
@ -1,12 +1,12 @@
|
|||
<Project>
|
||||
<ItemGroup Condition="'$(TargetFrameworkVersion)' == 'v10.0'">
|
||||
<PackageReference Include="Xamarin.AndroidX.Migration">
|
||||
<Version>1.0.0</Version>
|
||||
<Version>1.0.0.1</Version>
|
||||
</PackageReference>
|
||||
<PackageReference Include="Xamarin.AndroidX.Browser" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Palette" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0" />
|
||||
<PackageReference Include="Xamarin.Google.Android.Material" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Legacy.Support.V4" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Browser" Version="1.0.0.1" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Palette" Version="1.0.0.1" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0.1" />
|
||||
<PackageReference Include="Xamarin.Google.Android.Material" Version="1.0.0.1" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Legacy.Support.V4" Version="1.0.0.1" />
|
||||
</ItemGroup>
|
||||
</Project>
|
|
@ -1,12 +1,12 @@
|
|||
<Project>
|
||||
<ItemGroup Condition="'$(TargetFrameworkVersion)' == 'v10.0'">
|
||||
<PackageReference Include="Xamarin.AndroidX.Migration">
|
||||
<Version>1.0.0</Version>
|
||||
<Version>1.0.0.1</Version>
|
||||
</PackageReference>
|
||||
<PackageReference Include="Xamarin.AndroidX.Browser" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Palette" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0" />
|
||||
<PackageReference Include="Xamarin.Google.Android.Material" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Legacy.Support.V4" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Browser" Version="1.0.0.1" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Palette" Version="1.0.0.1" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0.1" />
|
||||
<PackageReference Include="Xamarin.Google.Android.Material" Version="1.0.0.1" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Legacy.Support.V4" Version="1.0.0.1" />
|
||||
</ItemGroup>
|
||||
</Project>
|
|
@ -26,10 +26,10 @@
|
|||
</ProjectReference>
|
||||
</ItemGroup>
|
||||
<ItemGroup Condition="'$(TargetFramework)' == 'MonoAndroid10.0'">
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Legacy.Support.V4" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.Google.Android.Material" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.RecyclerView" Version="1.1.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0.1" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Legacy.Support.V4" Version="1.0.0.1" />
|
||||
<PackageReference Include="Xamarin.Google.Android.Material" Version="1.0.0.1" />
|
||||
<PackageReference Include="Xamarin.AndroidX.RecyclerView" Version="1.1.0.1" />
|
||||
</ItemGroup>
|
||||
<ItemGroup Condition="'$(TargetFramework)' == 'MonoAndroid90'">
|
||||
<PackageReference Include="Xamarin.Android.Support.v4" Version="28.0.0.3" />
|
||||
|
|
|
@ -1,12 +1,12 @@
|
|||
<Project>
|
||||
<ItemGroup Condition="'$(TargetFrameworkVersion)' == 'v10.0'">
|
||||
<PackageReference Include="Xamarin.AndroidX.Migration">
|
||||
<Version>1.0.0</Version>
|
||||
</PackageReference>
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Browser" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.Google.Android.Material" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Legacy.Support.V4" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Palette" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Migration">
|
||||
<Version>1.0.0.1</Version>
|
||||
</PackageReference>
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0.1" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Browser" Version="1.0.0.1" />
|
||||
<PackageReference Include="Xamarin.Google.Android.Material" Version="1.0.0.1" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Legacy.Support.V4" Version="1.0.0.1" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Palette" Version="1.0.0.1" />
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
|
|
|
@ -12,7 +12,6 @@ using Xamarin.Forms.Controls;
|
|||
[assembly: UsesPermission(Android.Manifest.Permission.Internet)]
|
||||
[assembly: UsesPermission(Android.Manifest.Permission.WriteExternalStorage)]
|
||||
|
||||
[assembly: Android.App.MetaData("com.google.android.maps.v2.API_KEY", Value = "AIzaSyAdstcJQswxEjzX5YjLaMcu2aRVEBJw39Y")]
|
||||
[assembly: Xamarin.Forms.ResolutionGroupName(Xamarin.Forms.Controls.Issues.Effects.ResolutionGroupName)]
|
||||
|
||||
// Deliberately broken image source and handler so we can test handling of image loading errors
|
||||
|
|
|
@ -1,6 +0,0 @@
|
|||
using System.Reflection;
|
||||
using System.Runtime.CompilerServices;
|
||||
using System.Runtime.InteropServices;
|
||||
using Android.App;
|
||||
|
||||
[assembly: Android.App.MetaData("com.google.android.maps.v2.API_KEY", Value = "")]
|
|
@ -109,7 +109,6 @@
|
|||
<Compile Include="Tests\TestingPlatformService.cs" />
|
||||
<Compile Include="Tests\PlatformTestSettings.cs" />
|
||||
<Compile Include="PreApplicationClassActivity.cs" />
|
||||
<Compile Include="Properties\MapsKey.cs" />
|
||||
<Compile Include="Properties\AssemblyInfo.cs" />
|
||||
<Compile Include="RegistrarValidationService.cs" />
|
||||
<Compile Include="CustomRenderers.cs" />
|
||||
|
@ -405,12 +404,9 @@
|
|||
<SubType>Designer</SubType>
|
||||
</AndroidResource>
|
||||
</ItemGroup>
|
||||
<ItemGroup Condition="Exists('Properties\MapsKey.cs')">
|
||||
<Compile Include="Properties\MapsKey.cs" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(MSBuildExtensionsPath)\Xamarin\Android\Xamarin.Android.CSharp.targets" />
|
||||
<Import Project="$(SolutionDir)\.nuget\NuGet.targets" Condition="$(FromSource) == 'true' AND Exists('$(SolutionDir)\.nuget\NuGet.targets')" />
|
||||
<Target Name="BeforeBuild">
|
||||
<CreateItem Include="Properties\MapsKey.cs.blank">
|
||||
<Output TaskParameter="Include" ItemName="MapsKey" />
|
||||
</CreateItem>
|
||||
<Copy SourceFiles="@(MapsKey)" DestinationFiles="Properties\MapsKey.cs" Condition="!Exists('Properties\MapsKey.cs')" />
|
||||
</Target>
|
||||
<Import Project="$(SolutionDir)\.nuget\NuGet.targets" Condition="Exists('$(SolutionDir)\.nuget\NuGet.targets')" />
|
||||
</Project>
|
||||
|
|
|
@ -22,7 +22,7 @@ namespace Xamarin.Forms.ControlGallery.Tizen
|
|||
{
|
||||
var app = new MainApplication();
|
||||
FormsMaps.Init("HERE", "write-your-API-key-here");
|
||||
Forms.SetFlags("CollectionView_Experimental", "Shell_Experimental", "MediaElement_Experimental", "IndicatorView_Experimental");
|
||||
Forms.SetFlags("CollectionView_Experimental", "Shell_Experimental", "MediaElement_Experimental");
|
||||
Forms.Init(app);
|
||||
FormsMaterial.Init();
|
||||
app.Run(args);
|
||||
|
|
|
@ -27,9 +27,6 @@ namespace Xamarin.Forms.Controls.Issues
|
|||
|
||||
protected override void Init()
|
||||
{
|
||||
#if APP
|
||||
Device.SetFlags(new List<string>(Device.Flags ?? new List<string>()) { "IndicatorView_Experimental" });
|
||||
#endif
|
||||
var layout = new StackLayout();
|
||||
|
||||
var instructions = new Label
|
||||
|
|
|
@ -21,7 +21,6 @@ namespace Xamarin.Forms.Controls.Issues
|
|||
public Issue8958()
|
||||
{
|
||||
#if APP
|
||||
Device.SetFlags(new List<string>(Device.Flags ?? new List<string>()) { "IndicatorView_Experimental" });
|
||||
InitializeComponent();
|
||||
#endif
|
||||
}
|
||||
|
|
|
@ -30,7 +30,7 @@ namespace Xamarin.Forms.Controls.Issues
|
|||
public Issue9827()
|
||||
{
|
||||
#if APP
|
||||
Device.SetFlags(new List<string>(Device.Flags ?? new List<string>()) { ExperimentalFlags.IndicatorViewExperimental, ExperimentalFlags.CarouselViewExperimental });
|
||||
Device.SetFlags(new List<string>(Device.Flags ?? new List<string>()) { ExperimentalFlags.CarouselViewExperimental });
|
||||
InitializeComponent();
|
||||
#endif
|
||||
}
|
||||
|
|
|
@ -66,7 +66,7 @@ namespace Xamarin.Forms.Controls.GalleryPages.CollectionViewGalleries.CarouselVi
|
|||
button.TextColor = Color.Black;
|
||||
button.IsEnabled = false;
|
||||
|
||||
Device.SetFlags(new[] { ExperimentalFlags.CarouselViewExperimental, ExperimentalFlags.IndicatorViewExperimental });
|
||||
Device.SetFlags(new[] { ExperimentalFlags.CarouselViewExperimental });
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,6 +1,4 @@
|
|||
using System;
|
||||
|
||||
namespace Xamarin.Forms.Controls.GalleryPages
|
||||
namespace Xamarin.Forms.Controls.GalleryPages
|
||||
{
|
||||
public class IndicatorGalleries : ContentPage
|
||||
{
|
||||
|
@ -11,13 +9,6 @@ namespace Xamarin.Forms.Controls.GalleryPages
|
|||
|
||||
Title = "IndicatorView Galleries";
|
||||
|
||||
var button = new Button
|
||||
{
|
||||
Text = "Enable IndicatorView",
|
||||
AutomationId = "EnableIndicator"
|
||||
};
|
||||
button.Clicked += ButtonClicked;
|
||||
|
||||
Content = new ScrollView
|
||||
{
|
||||
Content = new StackLayout
|
||||
|
@ -25,7 +16,6 @@ namespace Xamarin.Forms.Controls.GalleryPages
|
|||
Children =
|
||||
{
|
||||
descriptionLabel,
|
||||
button,
|
||||
GalleryBuilder.NavButton("IndicatorView Gallery", () =>
|
||||
new IndicatorsSample(), Navigation),
|
||||
GalleryBuilder.NavButton("Indicator MaxVisible Gallery", () =>
|
||||
|
@ -34,16 +24,5 @@ namespace Xamarin.Forms.Controls.GalleryPages
|
|||
}
|
||||
};
|
||||
}
|
||||
|
||||
void ButtonClicked(object sender, EventArgs e)
|
||||
{
|
||||
var button = sender as Button;
|
||||
|
||||
button.Text = "IndicatorView Enabled!";
|
||||
button.TextColor = Color.Black;
|
||||
button.IsEnabled = false;
|
||||
|
||||
Device.SetFlags(new[] { ExperimentalFlags.IndicatorViewExperimental });
|
||||
}
|
||||
}
|
||||
}
|
|
@ -16,28 +16,31 @@ namespace Xamarin.Forms.Controls.GalleryPages.ShapesGalleries
|
|||
};
|
||||
button.Clicked += ButtonClicked;
|
||||
|
||||
Content = new StackLayout
|
||||
Content = new ScrollView
|
||||
{
|
||||
Children =
|
||||
{
|
||||
button,
|
||||
GalleryBuilder.NavButton("Path Gallery", () => new PathGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Path Aspect Gallery", () => new PathAspectGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Path LayoutOptions Gallery", () => new PathLayoutOptionsGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Transform Playground", () => new TransformPlaygroundGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Path Transform using string (TypeConverter) Gallery", () => new PathTransformStringGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Clip Gallery", () => new ClipGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Clip Views Gallery", () => new ClipViewsGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Add/Remove Clip Gallery", () => new AddRemoveClipGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Clip Performance Gallery", () => new ClipPerformanceGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Ellipse Gallery", () => new EllipseGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Line Gallery", () => new LineGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Polygon Gallery", () => new PolygonGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Polyline Gallery", () => new PolylineGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Rectangle Gallery", () => new RectangleGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("LineCap Gallery", () => new LineCapGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("LineJoin Gallery", () => new LineJoinGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("AutoSize Shapes Gallery", () => new AutoSizeShapesGallery(), Navigation)
|
||||
Content = new StackLayout
|
||||
{
|
||||
Children =
|
||||
{
|
||||
button,
|
||||
GalleryBuilder.NavButton("Ellipse Gallery", () => new EllipseGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Line Gallery", () => new LineGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Polygon Gallery", () => new PolygonGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Polyline Gallery", () => new PolylineGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Rectangle Gallery", () => new RectangleGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("LineCap Gallery", () => new LineCapGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("LineJoin Gallery", () => new LineJoinGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("AutoSize Shapes Gallery", () => new AutoSizeShapesGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Path Gallery", () => new PathGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Path Aspect Gallery", () => new PathAspectGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Path LayoutOptions Gallery", () => new PathLayoutOptionsGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Transform Playground", () => new TransformPlaygroundGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Path Transform using string (TypeConverter) Gallery", () => new PathTransformStringGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Clip Gallery", () => new ClipGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Clip Views Gallery", () => new ClipViewsGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Add/Remove Clip Gallery", () => new AddRemoveClipGallery(), Navigation),
|
||||
GalleryBuilder.NavButton("Clip Performance Gallery", () => new ClipPerformanceGallery(), Navigation)
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
|
|
|
@ -307,15 +307,15 @@ namespace Xamarin.Forms.Controls.XamStore
|
|||
Content = new ScrollView { Content = grid };
|
||||
|
||||
|
||||
grid.Children.Add(MakeButton("FlyoutBackdrop Color",
|
||||
() =>
|
||||
{
|
||||
if (Shell.GetFlyoutBackdropColor(Shell.Current) == Color.Default)
|
||||
Shell.SetFlyoutBackdropColor(Shell.Current, Color.Purple);
|
||||
else
|
||||
Shell.SetFlyoutBackdropColor(Shell.Current, Color.Default);
|
||||
}),
|
||||
0, 21);
|
||||
//grid.Children.Add(MakeButton("FlyoutBackdrop Color",
|
||||
// () =>
|
||||
// {
|
||||
// if (Shell.GetFlyoutBackdropColor(Shell.Current) == Color.Default)
|
||||
// Shell.SetFlyoutBackdropColor(Shell.Current, Color.Purple);
|
||||
// else
|
||||
// Shell.SetFlyoutBackdropColor(Shell.Current, Color.Default);
|
||||
// }),
|
||||
// 0, 21);
|
||||
|
||||
grid.Children.Add(MakeButton("Hide Nav Shadow",
|
||||
() => Shell.SetNavBarHasShadow(this, false)),
|
||||
|
|
|
@ -33,16 +33,8 @@ namespace Xamarin.Forms.Core.UnitTests
|
|||
}
|
||||
|
||||
[Test]
|
||||
public void TestChildOneWayOverridesMultiTwoWay()
|
||||
public void TestChildOneWayOnMultiTwoWay()
|
||||
{
|
||||
// This tests a weird edge case where the MultiBinding is TwoWay but
|
||||
// one of the child bindings is OneWay. This results in a situation where
|
||||
// you actually can't change the target value to be inconsistent with the
|
||||
// the source value for the OneWay because ConvertBack causes Convert
|
||||
// to get re-evaluated (and this effectively negates the change to the
|
||||
// target). This ensures that the target and source never go out of sync,
|
||||
// as the overall binding is still TwoWay.
|
||||
|
||||
var group = new GroupViewModel();
|
||||
var stack = new StackLayout
|
||||
{
|
||||
|
@ -71,8 +63,7 @@ namespace Xamarin.Forms.Core.UnitTests
|
|||
Assert.AreEqual(oldName, label.Text);
|
||||
Assert.AreEqual(oldName, group.Person1.FullName);
|
||||
|
||||
label.Text = $"{oldFirstName.ToUpper()} {oldMiddleName} {oldLastName.ToUpper()}";
|
||||
Assert.AreEqual($"{oldFirstName} {oldMiddleName} {oldLastName.ToUpper()}", label.Text);
|
||||
label.SetValueCore(Label.TextProperty, $"{oldFirstName.ToUpper()} {oldMiddleName} {oldLastName.ToUpper()}", Internals.SetValueFlags.None);
|
||||
Assert.AreEqual($"{oldFirstName} {oldMiddleName} {oldLastName.ToUpper()}", group.Person1.FullName);
|
||||
}
|
||||
|
||||
|
@ -100,7 +91,7 @@ namespace Xamarin.Forms.Core.UnitTests
|
|||
Assert.AreEqual("Courier New 12 Italic", entry1.Text);
|
||||
// Our unit test's ConvertBack should throw an exception below because the desired
|
||||
// return types aren't all strings
|
||||
Assert.Throws<Exception>(new TestDelegate(() => entry1.Text = "Arial 12 Italic"));
|
||||
Assert.Throws<Exception>(() => entry1.SetValueCore(Entry.TextProperty, "Arial 12 Italic", Internals.SetValueFlags.None));
|
||||
|
||||
// FindAncestor and FindAncestorBindingContext
|
||||
// are already tested in TestNestedMultiBindings
|
||||
|
@ -137,14 +128,10 @@ namespace Xamarin.Forms.Core.UnitTests
|
|||
var checkBox = new CheckBox();
|
||||
checkBox.SetBinding(
|
||||
CheckBox.IsCheckedProperty,
|
||||
new MultiBinding
|
||||
{
|
||||
Bindings = new Collection<BindingBase>
|
||||
{
|
||||
new MultiBinding
|
||||
{
|
||||
Bindings = new Collection<BindingBase>
|
||||
{
|
||||
new MultiBinding {
|
||||
Bindings = {
|
||||
new MultiBinding {
|
||||
Bindings = {
|
||||
new Binding(nameof(PersonViewModel.IsOver16)),
|
||||
new Binding(nameof(PersonViewModel.HasPassedTest)),
|
||||
new Binding(nameof(PersonViewModel.IsSuspended), converter: new Inverter()),
|
||||
|
@ -162,7 +149,8 @@ namespace Xamarin.Forms.Core.UnitTests
|
|||
$"{nameof(Element.BindingContext)}.{nameof(GroupViewModel.PardonAllSuspensions)}",
|
||||
source: new RelativeBindingSource(RelativeBindingSourceMode.FindAncestor, typeof(StackLayout))),
|
||||
},
|
||||
Converter = new AnyTrueMultiConverter()
|
||||
Converter = new AnyTrueMultiConverter(),
|
||||
FallbackValue = false,
|
||||
});
|
||||
|
||||
// ^^
|
||||
|
@ -235,22 +223,22 @@ namespace Xamarin.Forms.Core.UnitTests
|
|||
|
||||
var label2 = GenerateNameLabel(nameof(group.Person2), BindingMode.TwoWay);
|
||||
stack.Children.Add(label2);
|
||||
label2.Text = $"DoNothing {oldMiddleName} {oldLastName.ToUpper()}";
|
||||
label2.SetValueCore(Label.TextProperty, $"DoNothing {oldMiddleName} {oldLastName.ToUpper()}", Internals.SetValueFlags.None);
|
||||
Assert.AreEqual($"{oldFirstName} {oldMiddleName} {oldLastName.ToUpper()}", group.Person2.FullName);
|
||||
Assert.AreEqual(group.Person2.FullName, label2.Text);
|
||||
Assert.AreEqual($"DoNothing {oldMiddleName} {oldLastName.ToUpper()}", label2.Text);
|
||||
|
||||
label2.Text = oldName;
|
||||
Assert.AreEqual(oldName, group.Person2.FullName);
|
||||
Assert.AreEqual(oldName, label2.Text);
|
||||
// Any UnsetValue prevents any changes to source but target accepts value
|
||||
label2.Text = $"{oldFirstName.ToUpper()} UnsetValue {oldLastName}";
|
||||
Assert.AreEqual(oldName, group.Person2.FullName);
|
||||
label2.SetValueCore(Label.TextProperty, $"{oldFirstName.ToUpper()} UnsetValue {oldLastName}");
|
||||
Assert.AreEqual($"{oldFirstName.ToUpper()} {oldMiddleName} {oldLastName}", group.Person2.FullName);
|
||||
Assert.AreEqual($"{oldFirstName.ToUpper()} UnsetValue {oldLastName}", label2.Text);
|
||||
|
||||
label2.Text = oldName;
|
||||
Assert.AreEqual(oldName, group.Person2.FullName);
|
||||
Assert.AreEqual(oldName, label2.Text);
|
||||
label2.Text = "null";
|
||||
label2.SetValueCore(Label.TextProperty, "null");
|
||||
// Returning null prevents changes to source but target accepts value
|
||||
Assert.AreEqual(oldName, group.Person2.FullName);
|
||||
Assert.AreEqual("null", label2.Text);
|
||||
|
@ -259,67 +247,65 @@ namespace Xamarin.Forms.Core.UnitTests
|
|||
label2.Text = oldName;
|
||||
Assert.AreEqual(oldName, group.Person2.FullName);
|
||||
Assert.AreEqual(oldName, label2.Text);
|
||||
label2.Text = $"Duck Duck";
|
||||
label2.SetValueCore(Label.TextProperty, $"Duck Duck", Internals.SetValueFlags.None);
|
||||
Assert.AreEqual($"Duck Duck {oldLastName}", group.Person2.FullName);
|
||||
// Target can't go out of sync with source
|
||||
Assert.AreEqual($"Duck Duck {oldLastName}", label2.Text);
|
||||
Assert.AreEqual($"Duck Duck", label2.Text);
|
||||
|
||||
// Too many members are no problem either
|
||||
label2.Text = oldName;
|
||||
Assert.AreEqual(oldName, group.Person2.FullName);
|
||||
label2.Text = oldName + " Extra";
|
||||
label2.SetValueCore(Label.TextProperty, oldName + " Extra", Internals.SetValueFlags.None);
|
||||
Assert.AreEqual(oldName, group.Person2.FullName);
|
||||
// Target still won't go out of sync with source
|
||||
Assert.AreEqual(oldName, label2.Text);
|
||||
Assert.AreEqual(oldName + " Extra", label2.Text);
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void TestEfficiency()
|
||||
{
|
||||
var group = new GroupViewModel();
|
||||
var stack = new StackLayout
|
||||
{
|
||||
BindingContext = group.Person1
|
||||
};
|
||||
//[Test]
|
||||
//public void TestEfficiency()
|
||||
//{
|
||||
// var group = new GroupViewModel();
|
||||
// var stack = new StackLayout
|
||||
// {
|
||||
// BindingContext = group.Person1
|
||||
// };
|
||||
|
||||
string oldName = group.Person1.FullName;
|
||||
// string oldName = group.Person1.FullName;
|
||||
|
||||
var converter = new StringConcatenationConverter();
|
||||
// var converter = new StringConcatenationConverter();
|
||||
|
||||
var label = new Label();
|
||||
label.SetBinding(Label.TextProperty, new MultiBinding
|
||||
{
|
||||
Bindings = new Collection<BindingBase>
|
||||
{
|
||||
new Binding(nameof(PersonViewModel.FirstName)),
|
||||
new Binding(nameof(PersonViewModel.MiddleName)),
|
||||
new Binding(nameof(PersonViewModel.LastName)),
|
||||
},
|
||||
Converter = converter,
|
||||
Mode = BindingMode.TwoWay,
|
||||
});
|
||||
// var label = new Label();
|
||||
// label.SetBinding(Label.TextProperty, new MultiBinding
|
||||
// {
|
||||
// Bindings = new Collection<BindingBase>
|
||||
// {
|
||||
// new Binding(nameof(PersonViewModel.FirstName)),
|
||||
// new Binding(nameof(PersonViewModel.MiddleName)),
|
||||
// new Binding(nameof(PersonViewModel.LastName)),
|
||||
// },
|
||||
// Converter = converter,
|
||||
// Mode = BindingMode.TwoWay,
|
||||
// });
|
||||
|
||||
// Initial binding should result in 1 Convert, no ConvertBack's
|
||||
Assert.AreEqual(1, converter.Converts);
|
||||
Assert.AreEqual(0, converter.ConvertBacks);
|
||||
// // Initial binding should result in 1 Convert, no ConvertBack's
|
||||
// Assert.AreEqual(1, converter.Converts);
|
||||
// Assert.AreEqual(0, converter.ConvertBacks);
|
||||
|
||||
// Parenting results in bctx change; should be 1 additional Convert, no ConvertBack's
|
||||
stack.Children.Add(label);
|
||||
Assert.AreEqual(group.Person1.FullName, label.Text);
|
||||
Assert.AreEqual(2, converter.Converts);
|
||||
Assert.AreEqual(0, converter.ConvertBacks);
|
||||
// // Parenting results in bctx change; should be 1 additional Convert, no ConvertBack's
|
||||
// stack.Children.Add(label);
|
||||
// Assert.AreEqual(group.Person1.FullName, label.Text);
|
||||
// Assert.AreEqual(2, converter.Converts);
|
||||
// Assert.AreEqual(0, converter.ConvertBacks);
|
||||
|
||||
// Source change results in 1 additional Convert, no ConvertBack's
|
||||
group.Person1.FirstName = group.Person1.FullName.ToUpper();
|
||||
Assert.AreEqual(3, converter.Converts);
|
||||
Assert.AreEqual(0, converter.ConvertBacks);
|
||||
// // Source change results in 1 additional Convert, no ConvertBack's
|
||||
// group.Person1.FirstName = group.Person1.FullName.ToUpper();
|
||||
// Assert.AreEqual(3, converter.Converts);
|
||||
// Assert.AreEqual(0, converter.ConvertBacks);
|
||||
|
||||
// Target change results in 1 ConvertBack, one additional Convert
|
||||
label.Text = oldName;
|
||||
Assert.AreEqual(oldName, group.Person1.FullName);
|
||||
Assert.AreEqual(4, converter.Converts);
|
||||
Assert.AreEqual(1, converter.ConvertBacks);
|
||||
}
|
||||
// // Target change results in 1 ConvertBack, one additional Convert
|
||||
// label.Text = oldName;
|
||||
// Assert.AreEqual(oldName, group.Person1.FullName);
|
||||
// Assert.AreEqual(4, converter.Converts);
|
||||
// Assert.AreEqual(1, converter.ConvertBacks);
|
||||
//}
|
||||
|
||||
[Test]
|
||||
public void TestBindingModes()
|
||||
|
@ -335,7 +321,6 @@ namespace Xamarin.Forms.Core.UnitTests
|
|||
stack.Children.Add(label1W);
|
||||
Assert.AreEqual(group.Person1.FullName, label1W.Text);
|
||||
label1W.SetValueCore(Label.TextProperty, "don't change source", Internals.SetValueFlags.None);
|
||||
Assert.AreEqual("don't change source", label1W.Text);
|
||||
Assert.AreEqual(oldName, group.Person1.FullName);
|
||||
|
||||
var label2W = GenerateNameLabel(nameof(group.Person2), BindingMode.TwoWay);
|
||||
|
@ -347,10 +332,8 @@ namespace Xamarin.Forms.Core.UnitTests
|
|||
oldName = group.Person3.FullName;
|
||||
var label1WTS = GenerateNameLabel(nameof(group.Person3), BindingMode.OneWayToSource);
|
||||
stack.Children.Add(label1WTS);
|
||||
// Initial value is target fallback
|
||||
Assert.AreEqual(c_Fallback, label1WTS.Text);
|
||||
Assert.AreEqual(c_Fallback, group.Person3.FullName);
|
||||
label1WTS.Text = oldName;
|
||||
Assert.AreEqual(Label.TextProperty.DefaultValue, label1WTS.Text);
|
||||
label1WTS.SetValueCore(Label.TextProperty, oldName, Internals.SetValueFlags.None);
|
||||
Assert.AreEqual(oldName, label1WTS.Text);
|
||||
Assert.AreEqual(oldName, group.Person3.FullName);
|
||||
|
||||
|
@ -369,6 +352,24 @@ namespace Xamarin.Forms.Core.UnitTests
|
|||
Assert.AreEqual(group.Person1.FullName, label1T.Text);
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void TestStringFormat()
|
||||
{
|
||||
var property = BindableProperty.Create("foo", typeof(string), typeof(MockBindable), null);
|
||||
var bindable = new MockBindable();
|
||||
var multibinding = new MultiBinding {
|
||||
Bindings = {
|
||||
new Binding ("foo"),
|
||||
new Binding ("bar"),
|
||||
new Binding ("baz"),
|
||||
},
|
||||
StringFormat = "{0} - {1} - {2}"
|
||||
};
|
||||
Assert.DoesNotThrow(()=>bindable.SetBinding(property, multibinding));
|
||||
Assert.DoesNotThrow(()=>bindable.BindingContext = new { foo = "FOO", bar = 42, baz = "BAZ" });
|
||||
Assert.That(bindable.GetValue(property), Is.EqualTo("FOO - 42 - BAZ"));
|
||||
}
|
||||
|
||||
private Label GenerateNameLabel(string person, BindingMode mode)
|
||||
{
|
||||
var label = new Label();
|
||||
|
@ -479,7 +480,7 @@ namespace Xamarin.Forms.Core.UnitTests
|
|||
|
||||
if (values is null)
|
||||
return null;
|
||||
string concatenator = parameter as string ?? " ";
|
||||
string separator = parameter as string ?? " ";
|
||||
StringBuilder sb = new StringBuilder();
|
||||
int i = 0;
|
||||
|
||||
|
@ -495,8 +496,8 @@ namespace Xamarin.Forms.Core.UnitTests
|
|||
if (value as string == "null")
|
||||
return null;
|
||||
|
||||
if (i != 0 && concatenator != null)
|
||||
sb.Append(concatenator);
|
||||
if (i != 0 && separator != null)
|
||||
sb.Append(separator);
|
||||
sb.Append(value?.ToString());
|
||||
i++;
|
||||
}
|
||||
|
@ -511,13 +512,13 @@ namespace Xamarin.Forms.Core.UnitTests
|
|||
if (s == "null" || string.IsNullOrEmpty(s))
|
||||
return null;
|
||||
|
||||
string concatenator = parameter as string ?? " ";
|
||||
string separator = parameter as string ?? " ";
|
||||
|
||||
if (!targetTypes.All(t => t == typeof(string)))
|
||||
if (!targetTypes.All(t=>t==typeof(object)) && !targetTypes.All(t => t == typeof(string)))
|
||||
// Normally we'd return null but throw exception just for unit test to catch
|
||||
throw new Exception("Invalid targetTypes");
|
||||
|
||||
var array = s.Split(new string[] { concatenator }, StringSplitOptions.RemoveEmptyEntries).Cast<object>().ToArray();
|
||||
var array = s.Split(new string[] { separator }, StringSplitOptions.RemoveEmptyEntries).Cast<object>().ToArray();
|
||||
for (int i = 0; i < array.Length; i++)
|
||||
{
|
||||
var str = array[i] as string;
|
||||
|
@ -858,12 +859,12 @@ namespace Xamarin.Forms.Core.UnitTests
|
|||
source: new RelativeBindingSource(RelativeBindingSourceMode.TemplatedParent)));
|
||||
cp.SetBinding(ContentPresenter.IsVisibleProperty, new MultiBinding
|
||||
{
|
||||
Bindings = new Collection<BindingBase>
|
||||
{
|
||||
Bindings = {
|
||||
new Binding(nameof(ExpanderControl.IsEnabled), source: RelativeBindingSource.TemplatedParent),
|
||||
new Binding(nameof(ExpanderControl.IsExpanded), source: RelativeBindingSource.TemplatedParent)
|
||||
},
|
||||
Converter = new AllTrueMultiConverter()
|
||||
Converter = new AllTrueMultiConverter(),
|
||||
FallbackValue = false
|
||||
});
|
||||
this.Children.Add(cp);
|
||||
}
|
||||
|
|
|
@ -403,7 +403,7 @@ namespace Xamarin.Forms.Core.UnitTests
|
|||
{
|
||||
var shell = new Shell();
|
||||
ShellTestPage pagetoTest = new ShellTestPage();
|
||||
pagetoTest.BindingContext = pagetoTest;
|
||||
pagetoTest.BindingContext = pagetoTest;
|
||||
var one = CreateShellItem(pagetoTest, shellContentRoute: "content", templated: useDataTemplates);
|
||||
shell.Items.Add(one);
|
||||
ShellTestPage page = null;
|
||||
|
@ -1362,10 +1362,10 @@ namespace Xamarin.Forms.Core.UnitTests
|
|||
var classStyle = new Style(typeof(Grid))
|
||||
{
|
||||
Setters = {
|
||||
new Setter
|
||||
new Setter
|
||||
{
|
||||
Property = VisualStateManager.VisualStateGroupsProperty,
|
||||
Value = groups
|
||||
Value = groups
|
||||
}
|
||||
},
|
||||
Class = FlyoutItem.LayoutStyle,
|
||||
|
@ -1429,6 +1429,57 @@ namespace Xamarin.Forms.Core.UnitTests
|
|||
Assert.IsNotNull(item.CurrentItem.CurrentItem);
|
||||
}
|
||||
|
||||
[TestCase("ContentPage")]
|
||||
[TestCase("ShellItem")]
|
||||
[TestCase("Shell")]
|
||||
public void TabBarIsVisible(string test)
|
||||
{
|
||||
Shell shell = new Shell();
|
||||
ContentPage page = new ContentPage();
|
||||
var shellItem = CreateShellItem(page);
|
||||
shell.Items.Add(shellItem);
|
||||
|
||||
switch (test)
|
||||
{
|
||||
case "ContentPage":
|
||||
Shell.SetTabBarIsVisible(page, false);
|
||||
break;
|
||||
case "ShellItem":
|
||||
Shell.SetTabBarIsVisible(shellItem, false);
|
||||
break;
|
||||
case "Shell":
|
||||
Shell.SetTabBarIsVisible(shell, false);
|
||||
break;
|
||||
}
|
||||
|
||||
Assert.IsFalse((shellItem as IShellItemController).ShowTabs);
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void SendStructureChangedFiresWhenAddingItems()
|
||||
{
|
||||
Shell shell = new Shell();
|
||||
shell.Items.Add(CreateShellItem());
|
||||
|
||||
int count = 0;
|
||||
int previousCount = 0;
|
||||
(shell as IShellController).StructureChanged += (_, __) => count++;
|
||||
|
||||
|
||||
shell.Items.Add(CreateShellItem());
|
||||
Assert.Greater(count, previousCount, "StructureChanged not fired when adding Shell Item");
|
||||
|
||||
previousCount = count;
|
||||
shell.CurrentItem.Items.Add(CreateShellSection());
|
||||
Assert.Greater(count, previousCount, "StructureChanged not fired when adding Shell Section");
|
||||
|
||||
previousCount = count;
|
||||
shell.CurrentItem.CurrentItem.Items.Add(CreateShellContent());
|
||||
Assert.Greater(count, previousCount, "StructureChanged not fired when adding Shell Content");
|
||||
|
||||
}
|
||||
|
||||
|
||||
//[Test]
|
||||
//public void FlyoutItemLabelStyleCanBeChangedAfterRendered()
|
||||
//{
|
||||
|
|
|
@ -148,7 +148,7 @@ namespace Xamarin.Forms
|
|||
if (!(Source is RelativeBindingSource relativeSource))
|
||||
return;
|
||||
|
||||
var relativeSourceTarget = this.RelativeSourceTargetOverride ?? targetObject as Element;
|
||||
var relativeSourceTarget = RelativeSourceTargetOverride ?? targetObject as Element;
|
||||
if (!(relativeSourceTarget is Element))
|
||||
throw new InvalidOperationException();
|
||||
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
using System;
|
||||
using System.Collections;
|
||||
using System.Runtime.CompilerServices;
|
||||
using Xamarin.Forms.Internals;
|
||||
|
||||
namespace Xamarin.Forms
|
||||
{
|
||||
|
@ -42,7 +43,6 @@ namespace Xamarin.Forms
|
|||
set
|
||||
{
|
||||
ThrowIfApplied();
|
||||
|
||||
_stringFormat = value;
|
||||
}
|
||||
}
|
||||
|
@ -109,18 +109,12 @@ namespace Xamarin.Forms
|
|||
protected void ThrowIfApplied()
|
||||
{
|
||||
if (IsApplied)
|
||||
throw new InvalidOperationException("Can not change a binding while it's applied");
|
||||
throw new InvalidOperationException("Cannot change a binding while it's applied");
|
||||
}
|
||||
|
||||
internal virtual void Apply(bool fromTarget)
|
||||
{
|
||||
IsApplied = true;
|
||||
}
|
||||
internal virtual void Apply(bool fromTarget) => IsApplied = true;
|
||||
|
||||
internal virtual void Apply(object context, BindableObject bindObj, BindableProperty targetProperty, bool fromBindingContextChanged = false)
|
||||
{
|
||||
IsApplied = true;
|
||||
}
|
||||
internal virtual void Apply(object context, BindableObject bindObj, BindableProperty targetProperty, bool fromBindingContextChanged = false) => IsApplied = true;
|
||||
|
||||
internal abstract BindingBase Clone();
|
||||
|
||||
|
@ -129,17 +123,39 @@ namespace Xamarin.Forms
|
|||
if (value == null && TargetNullValue != null)
|
||||
return TargetNullValue;
|
||||
|
||||
if (StringFormat != null)
|
||||
return string.Format(StringFormat, value);
|
||||
if (StringFormat != null && TryFormat(StringFormat, value, out var formatted))
|
||||
return formatted;
|
||||
|
||||
return value;
|
||||
}
|
||||
|
||||
internal virtual object GetTargetValue(object value, Type sourcePropertyType)
|
||||
internal bool TryFormat(string format, object arg0, out string value)
|
||||
{
|
||||
return value;
|
||||
try {
|
||||
value = string.Format(format, arg0);
|
||||
return true;
|
||||
} catch (FormatException) {
|
||||
value = null;
|
||||
Log.Warning("Binding", "FormatException");
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
internal bool TryFormat(string format, object[] args, out string value)
|
||||
{
|
||||
try {
|
||||
value = string.Format(format, args);
|
||||
return true;
|
||||
}
|
||||
catch (FormatException) {
|
||||
value = null;
|
||||
Log.Warning("Binding", "FormatException");
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
internal virtual object GetTargetValue(object value, Type sourcePropertyType) => value;
|
||||
|
||||
internal static bool TryGetSynchronizedCollection(IEnumerable collection, out CollectionSynchronizationContext synchronizationContext)
|
||||
{
|
||||
if (collection == null)
|
||||
|
@ -148,9 +164,6 @@ namespace Xamarin.Forms
|
|||
return SynchronizedCollections.TryGetValue(collection, out synchronizationContext);
|
||||
}
|
||||
|
||||
internal virtual void Unapply(bool fromBindingContextChanged = false)
|
||||
{
|
||||
IsApplied = false;
|
||||
}
|
||||
internal virtual void Unapply(bool fromBindingContextChanged = false) => IsApplied = false;
|
||||
}
|
||||
}
|
|
@ -10,7 +10,6 @@ namespace Xamarin.Forms
|
|||
internal static class ExperimentalFlags
|
||||
{
|
||||
internal const string StateTriggersExperimental = "StateTriggers_Experimental";
|
||||
internal const string IndicatorViewExperimental = "IndicatorView_Experimental";
|
||||
internal const string ShellUWPExperimental = "Shell_UWP_Experimental";
|
||||
internal const string CarouselViewExperimental = "CarouselView_Experimental";
|
||||
internal const string SwipeViewExperimental = "SwipeView_Experimental";
|
||||
|
|
|
@ -39,7 +39,7 @@ namespace Xamarin.Forms
|
|||
|
||||
public IndicatorView()
|
||||
{
|
||||
ExperimentalFlags.VerifyFlagEnabled(nameof(IndicatorView), ExperimentalFlags.IndicatorViewExperimental);
|
||||
|
||||
}
|
||||
|
||||
public IndicatorShape IndicatorsShape
|
||||
|
|
|
@ -1,72 +0,0 @@
|
|||
namespace Xamarin.Forms.Internals
|
||||
{
|
||||
// This class serves as a "proxy" for the target and the sources,
|
||||
// with the MultiBinding serving as the bridge between them.
|
||||
// All the BindingExpression's actually bind between the proxies and the
|
||||
// target/sources. This avoids the need for what would otherwise be some very
|
||||
// ugly subclassing or modifications to BindingExpression. And it
|
||||
// makes it very easy to supported nested MultiBinding's which is
|
||||
// not possible with WPF.
|
||||
internal class MultiBindingProxy : BindableObject
|
||||
{
|
||||
internal bool SuspendValueChangeNotification { get; private set; }
|
||||
|
||||
internal bool IsTarget { get; }
|
||||
|
||||
public static readonly BindableProperty ValueProperty = BindableProperty.Create(
|
||||
nameof(Value),
|
||||
typeof(object),
|
||||
typeof(MultiBindingProxy),
|
||||
null,
|
||||
propertyChanged:
|
||||
new BindableProperty.BindingPropertyChangedDelegate(
|
||||
(obj, oldVal, newVal)=>
|
||||
(obj as MultiBindingProxy).OnValueChanged(oldVal, newVal)));
|
||||
|
||||
internal MultiBindingProxy(MultiBinding multiBinding, bool isTarget)
|
||||
{
|
||||
this.MultiBinding = multiBinding;
|
||||
this.IsTarget = isTarget;
|
||||
}
|
||||
|
||||
public object Value
|
||||
{
|
||||
get
|
||||
{
|
||||
return GetValue(ValueProperty);
|
||||
}
|
||||
set
|
||||
{
|
||||
SetValue(ValueProperty, value);
|
||||
}
|
||||
}
|
||||
|
||||
internal MultiBinding MultiBinding { get; }
|
||||
|
||||
internal BindingMode RealizedMode { get; set; }
|
||||
|
||||
internal void SetValueSilent(BindableProperty property, object value)
|
||||
{
|
||||
bool suspended = this.SuspendValueChangeNotification;
|
||||
this.SuspendValueChangeNotification = true;
|
||||
try
|
||||
{
|
||||
SetValue(property, value);
|
||||
}
|
||||
finally
|
||||
{
|
||||
SuspendValueChangeNotification = suspended;
|
||||
}
|
||||
}
|
||||
|
||||
void OnValueChanged(object oldValue, object newValue)
|
||||
{
|
||||
if (this.IsTarget)
|
||||
// Updates to target value are handled by MultiBinding.Apply
|
||||
return;
|
||||
|
||||
if (!SuspendValueChangeNotification)
|
||||
this.MultiBinding.ApplyBindingProxyValues(this);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,9 +1,6 @@
|
|||
using System;
|
||||
using System.Linq;
|
||||
using System.Collections.Generic;
|
||||
using System.Collections.ObjectModel;
|
||||
using System.Globalization;
|
||||
|
||||
using Xamarin.Forms.Internals;
|
||||
|
||||
namespace Xamarin.Forms
|
||||
|
@ -13,12 +10,12 @@ namespace Xamarin.Forms
|
|||
{
|
||||
IMultiValueConverter _converter;
|
||||
object _converterParameter;
|
||||
BindingExpression _expression;
|
||||
IList<BindingBase> _bindings;
|
||||
BindableProperty _targetProperty;
|
||||
bool _isApplying;
|
||||
bool _isCreating;
|
||||
bool _hasSuccessfullyConverted;
|
||||
BindableObject _targetObject;
|
||||
BindableObject _proxyObject;
|
||||
BindableProperty[] _bpProxies;
|
||||
bool _applying;
|
||||
|
||||
public IMultiValueConverter Converter
|
||||
{
|
||||
|
@ -50,17 +47,16 @@ namespace Xamarin.Forms
|
|||
}
|
||||
}
|
||||
|
||||
internal List<MultiBindingProxy> SourceProxies { get; private set; }
|
||||
|
||||
internal MultiBindingProxy TargetProxy { get; private set; }
|
||||
|
||||
internal override BindingBase Clone()
|
||||
{
|
||||
return new MultiBinding()
|
||||
{
|
||||
var bindingsclone = new List<BindingBase>(Bindings.Count);
|
||||
foreach (var b in Bindings)
|
||||
bindingsclone.Add(b.Clone());
|
||||
|
||||
return new MultiBinding() {
|
||||
Converter = Converter,
|
||||
ConverterParameter = ConverterParameter,
|
||||
Bindings = new Collection<BindingBase>(this.Bindings),
|
||||
Bindings = bindingsclone,
|
||||
FallbackValue = FallbackValue,
|
||||
Mode = Mode,
|
||||
TargetNullValue = TargetNullValue,
|
||||
|
@ -70,238 +66,147 @@ namespace Xamarin.Forms
|
|||
|
||||
internal override void Apply(bool fromTarget)
|
||||
{
|
||||
VerifyConverterBeforeApply();
|
||||
|
||||
base.Apply(fromTarget);
|
||||
|
||||
if (_hasSuccessfullyConverted && this.GetRealizedMode(_targetProperty) == BindingMode.OneTime)
|
||||
if (_applying)
|
||||
return;
|
||||
|
||||
if (_expression == null)
|
||||
_expression = new BindingExpression(this, Binding.SelfPath);
|
||||
|
||||
if (fromTarget && _isApplying)
|
||||
base.Apply(fromTarget);
|
||||
|
||||
if (this.GetRealizedMode(_targetProperty) == BindingMode.OneTime)
|
||||
return;
|
||||
|
||||
_expression.Apply(fromTarget);
|
||||
ApplyBindingProxyValues(fromTarget ? TargetProxy : null, false);
|
||||
}
|
||||
if (fromTarget && this.GetRealizedMode(_targetProperty) == BindingMode.OneWay)
|
||||
return;
|
||||
|
||||
internal override void Apply(
|
||||
object context,
|
||||
BindableObject bindObj,
|
||||
BindableProperty targetProperty,
|
||||
bool fromBindingContextChanged = false)
|
||||
{
|
||||
VerifyConverterBeforeApply();
|
||||
|
||||
base.Apply(context, bindObj, targetProperty, fromBindingContextChanged);
|
||||
|
||||
if (IsApplied && fromBindingContextChanged)
|
||||
if (!fromTarget && this.GetRealizedMode(_targetProperty) == BindingMode.OneWayToSource)
|
||||
return;
|
||||
|
||||
if (!fromTarget)
|
||||
{
|
||||
bool childContextChanged = false;
|
||||
foreach (var proxy in SourceProxies)
|
||||
{
|
||||
if (!object.ReferenceEquals(proxy.BindingContext, context))
|
||||
var value = GetSourceValue(GetValueArray(), _targetProperty.ReturnType);
|
||||
if (value != Binding.DoNothing) {
|
||||
_applying = true;
|
||||
_targetObject.SetValueCore(_targetProperty, value, SetValueFlags.ClearDynamicResource, BindableObject.SetValuePrivateFlags.Default | BindableObject.SetValuePrivateFlags.Converted);
|
||||
_applying = false;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
try {
|
||||
_applying = true;
|
||||
|
||||
//https://docs.microsoft.com/en-us/dotnet/api/system.windows.data.imultivalueconverter.convertback?view=netframework-4.8#remarks
|
||||
if (!(GetTargetValue(_targetObject.GetValue(_targetProperty), null) is object[] values)) //converter failed
|
||||
return;
|
||||
for (var i = 0; i < Math.Min(_bpProxies.Length, values.Length); i++)
|
||||
{
|
||||
childContextChanged = true;
|
||||
proxy.SetValueSilent(Element.BindingContextProperty, context);
|
||||
if (ReferenceEquals(values[i], Binding.DoNothing) || ReferenceEquals(values[i], BindableProperty.UnsetValue))
|
||||
continue;
|
||||
_proxyObject.SetValueCore(_bpProxies[i], values[i], SetValueFlags.None);
|
||||
}
|
||||
}
|
||||
if ( childContextChanged )
|
||||
ApplyBindingProxyValues(null, true);
|
||||
finally {
|
||||
_applying = false;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
internal override void Apply(object context, BindableObject targetObject, BindableProperty targetProperty, bool fromBindingContextChanged = false)
|
||||
{
|
||||
if (_bindings == null)
|
||||
throw new InvalidOperationException("Bindings is null");
|
||||
|
||||
base.Apply(context, targetObject, targetProperty, fromBindingContextChanged);
|
||||
|
||||
if (!ReferenceEquals(_targetObject, targetObject)) {
|
||||
_targetObject = targetObject;
|
||||
_proxyObject = new ProxyElement() { Parent = targetObject as Element };
|
||||
_targetProperty = targetProperty;
|
||||
|
||||
if (_bpProxies == null) {
|
||||
_bpProxies = new BindableProperty[Bindings.Count];
|
||||
_applying = true;
|
||||
var bindingMode = Mode == BindingMode.Default ? targetProperty.DefaultBindingMode : Mode;
|
||||
for (var i = 0; i < Bindings.Count; i++) {
|
||||
var binding = Bindings[i];
|
||||
binding.RelativeSourceTargetOverride = targetObject as Element;
|
||||
var bp = _bpProxies[i] = BindableProperty.Create($"mb-proxy{i}", typeof(object), typeof(MultiBinding), null, bindingMode, propertyChanged: OnBindingChanged);
|
||||
_proxyObject.SetBinding(bp, binding);
|
||||
}
|
||||
_applying = false;
|
||||
}
|
||||
}
|
||||
_proxyObject.BindingContext = context;
|
||||
|
||||
if (this.GetRealizedMode(_targetProperty) == BindingMode.OneWayToSource)
|
||||
return;
|
||||
}
|
||||
|
||||
_targetProperty = targetProperty;
|
||||
|
||||
if (_expression == null)
|
||||
_expression = new BindingExpression(this, nameof(MultiBindingProxy.Value));
|
||||
|
||||
CreateBindingProxies(bindObj, context);
|
||||
var value = GetSourceValue(GetValueArray(), _targetProperty.ReturnType);
|
||||
if (value != Binding.DoNothing) {
|
||||
_applying = true;
|
||||
_targetObject.SetValueCore(_targetProperty, value, SetValueFlags.ClearDynamicResource, BindableObject.SetValuePrivateFlags.Default | BindableObject.SetValuePrivateFlags.Converted);
|
||||
_applying = false;
|
||||
}
|
||||
}
|
||||
|
||||
_isApplying = true;
|
||||
try
|
||||
{
|
||||
ApplyBindingProxyValues(TargetProxy, reapplyExpression: false, firstApplication: true);
|
||||
_expression.Apply(TargetProxy, bindObj, targetProperty);
|
||||
if (this.GetRealizedMode(_targetProperty) == BindingMode.OneWayToSource &&
|
||||
this.FallbackValue != null)
|
||||
bindObj.SetValue(targetProperty, this.FallbackValue);
|
||||
}
|
||||
finally
|
||||
{
|
||||
_isApplying = false;
|
||||
class ProxyElement : Element
|
||||
{
|
||||
}
|
||||
|
||||
object[] GetValueArray()
|
||||
{
|
||||
var valuearray = new object[_bpProxies.Length];
|
||||
for (var i = 0; i < _bpProxies.Length; i++)
|
||||
valuearray[i] = _proxyObject.GetValue(_bpProxies[i]);
|
||||
return valuearray;
|
||||
}
|
||||
|
||||
internal override object GetSourceValue(object value, Type targetPropertyType)
|
||||
{
|
||||
var valuearray = value as object[];
|
||||
if (valuearray != null && Converter != null)
|
||||
value = Converter.Convert(valuearray, targetPropertyType, ConverterParameter, CultureInfo.CurrentUICulture);
|
||||
|
||||
if (valuearray != null && StringFormat != null && TryFormat(StringFormat, valuearray, out var formatted))
|
||||
return formatted;
|
||||
|
||||
if (ReferenceEquals(BindableProperty.UnsetValue, value))
|
||||
return FallbackValue;
|
||||
|
||||
return base.GetSourceValue(value, targetPropertyType);
|
||||
}
|
||||
|
||||
internal override object GetTargetValue(object value, Type sourcePropertyType)
|
||||
{
|
||||
if (Converter != null) {
|
||||
var values = GetValueArray();
|
||||
var types = new Type[_bpProxies.Length];
|
||||
for (var i = 0; i < _bpProxies.Length; i++)
|
||||
types[i] = values[i]?.GetType() ?? typeof(object);
|
||||
return Converter.ConvertBack(value, types, ConverterParameter, CultureInfo.CurrentUICulture);
|
||||
}
|
||||
|
||||
return base.GetTargetValue(value, sourcePropertyType);
|
||||
}
|
||||
|
||||
void OnBindingChanged(BindableObject bindable, object oldValue, object newValue)
|
||||
{
|
||||
if (!_applying)
|
||||
Apply(fromTarget: false);
|
||||
}
|
||||
|
||||
internal override void Unapply(bool fromBindingContextChanged = false)
|
||||
{
|
||||
if (fromBindingContextChanged && IsApplied)
|
||||
return;
|
||||
if (!fromBindingContextChanged) {
|
||||
if (_bpProxies != null && _proxyObject != null)
|
||||
foreach (var proxybp in _bpProxies)
|
||||
_proxyObject.RemoveBinding(proxybp);
|
||||
|
||||
_bpProxies = null;
|
||||
_proxyObject = null;
|
||||
}
|
||||
|
||||
base.Unapply(fromBindingContextChanged: fromBindingContextChanged);
|
||||
|
||||
if (_expression != null)
|
||||
_expression.Unapply();
|
||||
|
||||
TargetProxy.RemoveBinding(MultiBindingProxy.ValueProperty);
|
||||
if (this.SourceProxies?.Count > 0)
|
||||
{
|
||||
foreach (var proxy in this.SourceProxies)
|
||||
proxy.RemoveBinding(MultiBindingProxy.ValueProperty);
|
||||
}
|
||||
|
||||
TargetProxy = null;
|
||||
SourceProxies = null;
|
||||
}
|
||||
|
||||
internal void ApplyBindingProxyValues(MultiBindingProxy trigger, bool reapplyExpression = true, bool firstApplication = false)
|
||||
{
|
||||
if (_isCreating)
|
||||
return;
|
||||
|
||||
BindingMode mode = this.GetRealizedMode(_targetProperty);
|
||||
bool convertBackFailed = false;
|
||||
if (trigger?.IsTarget == true &&
|
||||
!trigger.SuspendValueChangeNotification &&
|
||||
(!firstApplication || mode == BindingMode.OneWayToSource) &&
|
||||
(mode == BindingMode.TwoWay || mode == BindingMode.OneWayToSource))
|
||||
{
|
||||
// triggered because the target property was updated
|
||||
convertBackFailed = !ApplyTargetValueUpdate();
|
||||
}
|
||||
|
||||
if (mode != BindingMode.OneWayToSource &&
|
||||
!convertBackFailed &&
|
||||
(trigger?.IsTarget != true || !TargetProxy.SuspendValueChangeNotification))
|
||||
{
|
||||
object newTargetValue = BindableProperty.UnsetValue;
|
||||
if (this.Converter != null)
|
||||
{
|
||||
newTargetValue = this.Converter.Convert(
|
||||
SourceProxies.Select(p => p.Value).ToArray(),
|
||||
_targetProperty.ReturnType,
|
||||
this.ConverterParameter,
|
||||
CultureInfo.CurrentUICulture);
|
||||
if (newTargetValue == Binding.DoNothing)
|
||||
return;
|
||||
}
|
||||
|
||||
if (newTargetValue == BindableProperty.UnsetValue)
|
||||
newTargetValue = this.FallbackValue ?? _targetProperty.DefaultValue;
|
||||
else if (newTargetValue == null)
|
||||
newTargetValue = this.TargetNullValue ?? _targetProperty.DefaultValue;
|
||||
else
|
||||
_hasSuccessfullyConverted = true;
|
||||
|
||||
TargetProxy.SetValueSilent(MultiBindingProxy.ValueProperty, newTargetValue);
|
||||
}
|
||||
|
||||
if (reapplyExpression)
|
||||
{
|
||||
bool wasApplying = _isApplying;
|
||||
_isApplying = true;
|
||||
_expression.Apply();
|
||||
_isApplying = wasApplying;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
bool ApplyTargetValueUpdate()
|
||||
{
|
||||
var types = SourceProxies
|
||||
.Select(p => p.Value?.GetType() ?? _targetProperty.ReturnType)
|
||||
.ToArray();
|
||||
var convertedValues = this.Converter?.ConvertBack(
|
||||
TargetProxy.Value,
|
||||
types,
|
||||
this.ConverterParameter,
|
||||
CultureInfo.CurrentUICulture);
|
||||
|
||||
if (convertedValues == null || convertedValues.Any(val=>object.ReferenceEquals(val, BindableProperty.UnsetValue)))
|
||||
{
|
||||
// https://docs.microsoft.com/en-us/dotnet/api/system.windows.data.imultivalueconverter.convertback?view=netframework-4.8
|
||||
// Return null to indicate that the converter cannot perform the
|
||||
// conversion or that it does not support conversion in this direction.
|
||||
// Return DependencyProperty.UnsetValue at position i to indicate that
|
||||
// the converter is unable to provide a value for the source binding at
|
||||
// index i, and that no value is to be set on it.
|
||||
return false;
|
||||
}
|
||||
|
||||
int count = Math.Min(convertedValues.Length, this.SourceProxies.Count);
|
||||
for (int i = 0; i < count; i++)
|
||||
{
|
||||
// https://docs.microsoft.com/en-us/dotnet/api/system.windows.data.imultivalueconverter.convertback?view=netframework-4.8
|
||||
// Return DoNothing at position i to indicate that no value is to
|
||||
// be set on the source binding at index i.
|
||||
if (convertedValues[i] == Binding.DoNothing)
|
||||
continue;
|
||||
|
||||
var childMode = this.SourceProxies[i].RealizedMode;
|
||||
if (childMode != BindingMode.TwoWay && childMode != BindingMode.OneWayToSource)
|
||||
continue;
|
||||
this.SourceProxies[i].SetValueSilent(MultiBindingProxy.ValueProperty, convertedValues[i]);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void CreateBindingProxies(BindableObject target, object context)
|
||||
{
|
||||
_hasSuccessfullyConverted = false;
|
||||
_isCreating = true;
|
||||
try
|
||||
{
|
||||
TargetProxy = new MultiBindingProxy(this, true);
|
||||
SourceProxies = new List<MultiBindingProxy>();
|
||||
|
||||
if (this.Bindings.Count == 0)
|
||||
return;
|
||||
|
||||
var mode = this.GetRealizedMode(_targetProperty);
|
||||
|
||||
if (mode == BindingMode.OneWayToSource)
|
||||
TargetProxy.Value = this.FallbackValue;
|
||||
|
||||
foreach (var binding in _bindings)
|
||||
{
|
||||
var proxy = new MultiBindingProxy(this, false);
|
||||
proxy.BindingContext = context;
|
||||
|
||||
// Bind proxy's Value property using the source binding settings
|
||||
var proxyBinding = binding.Clone();
|
||||
|
||||
// Ensures that RelativeSource bindings resolve using the
|
||||
// MultiBinding's BindableObject target rather than the proxy.
|
||||
if (target is MultiBindingProxy)
|
||||
proxyBinding.RelativeSourceTargetOverride = this.RelativeSourceTargetOverride;
|
||||
else if (target is Element e)
|
||||
proxyBinding.RelativeSourceTargetOverride = e;
|
||||
|
||||
// OneWayToSource, OneTime, or OneWay mode on the MultiBinding effectively
|
||||
// override the childrens' modes
|
||||
if ( mode == BindingMode.OneWayToSource ||
|
||||
mode == BindingMode.OneTime ||
|
||||
mode == BindingMode.OneWay ||
|
||||
proxyBinding.Mode == BindingMode.Default)
|
||||
proxyBinding.Mode = mode;
|
||||
|
||||
proxy.SetBinding(MultiBindingProxy.ValueProperty, proxyBinding);
|
||||
proxy.RealizedMode = proxyBinding.Mode;
|
||||
SourceProxies.Add(proxy);
|
||||
}
|
||||
}
|
||||
finally
|
||||
{
|
||||
_isCreating = false;
|
||||
}
|
||||
}
|
||||
|
||||
void VerifyConverterBeforeApply()
|
||||
{
|
||||
if (this.Converter == null)
|
||||
throw new InvalidOperationException($"{nameof(MultiBinding)} requires {nameof(Converter)} be set.");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -9,5 +9,6 @@ namespace Xamarin.Forms
|
|||
|
||||
ReadOnlyCollection<ShellSection> GetItems();
|
||||
event NotifyCollectionChangedEventHandler ItemsCollectionChanged;
|
||||
bool ShowTabs { get; }
|
||||
}
|
||||
}
|
|
@ -146,9 +146,9 @@ namespace Xamarin.Forms
|
|||
BindableProperty.CreateAttached("UnselectedColor", typeof(Color), typeof(Shell), Color.Default,
|
||||
propertyChanged: OnColorValueChanged);
|
||||
|
||||
public static readonly BindableProperty FlyoutBackdropColorProperty =
|
||||
BindableProperty.CreateAttached("FlyoutBackdropColor", typeof(Color), typeof(Shell), Color.Default,
|
||||
propertyChanged: OnColorValueChanged);
|
||||
//public static readonly BindableProperty FlyoutBackdropColorProperty =
|
||||
// BindableProperty.CreateAttached("FlyoutBackdropColor", typeof(Color), typeof(Shell), Color.Default,
|
||||
// propertyChanged: OnColorValueChanged);
|
||||
|
||||
public static Color GetBackgroundColor(BindableObject obj) => (Color)obj.GetValue(BackgroundColorProperty);
|
||||
public static void SetBackgroundColor(BindableObject obj, Color value) => obj.SetValue(BackgroundColorProperty, value);
|
||||
|
@ -180,8 +180,8 @@ namespace Xamarin.Forms
|
|||
public static Color GetUnselectedColor(BindableObject obj) => (Color)obj.GetValue(UnselectedColorProperty);
|
||||
public static void SetUnselectedColor(BindableObject obj, Color value) => obj.SetValue(UnselectedColorProperty, value);
|
||||
|
||||
public static Color GetFlyoutBackdropColor(BindableObject obj) => (Color)obj.GetValue(FlyoutBackdropColorProperty);
|
||||
public static void SetFlyoutBackdropColor(BindableObject obj, Color value) => obj.SetValue(FlyoutBackdropColorProperty, value);
|
||||
//public static Color GetFlyoutBackdropColor(BindableObject obj) => (Color)obj.GetValue(FlyoutBackdropColorProperty);
|
||||
//public static void SetFlyoutBackdropColor(BindableObject obj, Color value) => obj.SetValue(FlyoutBackdropColorProperty, value);
|
||||
|
||||
static void OnColorValueChanged(BindableObject bindable, object oldValue, object newValue)
|
||||
{
|
||||
|
@ -843,11 +843,11 @@ namespace Xamarin.Forms
|
|||
set => SetValue(FlyoutBackgroundColorProperty, value);
|
||||
}
|
||||
|
||||
public Color FlyoutBackdropColor
|
||||
{
|
||||
get => (Color)GetValue(FlyoutBackdropColorProperty);
|
||||
set => SetValue(FlyoutBackdropColorProperty, value);
|
||||
}
|
||||
//public Color FlyoutBackdropColor
|
||||
//{
|
||||
// get => (Color)GetValue(FlyoutBackdropColorProperty);
|
||||
// set => SetValue(FlyoutBackdropColorProperty, value);
|
||||
//}
|
||||
|
||||
public FlyoutBehavior FlyoutBehavior
|
||||
{
|
||||
|
@ -1218,15 +1218,14 @@ namespace Xamarin.Forms
|
|||
(o) => rootItem = rootItem ?? o as ShellItem);
|
||||
}
|
||||
|
||||
T GetEffectiveValue<T>(BindableProperty property, T defaultValue)
|
||||
internal T GetEffectiveValue<T>(BindableProperty property, T defaultValue)
|
||||
{
|
||||
return GetEffectiveValue(property, () => defaultValue, null);
|
||||
return GetEffectiveValue<T>(property, () => defaultValue, null);
|
||||
}
|
||||
|
||||
T GetEffectiveValue<T>(BindableProperty property, Func<T> defaultValue, Action<Element> observer)
|
||||
{
|
||||
Element element = GetVisiblePage() ?? CurrentContent;
|
||||
|
||||
internal T GetEffectiveValue<T>(BindableProperty property, Func<T> defaultValue, Action<Element> observer, Element element = null)
|
||||
{
|
||||
element = element ?? GetVisiblePage() ?? CurrentContent;
|
||||
while (element != this && element != null)
|
||||
{
|
||||
observer?.Invoke(element);
|
||||
|
|
|
@ -18,7 +18,7 @@ namespace Xamarin.Forms
|
|||
Shell.TabBarUnselectedColorProperty,
|
||||
Shell.TitleColorProperty,
|
||||
Shell.UnselectedColorProperty,
|
||||
Shell.FlyoutBackdropColorProperty
|
||||
//Shell.FlyoutBackdropColorProperty
|
||||
};
|
||||
|
||||
Color?[] _colorArray = new Color?[s_ingestArray.Length];
|
||||
|
@ -43,7 +43,7 @@ namespace Xamarin.Forms
|
|||
|
||||
public Color UnselectedColor => _colorArray[9].Value;
|
||||
|
||||
public Color FlyoutBackdropColor => _colorArray[10].Value;
|
||||
//public Color FlyoutBackdropColor => _colorArray[10].Value;
|
||||
|
||||
Color IShellAppearanceElement.EffectiveTabBarBackgroundColor =>
|
||||
!TabBarBackgroundColor.IsDefault ? TabBarBackgroundColor : BackgroundColor;
|
||||
|
|
|
@ -93,6 +93,23 @@ namespace Xamarin.Forms
|
|||
remove { ((ShellSectionCollection)Items).VisibleItemsChanged -= value; }
|
||||
}
|
||||
|
||||
bool IShellItemController.ShowTabs
|
||||
{
|
||||
get
|
||||
{
|
||||
var displayedPage = CurrentItem?.DisplayedPage;
|
||||
if (displayedPage == null)
|
||||
return true;
|
||||
|
||||
Shell shell = Parent as Shell;
|
||||
if (shell == null)
|
||||
return true;
|
||||
|
||||
bool defaultShow = ShellItemController.GetItems().Count > 1;
|
||||
return shell.GetEffectiveValue<bool>(Shell.TabBarIsVisibleProperty, () => defaultShow, null, displayedPage);
|
||||
}
|
||||
}
|
||||
|
||||
#endregion IShellItemController
|
||||
|
||||
#region IPropertyPropagationController
|
||||
|
|
|
@ -277,7 +277,7 @@ namespace Xamarin.Forms
|
|||
|
||||
internal override ReadOnlyCollection<Element> LogicalChildrenInternal => _logicalChildrenReadOnly ?? (_logicalChildrenReadOnly = new ReadOnlyCollection<Element>(_logicalChildren));
|
||||
|
||||
Page DisplayedPage
|
||||
internal Page DisplayedPage
|
||||
{
|
||||
get { return _displayedPage; }
|
||||
set
|
||||
|
|
|
@ -59,9 +59,9 @@
|
|||
</ProjectReference>
|
||||
</ItemGroup>
|
||||
<ItemGroup Condition="'$(TargetFramework)' == 'MonoAndroid10.0'">
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0" />
|
||||
<PackageReference Include="Xamarin.Google.Android.Material" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Legacy.Support.V4" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0.1" />
|
||||
<PackageReference Include="Xamarin.Google.Android.Material" Version="1.0.0.1" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Legacy.Support.V4" Version="1.0.0.1" />
|
||||
</ItemGroup>
|
||||
<ItemGroup Condition="'$(TargetFramework)' == 'MonoAndroid90'">
|
||||
<PackageReference Include="Xamarin.Android.Support.Design" Version="28.0.0.3" />
|
||||
|
|
|
@ -24,11 +24,11 @@
|
|||
</ProjectReference>
|
||||
</ItemGroup>
|
||||
<ItemGroup Condition="'$(TargetFramework)' == 'MonoAndroid10.0'">
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0" />
|
||||
<PackageReference Include="Xamarin.Google.Android.Material" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Legacy.Support.V4" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0.1" />
|
||||
<PackageReference Include="Xamarin.Google.Android.Material" Version="1.0.0.1" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Legacy.Support.V4" Version="1.0.0.1" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Migration">
|
||||
<Version>1.0.0</Version>
|
||||
<Version>1.0.0.1</Version>
|
||||
</PackageReference>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
|
|
|
@ -19,8 +19,8 @@
|
|||
<AndroidResource Include="Resources\**\*" />
|
||||
</ItemGroup>
|
||||
<ItemGroup Condition="'$(TargetFramework)' == 'MonoAndroid10.0'">
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0" />
|
||||
<PackageReference Include="Xamarin.Google.Android.Material" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0.1" />
|
||||
<PackageReference Include="Xamarin.Google.Android.Material" Version="1.0.0.1" />
|
||||
</ItemGroup>
|
||||
<ItemGroup Condition="'$(TargetFramework)' == 'MonoAndroid90'">
|
||||
<PackageReference Include="Xamarin.Android.Support.v7.AppCompat" Version="28.0.0.3" />
|
||||
|
|
|
@ -30,10 +30,10 @@
|
|||
</ProjectReference>
|
||||
</ItemGroup>
|
||||
<ItemGroup Condition="'$(TargetFramework)' == 'MonoAndroid10.0'">
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Legacy.Support.V4" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0.1" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Legacy.Support.V4" Version="1.0.0.1" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Migration">
|
||||
<Version>1.0.0</Version>
|
||||
<Version>1.0.0.1</Version>
|
||||
</PackageReference>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
|
|
|
@ -22,10 +22,10 @@ namespace Xamarin.Forms.Platform.Android
|
|||
|
||||
void IAppearanceObserver.OnAppearanceChanged(ShellAppearance appearance)
|
||||
{
|
||||
if (appearance == null)
|
||||
//if (appearance == null)
|
||||
UpdateScrimColor(Color.Default);
|
||||
else
|
||||
UpdateScrimColor(appearance.FlyoutBackdropColor);
|
||||
//else
|
||||
// UpdateScrimColor(appearance.FlyoutBackdropColor);
|
||||
}
|
||||
|
||||
#endregion IAppearanceObserver
|
||||
|
|
|
@ -56,6 +56,7 @@ namespace Xamarin.Forms.Platform.Android
|
|||
BottomNavigationViewTracker _bottomNavigationTracker;
|
||||
BottomSheetDialog _bottomSheetDialog;
|
||||
bool _disposed;
|
||||
public IShellItemController ShellItemController => ShellItem;
|
||||
|
||||
public ShellItemRenderer(IShellContext shellContext) : base(shellContext)
|
||||
{
|
||||
|
@ -418,7 +419,7 @@ namespace Xamarin.Forms.Platform.Android
|
|||
if (DisplayedPage == null)
|
||||
return;
|
||||
|
||||
bool visible = Shell.GetTabBarIsVisible(DisplayedPage);
|
||||
bool visible = ShellItemController.ShowTabs;
|
||||
using (var menu = _bottomView.Menu)
|
||||
{
|
||||
if (menu.Size() == 1)
|
||||
|
|
|
@ -55,9 +55,9 @@
|
|||
<Reference Include="System.Net.Http" />
|
||||
</ItemGroup>
|
||||
<ItemGroup Condition="'$(TargetFramework)' == 'MonoAndroid10.0'">
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0" />
|
||||
<PackageReference Include="Xamarin.Google.Android.Material" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Legacy.Support.V4" Version="1.0.0" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Lifecycle.LiveData" Version="2.1.0.1" />
|
||||
<PackageReference Include="Xamarin.Google.Android.Material" Version="1.0.0.1" />
|
||||
<PackageReference Include="Xamarin.AndroidX.Legacy.Support.V4" Version="1.0.0.1" />
|
||||
</ItemGroup>
|
||||
<ItemGroup Condition="'$(TargetFramework)' == 'MonoAndroid90'">
|
||||
<PackageReference Include="Xamarin.Android.Support.Design" Version="28.0.0.3" />
|
||||
|
|
|
@ -34,6 +34,7 @@ namespace Xamarin.Forms.Platform.UWP
|
|||
internal ShellRenderer ShellContext { get; set; }
|
||||
|
||||
IShellItemController ShellItemController => ShellItem;
|
||||
IShellController ShellController => ShellContext?.Shell;
|
||||
|
||||
public ShellItemRenderer(ShellRenderer shellContext)
|
||||
{
|
||||
|
@ -241,6 +242,7 @@ namespace Xamarin.Forms.Platform.UWP
|
|||
{
|
||||
shellItem.PropertyChanged += OnShellItemPropertyChanged;
|
||||
ShellItemController.ItemsCollectionChanged += OnShellItemsChanged;
|
||||
ShellController.StructureChanged += OnShellStructureChanged;
|
||||
foreach (var shellSection in ShellItemController.GetItems())
|
||||
{
|
||||
HookChildEvents(shellSection);
|
||||
|
@ -255,6 +257,8 @@ namespace Xamarin.Forms.Platform.UWP
|
|||
{
|
||||
UnhookChildEvents(shellSection);
|
||||
}
|
||||
|
||||
ShellController.StructureChanged -= OnShellStructureChanged;
|
||||
ShellItemController.ItemsCollectionChanged -= OnShellItemsChanged;
|
||||
ShellItem.PropertyChanged -= OnShellItemPropertyChanged;
|
||||
ShellSection = null;
|
||||
|
@ -299,6 +303,11 @@ namespace Xamarin.Forms.Platform.UWP
|
|||
SwitchSection(ShellNavigationSource.ShellSectionChanged, newSection, null, oldSection != null);
|
||||
}
|
||||
|
||||
void OnShellStructureChanged(object sender, EventArgs e)
|
||||
{
|
||||
UpdateBottomBarVisibility();
|
||||
}
|
||||
|
||||
void SwitchSection(ShellNavigationSource source, ShellSection section, Page page, bool animate = true)
|
||||
{
|
||||
if (section == null)
|
||||
|
@ -365,7 +374,8 @@ namespace Xamarin.Forms.Platform.UWP
|
|||
|
||||
void UpdateBottomBarVisibility()
|
||||
{
|
||||
_BottomBar.Visibility = DisplayedPage == null || Shell.GetTabBarIsVisible(DisplayedPage) ? Visibility.Visible : Visibility.Collapsed;
|
||||
bool isVisible = ShellItemController?.ShowTabs ?? false;
|
||||
_BottomBar.Visibility = isVisible ? Visibility.Visible : Visibility.Collapsed;
|
||||
}
|
||||
|
||||
void UpdateToolbar()
|
||||
|
|
|
@ -171,10 +171,10 @@ namespace Xamarin.Forms.Platform.UWP
|
|||
{
|
||||
UpdateFlyoutBackgroundColor();
|
||||
}
|
||||
else if (e.PropertyName == Shell.FlyoutBackdropColorProperty.PropertyName)
|
||||
{
|
||||
UpdateFlyoutBackdropColor();
|
||||
}
|
||||
//else if (e.PropertyName == Shell.FlyoutBackdropColorProperty.PropertyName)
|
||||
//{
|
||||
// UpdateFlyoutBackdropColor();
|
||||
//}
|
||||
}
|
||||
|
||||
protected virtual void UpdateFlyoutBackdropColor()
|
||||
|
@ -182,7 +182,7 @@ namespace Xamarin.Forms.Platform.UWP
|
|||
var splitView = ShellSplitView;
|
||||
if (splitView != null)
|
||||
{
|
||||
splitView.FlyoutBackdropColor = _shell.FlyoutBackdropColor;
|
||||
//splitView.FlyoutBackdropColor = _shell.FlyoutBackdropColor;
|
||||
if (IsPaneOpen)
|
||||
ShellSplitView.UpdateFlyoutBackdropColor();
|
||||
}
|
||||
|
|
|
@ -79,12 +79,7 @@ namespace Xamarin.Forms.Platform.iOS
|
|||
if (Element.BackgroundColor == Color.Default)
|
||||
_actualView.Layer.BackgroundColor = ColorExtensions.BackgroundColor.CGColor;
|
||||
else
|
||||
{
|
||||
// BackgroundColor gets set on the base class too which messes with
|
||||
// the corner radius, shadow, etc. so override that behaviour here
|
||||
BackgroundColor = null;
|
||||
_actualView.Layer.BackgroundColor = Element.BackgroundColor.ToCGColor();
|
||||
}
|
||||
|
||||
if (Element.BorderColor == Color.Default)
|
||||
_actualView.Layer.BorderColor = UIColor.Clear.CGColor;
|
||||
|
|
|
@ -14,10 +14,10 @@ namespace Xamarin.Forms.Platform.iOS
|
|||
|
||||
void IAppearanceObserver.OnAppearanceChanged(ShellAppearance appearance)
|
||||
{
|
||||
if (appearance == null)
|
||||
//if (appearance == null)
|
||||
_backdropColor = Color.Default;
|
||||
else
|
||||
_backdropColor = appearance.FlyoutBackdropColor;
|
||||
//else
|
||||
// _backdropColor = appearance.FlyoutBackdropColor;
|
||||
|
||||
UpdateTapoffViewBackgroundColor();
|
||||
}
|
||||
|
|
|
@ -206,7 +206,7 @@ namespace Xamarin.Forms.Platform.iOS
|
|||
GoTo(ShellItem.CurrentItem);
|
||||
}
|
||||
|
||||
SetTabBarHidden(ViewControllers.Length == 1);
|
||||
UpdateTabBarHidden();
|
||||
}
|
||||
|
||||
protected virtual void OnShellItemSet(ShellItem shellItem)
|
||||
|
@ -271,9 +271,7 @@ namespace Xamarin.Forms.Platform.iOS
|
|||
ViewControllers = viewControllers;
|
||||
CustomizableViewControllers = Array.Empty<UIViewController>();
|
||||
|
||||
// No sense showing a bar that has a single icon
|
||||
if (ViewControllers.Length == 1)
|
||||
SetTabBarHidden(true);
|
||||
UpdateTabBarHidden();
|
||||
|
||||
// Make sure we are at the right item
|
||||
GoTo(ShellItem.CurrentItem);
|
||||
|
@ -370,21 +368,12 @@ namespace Xamarin.Forms.Platform.iOS
|
|||
return null;
|
||||
}
|
||||
|
||||
void SetTabBarHidden(bool hidden)
|
||||
{
|
||||
TabBar.Hidden = hidden;
|
||||
}
|
||||
|
||||
void UpdateTabBarHidden()
|
||||
{
|
||||
if (_displayedPage == null || ShellItem == null)
|
||||
if (ShellItemController == null)
|
||||
return;
|
||||
|
||||
var hidden = !Shell.GetTabBarIsVisible(_displayedPage);
|
||||
if (ShellItemController.GetItems().Count > 1)
|
||||
{
|
||||
SetTabBarHidden(hidden);
|
||||
}
|
||||
TabBar.Hidden = !ShellItemController.ShowTabs;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -661,6 +661,7 @@ Global
|
|||
{C7131F14-274F-4B55-ACA9-E81731AD012F}.Debug|ARM64.ActiveCfg = Debug|iPhone
|
||||
{C7131F14-274F-4B55-ACA9-E81731AD012F}.Debug|iPhone.ActiveCfg = Debug|iPhone
|
||||
{C7131F14-274F-4B55-ACA9-E81731AD012F}.Debug|iPhone.Build.0 = Debug|iPhone
|
||||
{C7131F14-274F-4B55-ACA9-E81731AD012F}.Debug|iPhone.Deploy.0 = Debug|iPhone
|
||||
{C7131F14-274F-4B55-ACA9-E81731AD012F}.Debug|iPhoneSimulator.ActiveCfg = Debug|iPhoneSimulator
|
||||
{C7131F14-274F-4B55-ACA9-E81731AD012F}.Debug|iPhoneSimulator.Build.0 = Debug|iPhoneSimulator
|
||||
{C7131F14-274F-4B55-ACA9-E81731AD012F}.Debug|x64.ActiveCfg = Debug|iPhoneSimulator
|
||||
|
|
103
build.cake
103
build.cake
|
@ -43,10 +43,10 @@ var releaseChannelArg = Argument("CHANNEL", "Stable");
|
|||
releaseChannelArg = EnvironmentVariable("CHANNEL") ?? releaseChannelArg;
|
||||
var teamProject = Argument("TeamProject", "");
|
||||
bool buildForVS2017 = Convert.ToBoolean(Argument("buildForVS2017", "false"));
|
||||
string agentName = EnvironmentVariable("Agent_Name", "");
|
||||
string agentName = EnvironmentVariable("AGENT_NAME", "");
|
||||
bool isHostedAgent = agentName.StartsWith("Azure Pipelines");
|
||||
bool isCIBuild = !String.IsNullOrWhiteSpace(agentName);
|
||||
string artifactStagingDirectory = Argument("Build_ArtifactStagingDirectory", (string)null) ?? EnvironmentVariable("Build.ArtifactStagingDirectory") ?? EnvironmentVariable("Build_ArtifactStagingDirectory") ?? ".";
|
||||
string artifactStagingDirectory = EnvironmentVariable("BUILD_ARTIFACTSTAGINGDIRECTORY", ".");
|
||||
var ANDROID_HOME = EnvironmentVariable("ANDROID_HOME") ??
|
||||
(IsRunningOnWindows () ? "C:\\Program Files (x86)\\Android\\android-sdk\\" : "");
|
||||
|
||||
|
@ -89,9 +89,9 @@ Information ("configuration: {0}", configuration);
|
|||
Information ("ANDROID_HOME: {0}", ANDROID_HOME);
|
||||
Information ("Team Project: {0}", teamProject);
|
||||
Information ("buildForVS2017: {0}", buildForVS2017);
|
||||
Information ("Agent.Name: {0}", EnvironmentVariable("Agent_Name"));
|
||||
Information ("Agent.Name: {0}", agentName);
|
||||
Information ("isCIBuild: {0}", isCIBuild);
|
||||
|
||||
Information ("artifactStagingDirectory: {0}", artifactStagingDirectory);
|
||||
|
||||
var releaseChannel = ReleaseChannel.Stable;
|
||||
if(releaseChannelArg == "Preview")
|
||||
|
@ -488,6 +488,19 @@ Task("Restore")
|
|||
}
|
||||
});
|
||||
|
||||
Task("WriteGoogleMapsAPIKey")
|
||||
.Description("Write GoogleMapsAPIKey to Android Control Gallery")
|
||||
.Does(() =>
|
||||
{
|
||||
string GoogleMapsAPIKey = Argument("GoogleMapsAPIKey", "");
|
||||
|
||||
if(!String.IsNullOrWhiteSpace(GoogleMapsAPIKey))
|
||||
{
|
||||
Information("Writing GoogleMapsAPIKey");
|
||||
System.IO.File.WriteAllText("Xamarin.Forms.ControlGallery.Android/Properties/MapsKey.cs", "[assembly: Android.App.MetaData(\"com.google.android.maps.v2.API_KEY\", Value = \"" + GoogleMapsAPIKey + "\")]");
|
||||
}
|
||||
});
|
||||
|
||||
Task("BuildForNuget")
|
||||
.Description("Builds all necessary projects to create Nuget Packages")
|
||||
.Does(() =>
|
||||
|
@ -500,7 +513,6 @@ Task("BuildForNuget")
|
|||
};
|
||||
|
||||
msbuildSettings.BinaryLogger = binaryLogger;
|
||||
msbuildSettings.ArgumentCustomization = args => args.Append("/nowarn:VSX1000");
|
||||
binaryLogger.FileName = $"{artifactStagingDirectory}/win-{configuration}.binlog";
|
||||
|
||||
MSBuild("./Xamarin.Forms.sln", msbuildSettings);
|
||||
|
@ -586,6 +598,56 @@ Task("VSMAC")
|
|||
StartProcess("open", new ProcessSettings{ Arguments = "Xamarin.Forms.sln" });
|
||||
});
|
||||
|
||||
Task("cg-android")
|
||||
.Description("Builds Android Control Gallery")
|
||||
.IsDependentOn("WriteGoogleMapsAPIKey")
|
||||
.IsDependentOn("BuildTasks")
|
||||
.Does(() =>
|
||||
{
|
||||
var buildSettings = GetMSBuildSettings();
|
||||
|
||||
if(isCIBuild)
|
||||
{
|
||||
buildSettings = buildSettings.WithTarget("Rebuild").WithTarget("SignAndroidPackage");
|
||||
var binaryLogger = new MSBuildBinaryLogSettings {
|
||||
Enabled = true
|
||||
};
|
||||
|
||||
buildSettings.BinaryLogger = binaryLogger;
|
||||
binaryLogger.FileName = $"{artifactStagingDirectory}/android-{ANDROID_RENDERERS}.binlog";
|
||||
}
|
||||
else
|
||||
{
|
||||
buildSettings = buildSettings.WithRestore();
|
||||
}
|
||||
|
||||
MSBuild("./Xamarin.Forms.ControlGallery.Android/Xamarin.Forms.ControlGallery.Android.csproj", buildSettings);
|
||||
});
|
||||
|
||||
Task("cg-android-vs")
|
||||
.Description("Builds Android Control Gallery and open VS")
|
||||
.IsDependentOn("cg-android")
|
||||
.Does(() =>
|
||||
{
|
||||
StartVisualStudio();
|
||||
});
|
||||
|
||||
Task("cg-ios")
|
||||
.Description("Builds iOS Control Gallery and open VS")
|
||||
.IsDependentOn("BuildTasks")
|
||||
.Does(() =>
|
||||
{
|
||||
MSBuild("./Xamarin.Forms.ControlGallery.iOS/Xamarin.Forms.ControlGallery.iOS.csproj", GetMSBuildSettings().WithRestore());
|
||||
});
|
||||
|
||||
Task("cg-ios-vs")
|
||||
.Description("Builds iOS Control Gallery and open VS")
|
||||
.IsDependentOn("cg-ios")
|
||||
.Does(() =>
|
||||
{
|
||||
StartVisualStudio();
|
||||
});
|
||||
|
||||
/*
|
||||
Task("Deploy")
|
||||
.IsDependentOn("DeployiOS")
|
||||
|
@ -613,6 +675,27 @@ Task("DeployAndroid")
|
|||
AmStartActivity("AndroidControlGallery.AndroidControlGallery/md546303760447087909496d02dc7b17ae8.Activity1");
|
||||
});
|
||||
|
||||
Task("_PrintEnvironmentVariables")
|
||||
.Does(() =>
|
||||
{
|
||||
var envVars = EnvironmentVariables();
|
||||
|
||||
string path;
|
||||
if (envVars.TryGetValue("PATH", out path))
|
||||
{
|
||||
Information("Path: {0}", path);
|
||||
}
|
||||
|
||||
foreach(var envVar in envVars)
|
||||
{
|
||||
Information(
|
||||
"Key: {0}\tValue: \"{1}\"",
|
||||
envVar.Key,
|
||||
envVar.Value
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
// TASK TARGETS
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
|
@ -627,6 +710,16 @@ Task("Default")
|
|||
|
||||
RunTarget(target);
|
||||
|
||||
void StartVisualStudio(string sln = "Xamarin.Forms.sln")
|
||||
{
|
||||
if(isCIBuild)
|
||||
return;
|
||||
|
||||
if(IsRunningOnWindows())
|
||||
StartProcess("start", new ProcessSettings{ Arguments = "Xamarin.Forms.sln" });
|
||||
else
|
||||
StartProcess("open", new ProcessSettings{ Arguments = "Xamarin.Forms.sln" });
|
||||
}
|
||||
|
||||
MSBuildSettings GetMSBuildSettings()
|
||||
{
|
||||
|
|
|
@ -94,18 +94,12 @@ jobs:
|
|||
feedsToUse: config
|
||||
nugetConfigPath: 'DevopsNuget.config'
|
||||
|
||||
- task: MSBuild@1
|
||||
displayName: 'Build ${{ parameters.buildTaskPath }}'
|
||||
inputs:
|
||||
solution: ${{ parameters.buildTaskPath }}
|
||||
configuration: ${{ parameters.buildConfiguration }}
|
||||
|
||||
- task: MSBuild@1
|
||||
- task: Bash@3
|
||||
displayName: 'Build Android $(renderers)'
|
||||
inputs:
|
||||
solution: ${{ parameters.androidProjectPath }}
|
||||
configuration: ${{ parameters.buildConfiguration }}
|
||||
msbuildArguments: '/t:"Rebuild;SignAndroidPackage" /p:ANDROID_RENDERERS="$(renderers)" /bl:$(Build.ArtifactStagingDirectory)/android-$(renderers)-2017_$(buildForVS2017).binlog'
|
||||
targetType: 'filePath'
|
||||
filePath: 'build.sh'
|
||||
arguments: --target cg-android --ANDROID_RENDERERS="$(renderers)" --GoogleMapsAPIKey="$(GoogleMapsAPIKey)"
|
||||
|
||||
- task: CopyFiles@2
|
||||
displayName: 'Copy $(renderers)'
|
||||
|
|
Загрузка…
Ссылка в новой задаче