basic logic
@ -24,6 +24,7 @@
|
|||||||
<Compile Include="$(MSBuildThisFileDirectory)Models\BaseModel.cs" />
|
<Compile Include="$(MSBuildThisFileDirectory)Models\BaseModel.cs" />
|
||||||
<Compile Include="$(MSBuildThisFileDirectory)Models\Billing.cs" />
|
<Compile Include="$(MSBuildThisFileDirectory)Models\Billing.cs" />
|
||||||
<Compile Include="$(MSBuildThisFileDirectory)Models\Category.cs" />
|
<Compile Include="$(MSBuildThisFileDirectory)Models\Category.cs" />
|
||||||
|
<Compile Include="$(MSBuildThisFileDirectory)Models\Account.cs" />
|
||||||
<Compile Include="$(MSBuildThisFileDirectory)Themes\BaseTheme.cs" />
|
<Compile Include="$(MSBuildThisFileDirectory)Themes\BaseTheme.cs" />
|
||||||
<Compile Include="$(MSBuildThisFileDirectory)Themes\Dark.cs" />
|
<Compile Include="$(MSBuildThisFileDirectory)Themes\Dark.cs" />
|
||||||
<Compile Include="$(MSBuildThisFileDirectory)Themes\Light.cs" />
|
<Compile Include="$(MSBuildThisFileDirectory)Themes\Light.cs" />
|
||||||
@ -33,10 +34,15 @@
|
|||||||
<Compile Include="$(MSBuildThisFileDirectory)UI\BillingPage.cs" />
|
<Compile Include="$(MSBuildThisFileDirectory)UI\BillingPage.cs" />
|
||||||
<Compile Include="$(MSBuildThisFileDirectory)UI\Converters.cs" />
|
<Compile Include="$(MSBuildThisFileDirectory)UI\Converters.cs" />
|
||||||
<Compile Include="$(MSBuildThisFileDirectory)UI\CustomControl.cs" />
|
<Compile Include="$(MSBuildThisFileDirectory)UI\CustomControl.cs" />
|
||||||
|
<Compile Include="$(MSBuildThisFileDirectory)UI\CustomEffect.cs" />
|
||||||
<Compile Include="$(MSBuildThisFileDirectory)UI\Definition.cs" />
|
<Compile Include="$(MSBuildThisFileDirectory)UI\Definition.cs" />
|
||||||
<Compile Include="$(MSBuildThisFileDirectory)Views\AccountPage.xaml.cs">
|
<Compile Include="$(MSBuildThisFileDirectory)Views\AccountPage.xaml.cs">
|
||||||
<DependentUpon>AccountPage.xaml</DependentUpon>
|
<DependentUpon>AccountPage.xaml</DependentUpon>
|
||||||
</Compile>
|
</Compile>
|
||||||
|
<Compile Include="$(MSBuildThisFileDirectory)Views\AddAccountPage.xaml.cs">
|
||||||
|
<DependentUpon>AddAccountPage.xaml</DependentUpon>
|
||||||
|
<SubType>Code</SubType>
|
||||||
|
</Compile>
|
||||||
<Compile Include="$(MSBuildThisFileDirectory)Views\AddBillPage.xaml.cs">
|
<Compile Include="$(MSBuildThisFileDirectory)Views\AddBillPage.xaml.cs">
|
||||||
<DependentUpon>AddBillPage.xaml</DependentUpon>
|
<DependentUpon>AddBillPage.xaml</DependentUpon>
|
||||||
</Compile>
|
</Compile>
|
||||||
@ -73,4 +79,9 @@
|
|||||||
<Generator>MSBuild:UpdateDesignTimeXaml</Generator>
|
<Generator>MSBuild:UpdateDesignTimeXaml</Generator>
|
||||||
</EmbeddedResource>
|
</EmbeddedResource>
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<EmbeddedResource Include="$(MSBuildThisFileDirectory)Views\AddAccountPage.xaml">
|
||||||
|
<Generator>MSBuild:UpdateDesignTimeXaml</Generator>
|
||||||
|
</EmbeddedResource>
|
||||||
|
</ItemGroup>
|
||||||
</Project>
|
</Project>
|
@ -11,6 +11,20 @@
|
|||||||
<Friday>Fr</Friday>
|
<Friday>Fr</Friday>
|
||||||
<Saturday>Sa</Saturday>
|
<Saturday>Sa</Saturday>
|
||||||
<NoRecords>Bills not yet generated</NoRecords>
|
<NoRecords>Bills not yet generated</NoRecords>
|
||||||
<Memo>Click here to record</Memo>
|
<TapToMemo>Click here to record</TapToMemo>
|
||||||
<TitleDateFormat>MM/dd/yyyy</TitleDateFormat>
|
<TitleDateFormat>MM/dd/yyyy</TitleDateFormat>
|
||||||
|
<Balance>Balance</Balance>
|
||||||
|
<Assets>Assets</Assets>
|
||||||
|
<Liability>Liability</Liability>
|
||||||
|
<AddAccount>Add Account</AddAccount>
|
||||||
|
<AccountName>Account Name</AccountName>
|
||||||
|
<AccountNamePlaceholder>Please enter account name</AccountNamePlaceholder>
|
||||||
|
<Icon>Icon</Icon>
|
||||||
|
<Category>Category</Category>
|
||||||
|
<Balance>Balance</Balance>
|
||||||
|
<BalancePlaceholder>Please enter the balance</BalancePlaceholder>
|
||||||
|
<Currency>Currency</Currency>
|
||||||
|
<CNY>Chinese Yuan (CNY)</CNY>
|
||||||
|
<Memo>Note</Memo>
|
||||||
|
<MemoPlaceholder>Please enter a note</MemoPlaceholder>
|
||||||
</root>
|
</root>
|
@ -11,6 +11,20 @@
|
|||||||
<Friday>周五</Friday>
|
<Friday>周五</Friday>
|
||||||
<Saturday>周六</Saturday>
|
<Saturday>周六</Saturday>
|
||||||
<NoRecords>还未产生账单</NoRecords>
|
<NoRecords>还未产生账单</NoRecords>
|
||||||
<Memo>点此记录</Memo>
|
<TapToMemo>点此记录</TapToMemo>
|
||||||
<TitleDateFormat>yyyy年MM月dd日</TitleDateFormat>
|
<TitleDateFormat>yyyy年MM月dd日</TitleDateFormat>
|
||||||
|
<Balance>余额</Balance>
|
||||||
|
<Assets>资产</Assets>
|
||||||
|
<Liability>负债</Liability>
|
||||||
|
<AddAccount>新建账户</AddAccount>
|
||||||
|
<AccountName>账户名称</AccountName>
|
||||||
|
<AccountNamePlaceholder>请输入账户名称</AccountNamePlaceholder>
|
||||||
|
<Icon>图标</Icon>
|
||||||
|
<Category>种类</Category>
|
||||||
|
<Balance>余额</Balance>
|
||||||
|
<BalancePlaceholder>请输入余额</BalancePlaceholder>
|
||||||
|
<Currency>币种</Currency>
|
||||||
|
<CNY>人民币 (CNY)</CNY>
|
||||||
|
<Memo>备注</Memo>
|
||||||
|
<MemoPlaceholder>请输入备注</MemoPlaceholder>
|
||||||
</root>
|
</root>
|
41
Billing.Shared/Models/Account.cs
Normal file
@ -0,0 +1,41 @@
|
|||||||
|
using System.Xml.Linq;
|
||||||
|
|
||||||
|
namespace Billing.Models;
|
||||||
|
|
||||||
|
public class Account : BaseModel
|
||||||
|
{
|
||||||
|
public int Id { get; set; }
|
||||||
|
public string Icon { get; set; } = ICON_DEFAULT;
|
||||||
|
public AccountCategory Category { get; set; }
|
||||||
|
public string Name { get; set; }
|
||||||
|
public decimal Balance { get; set; }
|
||||||
|
public string Memo { get; set; }
|
||||||
|
|
||||||
|
public override void OnXmlDeserialize(XElement node)
|
||||||
|
{
|
||||||
|
Id = Read(node, nameof(Id), 0);
|
||||||
|
Icon = Read(node, nameof(Icon), ICON_DEFAULT);
|
||||||
|
Category = (AccountCategory)Read(node, nameof(Category), 0);
|
||||||
|
Name = Read(node, nameof(Name), string.Empty);
|
||||||
|
Balance = Read(node, nameof(Balance), 0m);
|
||||||
|
Memo = Read(node, nameof(Memo), null);
|
||||||
|
}
|
||||||
|
|
||||||
|
public override void OnXmlSerialize(XElement node)
|
||||||
|
{
|
||||||
|
Write(node, nameof(Id), Id);
|
||||||
|
Write(node, nameof(Icon), Icon);
|
||||||
|
Write(node, nameof(Category), (int)Category);
|
||||||
|
Write(node, nameof(Name), Name);
|
||||||
|
Write(node, nameof(Balance), Balance);
|
||||||
|
Write(node, nameof(Memo), Memo);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public enum AccountCategory
|
||||||
|
{
|
||||||
|
Cash = 0,
|
||||||
|
CreditCard,
|
||||||
|
DebitCard,
|
||||||
|
ElecAccount
|
||||||
|
}
|
@ -16,6 +16,8 @@ public interface IModel
|
|||||||
|
|
||||||
public abstract class BaseModel : IModel, IDisposable
|
public abstract class BaseModel : IModel, IDisposable
|
||||||
{
|
{
|
||||||
|
protected const string ICON_DEFAULT = "ic_default";
|
||||||
|
|
||||||
private bool disposed = false;
|
private bool disposed = false;
|
||||||
|
|
||||||
public static T ParseXml<T>(string xml) where T : BaseModel, new()
|
public static T ParseXml<T>(string xml) where T : BaseModel, new()
|
||||||
|
@ -8,6 +8,7 @@ public class Billing : BaseModel
|
|||||||
public decimal Amount { get; set; }
|
public decimal Amount { get; set; }
|
||||||
public string Name { get; set; }
|
public string Name { get; set; }
|
||||||
public int CategoryId { get; set; }
|
public int CategoryId { get; set; }
|
||||||
|
public int WalletId { get; set; }
|
||||||
public string Store { get; set; }
|
public string Store { get; set; }
|
||||||
public DateTime CreateTime { get; set; }
|
public DateTime CreateTime { get; set; }
|
||||||
|
|
||||||
@ -16,6 +17,7 @@ public class Billing : BaseModel
|
|||||||
Amount = Read(node, nameof(Amount), 0m);
|
Amount = Read(node, nameof(Amount), 0m);
|
||||||
Name = Read(node, nameof(Name), string.Empty);
|
Name = Read(node, nameof(Name), string.Empty);
|
||||||
CategoryId = Read(node, nameof(CategoryId), -1);
|
CategoryId = Read(node, nameof(CategoryId), -1);
|
||||||
|
WalletId = Read(node, nameof(WalletId), -1);
|
||||||
Store = Read(node, nameof(Store), string.Empty);
|
Store = Read(node, nameof(Store), string.Empty);
|
||||||
CreateTime = Read(node, nameof(CreateTime), default(DateTime));
|
CreateTime = Read(node, nameof(CreateTime), default(DateTime));
|
||||||
}
|
}
|
||||||
@ -25,6 +27,7 @@ public class Billing : BaseModel
|
|||||||
Write(node, nameof(Amount), Amount);
|
Write(node, nameof(Amount), Amount);
|
||||||
Write(node, nameof(Name), Name);
|
Write(node, nameof(Name), Name);
|
||||||
Write(node, nameof(CategoryId), CategoryId);
|
Write(node, nameof(CategoryId), CategoryId);
|
||||||
|
Write(node, nameof(WalletId), WalletId);
|
||||||
Write(node, nameof(Store), Store);
|
Write(node, nameof(Store), Store);
|
||||||
Write(node, nameof(CreateTime), CreateTime);
|
Write(node, nameof(CreateTime), CreateTime);
|
||||||
}
|
}
|
||||||
|
@ -5,12 +5,14 @@ namespace Billing.Models;
|
|||||||
public class Category : BaseModel
|
public class Category : BaseModel
|
||||||
{
|
{
|
||||||
public int Id { get; set; }
|
public int Id { get; set; }
|
||||||
|
public string Icon { get; set; } = ICON_DEFAULT;
|
||||||
public string Name { get; set; }
|
public string Name { get; set; }
|
||||||
public int? ParentId { get; set; }
|
public int? ParentId { get; set; }
|
||||||
|
|
||||||
public override void OnXmlDeserialize(XElement node)
|
public override void OnXmlDeserialize(XElement node)
|
||||||
{
|
{
|
||||||
Id = Read(node, nameof(Id), 0);
|
Id = Read(node, nameof(Id), 0);
|
||||||
|
Icon = Read(node, nameof(Icon), ICON_DEFAULT);
|
||||||
Name = Read(node, nameof(Name), string.Empty);
|
Name = Read(node, nameof(Name), string.Empty);
|
||||||
var parentId = Read(node, nameof(ParentId), -1);
|
var parentId = Read(node, nameof(ParentId), -1);
|
||||||
if (parentId >= 0)
|
if (parentId >= 0)
|
||||||
@ -22,6 +24,7 @@ public class Category : BaseModel
|
|||||||
public override void OnXmlSerialize(XElement node)
|
public override void OnXmlSerialize(XElement node)
|
||||||
{
|
{
|
||||||
Write(node, nameof(Id), Id);
|
Write(node, nameof(Id), Id);
|
||||||
|
Write(node, nameof(Icon), Icon);
|
||||||
Write(node, nameof(Name), Name);
|
Write(node, nameof(Name), Name);
|
||||||
if (ParentId != null)
|
if (ParentId != null)
|
||||||
{
|
{
|
||||||
|
@ -9,7 +9,9 @@ public abstract class BaseTheme : ResourceDictionary
|
|||||||
public const string CascadiaFontBold = nameof(CascadiaFontBold);
|
public const string CascadiaFontBold = nameof(CascadiaFontBold);
|
||||||
public const string RobotoCondensedFontRegular = nameof(RobotoCondensedFontRegular);
|
public const string RobotoCondensedFontRegular = nameof(RobotoCondensedFontRegular);
|
||||||
public const string RobotoCondensedFontBold = nameof(RobotoCondensedFontBold);
|
public const string RobotoCondensedFontBold = nameof(RobotoCondensedFontBold);
|
||||||
|
|
||||||
public const string WindowBackgroundColor = nameof(WindowBackgroundColor);
|
public const string WindowBackgroundColor = nameof(WindowBackgroundColor);
|
||||||
|
public const string OptionTintColor = nameof(OptionTintColor);
|
||||||
public const string PromptBackgroundColor = nameof(PromptBackgroundColor);
|
public const string PromptBackgroundColor = nameof(PromptBackgroundColor);
|
||||||
public const string PrimaryColor = nameof(PrimaryColor);
|
public const string PrimaryColor = nameof(PrimaryColor);
|
||||||
public const string SecondaryColor = nameof(SecondaryColor);
|
public const string SecondaryColor = nameof(SecondaryColor);
|
||||||
@ -18,7 +20,8 @@ public abstract class BaseTheme : ResourceDictionary
|
|||||||
public const string TabBarUnselectedColor = nameof(TabBarUnselectedColor);
|
public const string TabBarUnselectedColor = nameof(TabBarUnselectedColor);
|
||||||
public const string OutRangeDayColor = nameof(OutRangeDayColor);
|
public const string OutRangeDayColor = nameof(OutRangeDayColor);
|
||||||
public const string TextColor = nameof(TextColor);
|
public const string TextColor = nameof(TextColor);
|
||||||
public const string WeekendColor = nameof(WeekendColor);
|
public const string SecondaryTextColor = nameof(SecondaryTextColor);
|
||||||
|
public const string RedColor = nameof(RedColor);
|
||||||
|
|
||||||
protected abstract Color PrimaryMauiColor { get; }
|
protected abstract Color PrimaryMauiColor { get; }
|
||||||
protected abstract Color SecondaryMauiColor { get; }
|
protected abstract Color SecondaryMauiColor { get; }
|
||||||
@ -44,6 +47,14 @@ public abstract class BaseTheme : ResourceDictionary
|
|||||||
new Setter { Property = Label.FontFamilyProperty, Value = robotoRegularFontFamily }
|
new Setter { Property = Label.FontFamilyProperty, Value = robotoRegularFontFamily }
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
Add(new Style(typeof(OptionEntry))
|
||||||
|
{
|
||||||
|
Setters =
|
||||||
|
{
|
||||||
|
new Setter { Property = Entry.FontSizeProperty, Value = Device.GetNamedSize(NamedSize.Small, typeof(Entry)) },
|
||||||
|
new Setter { Property = Entry.FontFamilyProperty, Value = robotoRegularFontFamily }
|
||||||
|
}
|
||||||
|
});
|
||||||
Add(new Style(typeof(Button))
|
Add(new Style(typeof(Button))
|
||||||
{
|
{
|
||||||
Setters =
|
Setters =
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
using Xamarin.Forms;
|
using Billing.UI;
|
||||||
|
using Xamarin.Forms;
|
||||||
|
|
||||||
namespace Billing.Themes;
|
namespace Billing.Themes;
|
||||||
|
|
||||||
@ -20,12 +21,14 @@ public class Dark : BaseTheme
|
|||||||
private void InitColors()
|
private void InitColors()
|
||||||
{
|
{
|
||||||
Add(WindowBackgroundColor, Color.Black);
|
Add(WindowBackgroundColor, Color.Black);
|
||||||
|
Add(OptionTintColor, Color.FromRgb(28, 28, 28));
|
||||||
Add(PromptBackgroundColor, Color.FromRgb(0x1f, 0x1f, 0x1f));
|
Add(PromptBackgroundColor, Color.FromRgb(0x1f, 0x1f, 0x1f));
|
||||||
Add(TabBarBackgroundColor, Color.Black);
|
Add(TabBarBackgroundColor, Color.Black);
|
||||||
Add(TabBarUnselectedColor, Color.FromRgb(0x82, 0x82, 0x82));
|
Add(TabBarUnselectedColor, Color.FromRgb(0x82, 0x82, 0x82));
|
||||||
Add(OutRangeDayColor, Color.DarkGray);
|
Add(OutRangeDayColor, Color.DarkGray);
|
||||||
Add(TextColor, Color.FromRgb(0xcc, 0xcc, 0xcc));
|
Add(TextColor, Color.FromRgb(0xcc, 0xcc, 0xcc));
|
||||||
Add(WeekendColor, Color.FromRgb(211, 5, 5));
|
Add(SecondaryTextColor, Color.LightGray);
|
||||||
|
Add(RedColor, Color.FromRgb(211, 5, 5));
|
||||||
|
|
||||||
Add(new Style(typeof(TabBar))
|
Add(new Style(typeof(TabBar))
|
||||||
{
|
{
|
||||||
@ -36,5 +39,12 @@ public class Dark : BaseTheme
|
|||||||
new Setter { Property = Shell.TabBarUnselectedColorProperty, Value = Color.FromRgb(0x82, 0x82, 0x82) }
|
new Setter { Property = Shell.TabBarUnselectedColorProperty, Value = Color.FromRgb(0x82, 0x82, 0x82) }
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
Add(new Style(typeof(TableView))
|
||||||
|
{
|
||||||
|
Setters =
|
||||||
|
{
|
||||||
|
new Setter { Property = VisualElement.BackgroundColorProperty, Value = Color.Black }
|
||||||
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
using Xamarin.Forms;
|
using Billing.UI;
|
||||||
|
using Xamarin.Forms;
|
||||||
|
|
||||||
namespace Billing.Themes;
|
namespace Billing.Themes;
|
||||||
|
|
||||||
@ -20,12 +21,14 @@ public class Light : BaseTheme
|
|||||||
private void InitColors()
|
private void InitColors()
|
||||||
{
|
{
|
||||||
Add(WindowBackgroundColor, Color.White);
|
Add(WindowBackgroundColor, Color.White);
|
||||||
|
Add(OptionTintColor, Color.White);
|
||||||
Add(PromptBackgroundColor, Color.FromRgb(0xe0, 0xe0, 0xe0));
|
Add(PromptBackgroundColor, Color.FromRgb(0xe0, 0xe0, 0xe0));
|
||||||
Add(TabBarBackgroundColor, Color.White);
|
Add(TabBarBackgroundColor, Color.White);
|
||||||
Add(TabBarUnselectedColor, Color.FromRgb(0x82, 0x82, 0x82));
|
Add(TabBarUnselectedColor, Color.FromRgb(0x82, 0x82, 0x82));
|
||||||
Add(OutRangeDayColor, Color.LightGray);
|
Add(OutRangeDayColor, Color.LightGray);
|
||||||
Add(TextColor, Color.FromRgb(0x33, 0x33, 0x33));
|
Add(TextColor, Color.FromRgb(0x33, 0x33, 0x33));
|
||||||
Add(WeekendColor, Color.FromRgb(211, 64, 85));
|
Add(SecondaryTextColor, Color.DimGray);
|
||||||
|
Add(RedColor, Color.FromRgb(211, 64, 85));
|
||||||
|
|
||||||
Add(new Style(typeof(TabBar))
|
Add(new Style(typeof(TabBar))
|
||||||
{
|
{
|
||||||
@ -36,5 +39,12 @@ public class Light : BaseTheme
|
|||||||
new Setter { Property = Shell.TabBarUnselectedColorProperty, Value = Color.FromRgb(0x82, 0x82, 0x82) }
|
new Setter { Property = Shell.TabBarUnselectedColorProperty, Value = Color.FromRgb(0x82, 0x82, 0x82) }
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
Add(new Style(typeof(TableView))
|
||||||
|
{
|
||||||
|
Setters =
|
||||||
|
{
|
||||||
|
new Setter { Property = VisualElement.BackgroundColorProperty, Value = Color.FromRgb(242, 241, 245) }
|
||||||
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -37,7 +37,7 @@
|
|||||||
<TapGestureRecognizer Command="{Binding OnDayTapped, Source={x:Reference billingDate}}" CommandParameter="{TemplateBinding BillingDay}"/>
|
<TapGestureRecognizer Command="{Binding OnDayTapped, Source={x:Reference billingDate}}" CommandParameter="{TemplateBinding BillingDay}"/>
|
||||||
</Grid.GestureRecognizers>
|
</Grid.GestureRecognizers>
|
||||||
<Label Style="{StaticResource dateLabel}" Text="{TemplateBinding BillingDay.Text}"
|
<Label Style="{StaticResource dateLabel}" Text="{TemplateBinding BillingDay.Text}"
|
||||||
TextColor="{DynamicResource WeekendColor}"
|
TextColor="{DynamicResource RedColor}"
|
||||||
FontFamily="{TemplateBinding BillingDay.FontFamily}"
|
FontFamily="{TemplateBinding BillingDay.FontFamily}"
|
||||||
Opacity="{TemplateBinding BillingDay.TextOpacity}"/>
|
Opacity="{TemplateBinding BillingDay.TextOpacity}"/>
|
||||||
<StackLayout Grid.Row="1"
|
<StackLayout Grid.Row="1"
|
||||||
|
@ -1,4 +1,3 @@
|
|||||||
using Billing.Themes;
|
|
||||||
using System;
|
using System;
|
||||||
using Xamarin.Forms;
|
using Xamarin.Forms;
|
||||||
|
|
||||||
|
@ -21,3 +21,20 @@ public class TitleDateConverter : IValueConverter
|
|||||||
return value;
|
return value;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public class MoneyConverter : IValueConverter
|
||||||
|
{
|
||||||
|
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
|
||||||
|
{
|
||||||
|
if (value is decimal d)
|
||||||
|
{
|
||||||
|
return "¥ " + d.ToString("n2", CultureInfo.InvariantCulture);
|
||||||
|
}
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
|
||||||
|
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
|
||||||
|
{
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
using System;
|
using Billing.Themes;
|
||||||
|
using System;
|
||||||
using Xamarin.Forms;
|
using Xamarin.Forms;
|
||||||
|
|
||||||
namespace Billing.UI;
|
namespace Billing.UI;
|
||||||
@ -29,3 +30,125 @@ public class LongPressButton : Button
|
|||||||
LongPressed?.Invoke(this, EventArgs.Empty);
|
LongPressed?.Invoke(this, EventArgs.Empty);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public class OptionEntry : Entry { }
|
||||||
|
|
||||||
|
public abstract class OptionCell : ViewCell
|
||||||
|
{
|
||||||
|
public static readonly BindableProperty TitleProperty = BindableProperty.Create(nameof(Title), typeof(string), typeof(OptionCell));
|
||||||
|
public static readonly BindableProperty BackgroundColorProperty = BindableProperty.Create(nameof(BackgroundColor), typeof(Color), typeof(OptionCell));
|
||||||
|
|
||||||
|
public string Title
|
||||||
|
{
|
||||||
|
get => (string)GetValue(TitleProperty);
|
||||||
|
set => SetValue(TitleProperty, value);
|
||||||
|
}
|
||||||
|
public Color BackgroundColor
|
||||||
|
{
|
||||||
|
get => (Color)GetValue(BackgroundColorProperty);
|
||||||
|
set => SetValue(BackgroundColorProperty, value);
|
||||||
|
}
|
||||||
|
|
||||||
|
protected abstract View Content { get; }
|
||||||
|
|
||||||
|
public OptionCell()
|
||||||
|
{
|
||||||
|
View = new Grid
|
||||||
|
{
|
||||||
|
BindingContext = this,
|
||||||
|
Padding = new Thickness(20, 0),
|
||||||
|
ColumnDefinitions =
|
||||||
|
{
|
||||||
|
new ColumnDefinition { Width = new GridLength(.3, GridUnitType.Star) },
|
||||||
|
new ColumnDefinition { Width = new GridLength(.7, GridUnitType.Star) }
|
||||||
|
},
|
||||||
|
Children =
|
||||||
|
{
|
||||||
|
new Label
|
||||||
|
{
|
||||||
|
LineBreakMode = LineBreakMode.TailTruncation,
|
||||||
|
VerticalOptions = LayoutOptions.Center
|
||||||
|
}
|
||||||
|
.Binding(Label.TextProperty, nameof(Title))
|
||||||
|
.DynamicResource(Label.TextColorProperty, BaseTheme.TextColor),
|
||||||
|
|
||||||
|
Content.GridColumn(1)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.DynamicResource(VisualElement.BackgroundColorProperty, BaseTheme.OptionTintColor);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public class OptionTextCell : OptionCell
|
||||||
|
{
|
||||||
|
public static readonly BindableProperty DetailProperty = BindableProperty.Create(nameof(Detail), typeof(string), typeof(OptionTextCell));
|
||||||
|
|
||||||
|
public string Detail
|
||||||
|
{
|
||||||
|
get => (string)GetValue(DetailProperty);
|
||||||
|
set => SetValue(DetailProperty, value);
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override View Content => new Label
|
||||||
|
{
|
||||||
|
HorizontalOptions = LayoutOptions.End,
|
||||||
|
VerticalOptions = LayoutOptions.Center
|
||||||
|
}
|
||||||
|
.Binding(Label.TextProperty, nameof(Detail))
|
||||||
|
.DynamicResource(Label.TextColorProperty, BaseTheme.SecondaryTextColor);
|
||||||
|
}
|
||||||
|
|
||||||
|
public class OptionSwitchCell : OptionCell
|
||||||
|
{
|
||||||
|
public static readonly BindableProperty IsToggledProperty = BindableProperty.Create(nameof(IsToggled), typeof(bool), typeof(OptionSwitchCell));
|
||||||
|
|
||||||
|
public bool IsToggled
|
||||||
|
{
|
||||||
|
get => (bool)GetValue(IsToggledProperty);
|
||||||
|
set => SetValue(IsToggledProperty, value);
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override View Content => new Switch
|
||||||
|
{
|
||||||
|
HorizontalOptions = LayoutOptions.End,
|
||||||
|
VerticalOptions = LayoutOptions.Center
|
||||||
|
}
|
||||||
|
.Binding(Switch.IsToggledProperty, nameof(IsToggled), BindingMode.TwoWay);
|
||||||
|
}
|
||||||
|
|
||||||
|
public class OptionEntryCell : OptionCell
|
||||||
|
{
|
||||||
|
public static readonly BindableProperty TextProperty = BindableProperty.Create(nameof(Text), typeof(string), typeof(OptionEntryCell));
|
||||||
|
public static readonly BindableProperty KeyboardProperty = BindableProperty.Create(nameof(Keyboard), typeof(Keyboard), typeof(OptionEntryCell));
|
||||||
|
public static readonly BindableProperty PlaceholderProperty = BindableProperty.Create(nameof(Placeholder), typeof(string), typeof(OptionEntryCell));
|
||||||
|
|
||||||
|
public string Text
|
||||||
|
{
|
||||||
|
get => (string)GetValue(TextProperty);
|
||||||
|
set => SetValue(TextProperty, value);
|
||||||
|
}
|
||||||
|
public Keyboard Keyboard
|
||||||
|
{
|
||||||
|
get => (Keyboard)GetValue(KeyboardProperty);
|
||||||
|
set => SetValue(KeyboardProperty, value);
|
||||||
|
}
|
||||||
|
public string Placeholder
|
||||||
|
{
|
||||||
|
get => (string)GetValue(PlaceholderProperty);
|
||||||
|
set => SetValue(PlaceholderProperty, value);
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override View Content => new OptionEntry
|
||||||
|
{
|
||||||
|
HorizontalOptions = LayoutOptions.Fill,
|
||||||
|
HorizontalTextAlignment = TextAlignment.End,
|
||||||
|
VerticalOptions = LayoutOptions.Center,
|
||||||
|
ReturnType = ReturnType.Next
|
||||||
|
}
|
||||||
|
.Binding(Entry.TextProperty, nameof(Text), BindingMode.TwoWay)
|
||||||
|
.Binding(InputView.KeyboardProperty, nameof(Keyboard))
|
||||||
|
.Binding(Entry.PlaceholderProperty, nameof(Placeholder))
|
||||||
|
.DynamicResource(Entry.TextColorProperty, BaseTheme.TextColor)
|
||||||
|
.DynamicResource(Entry.PlaceholderColorProperty, BaseTheme.SecondaryTextColor)
|
||||||
|
.DynamicResource(VisualElement.BackgroundColorProperty, BaseTheme.OptionTintColor);
|
||||||
|
}
|
15
Billing.Shared/UI/CustomEffect.cs
Normal file
@ -0,0 +1,15 @@
|
|||||||
|
using Xamarin.Forms;
|
||||||
|
|
||||||
|
namespace Billing.UI;
|
||||||
|
|
||||||
|
public class ShadowEffect : RoutingEffect
|
||||||
|
{
|
||||||
|
public float Radius { get; set; }
|
||||||
|
public Color Color { get; set; }
|
||||||
|
public Size Offect { get; set; }
|
||||||
|
public float Opacity { get; set; }
|
||||||
|
|
||||||
|
public ShadowEffect() : base($"Org.Tsanie.{nameof(ShadowEffect)}")
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
@ -1,4 +1,7 @@
|
|||||||
namespace Billing.UI;
|
using System;
|
||||||
|
using Xamarin.Forms;
|
||||||
|
|
||||||
|
namespace Billing.UI;
|
||||||
|
|
||||||
public static partial class Definition
|
public static partial class Definition
|
||||||
{
|
{
|
||||||
@ -7,3 +10,59 @@ public static partial class Definition
|
|||||||
public static partial string GetRobotoCondensedRegularFontFamily();
|
public static partial string GetRobotoCondensedRegularFontFamily();
|
||||||
public static partial string GetRobotoCondensedBoldFontFamily();
|
public static partial string GetRobotoCondensedBoldFontFamily();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static class ExtensionHelper
|
||||||
|
{
|
||||||
|
public static View Binding(this View view, BindableProperty property, string path, BindingMode mode = BindingMode.Default, IValueConverter converter = null)
|
||||||
|
{
|
||||||
|
view.SetBinding(property, path, mode, converter);
|
||||||
|
return view;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static View DynamicResource(this View view, BindableProperty property, string key)
|
||||||
|
{
|
||||||
|
view.SetDynamicResource(property, key);
|
||||||
|
return view;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static View GridColumn(this View view, int column)
|
||||||
|
{
|
||||||
|
Grid.SetColumn(view, column);
|
||||||
|
return view;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static View GridRow(this View view, int row)
|
||||||
|
{
|
||||||
|
Grid.SetRow(view, row);
|
||||||
|
return view;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public class Tap : IDisposable
|
||||||
|
{
|
||||||
|
private readonly static object sync = new();
|
||||||
|
private static Tap instance;
|
||||||
|
|
||||||
|
private bool busy = false;
|
||||||
|
|
||||||
|
private Tap() { }
|
||||||
|
|
||||||
|
public static bool IsBusy => instance?.busy ?? false;
|
||||||
|
|
||||||
|
public static Tap Start()
|
||||||
|
{
|
||||||
|
lock (sync)
|
||||||
|
{
|
||||||
|
(instance ??= new Tap()).busy = true;
|
||||||
|
}
|
||||||
|
return instance;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Dispose()
|
||||||
|
{
|
||||||
|
lock (sync)
|
||||||
|
{
|
||||||
|
busy = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@ -2,12 +2,44 @@
|
|||||||
<ui:BillingPage xmlns="http://xamarin.com/schemas/2014/forms"
|
<ui:BillingPage xmlns="http://xamarin.com/schemas/2014/forms"
|
||||||
xmlns:r="clr-namespace:Billing.Languages"
|
xmlns:r="clr-namespace:Billing.Languages"
|
||||||
xmlns:ui="clr-namespace:Billing.UI"
|
xmlns:ui="clr-namespace:Billing.UI"
|
||||||
|
xmlns:v="clr-namespace:Billing.Views"
|
||||||
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
|
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
|
||||||
x:Class="Billing.Views.AccountPage"
|
x:Class="Billing.Views.AccountPage"
|
||||||
Title="{r:Text Accounts}">
|
x:Name="accountPage"
|
||||||
<StackLayout>
|
x:DataType="v:AccountPage"
|
||||||
<Label Text="Welcome to Account Page!"
|
Title="{r:Text Accounts}"
|
||||||
VerticalOptions="CenterAndExpand"
|
BindingContext="{x:Reference accountPage}">
|
||||||
HorizontalOptions="CenterAndExpand" />
|
|
||||||
</StackLayout>
|
<ContentPage.Resources>
|
||||||
|
<ui:MoneyConverter x:Key="moneyConverter"/>
|
||||||
|
</ContentPage.Resources>
|
||||||
|
|
||||||
|
<ContentPage.ToolbarItems>
|
||||||
|
<ToolbarItem Order="Primary" IconImageSource="plus.png" Command="{Binding AddAccount}"/>
|
||||||
|
</ContentPage.ToolbarItems>
|
||||||
|
|
||||||
|
<ScrollView>
|
||||||
|
<StackLayout>
|
||||||
|
<Grid HeightRequest="100" BackgroundColor="{DynamicResource PromptBackgroundColor}" ColumnDefinitions="Auto, *">
|
||||||
|
<!--<Grid.Effects>
|
||||||
|
<ui:ShadowEffect Offect="0, 3" Color="Black" Opacity=".4"/>
|
||||||
|
</Grid.Effects>-->
|
||||||
|
<StackLayout VerticalOptions="Center" Margin="20, 0" Spacing="0">
|
||||||
|
<Label FontSize="Small" Text="{r:Text Balance}"/>
|
||||||
|
<Label FontSize="24" FontFamily="{DynamicResource RobotoCondensedFontBold}"
|
||||||
|
Text="{Binding Balance, Converter={StaticResource moneyConverter}}"/>
|
||||||
|
</StackLayout>
|
||||||
|
<Grid Grid.Column="1" Margin="20, 0" VerticalOptions="Center" HorizontalOptions="End"
|
||||||
|
ColumnDefinitions="Auto, Auto" RowDefinitions="Auto, Auto">
|
||||||
|
<Label FontSize="Small" HorizontalOptions="End" Text="{r:Text Assets}"/>
|
||||||
|
<Label Grid.Column="1" FontSize="Small" Margin="10, 0, 0, 0" HorizontalOptions="End"
|
||||||
|
Text="{Binding Asset, Converter={StaticResource moneyConverter}}"/>
|
||||||
|
<Label Grid.Row="1" FontSize="Small" HorizontalOptions="End" Text="{r:Text Liability}"/>
|
||||||
|
<Label Grid.Row="1" Grid.Column="1" FontSize="Small" Margin="10, 0, 0, 0" HorizontalOptions="End"
|
||||||
|
TextColor="{DynamicResource RedColor}"
|
||||||
|
Text="{Binding Liability, Converter={StaticResource moneyConverter}}"/>
|
||||||
|
</Grid>
|
||||||
|
</Grid>
|
||||||
|
</StackLayout>
|
||||||
|
</ScrollView>
|
||||||
</ui:BillingPage>
|
</ui:BillingPage>
|
@ -1,11 +1,44 @@
|
|||||||
using Billing.UI;
|
using Billing.UI;
|
||||||
|
using System;
|
||||||
|
using Xamarin.Forms;
|
||||||
|
|
||||||
namespace Billing.Views;
|
namespace Billing.Views;
|
||||||
|
|
||||||
public partial class AccountPage : BillingPage
|
public partial class AccountPage : BillingPage
|
||||||
{
|
{
|
||||||
|
private static readonly BindableProperty BalanceProperty = BindableProperty.Create(nameof(Balance), typeof(decimal), typeof(AccountPage));
|
||||||
|
private static readonly BindableProperty AssetProperty = BindableProperty.Create(nameof(Asset), typeof(decimal), typeof(AccountPage));
|
||||||
|
private static readonly BindableProperty LiabilityProperty = BindableProperty.Create(nameof(Liability), typeof(decimal), typeof(AccountPage));
|
||||||
|
|
||||||
|
public decimal Balance => (decimal)GetValue(BalanceProperty);
|
||||||
|
public decimal Asset => (decimal)GetValue(AssetProperty);
|
||||||
|
public decimal Liability => (decimal)GetValue(LiabilityProperty);
|
||||||
|
|
||||||
|
public Command AddAccount { get; }
|
||||||
|
|
||||||
public AccountPage()
|
public AccountPage()
|
||||||
{
|
{
|
||||||
|
AddAccount = new Command(OnAddAccount);
|
||||||
|
|
||||||
InitializeComponent();
|
InitializeComponent();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private async void OnAddAccount()
|
||||||
|
{
|
||||||
|
if (Tap.IsBusy)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
using (Tap.Start())
|
||||||
|
{
|
||||||
|
var page = new AddAccountPage();
|
||||||
|
page.AccountChecked += AccountChecked;
|
||||||
|
await Navigation.PushAsync(page);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void AccountChecked(object sender, AccountEventArgs e)
|
||||||
|
{
|
||||||
|
Helper.Debug(e.Account.ToString());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
40
Billing.Shared/Views/AddAccountPage.xaml
Normal file
@ -0,0 +1,40 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8" ?>
|
||||||
|
<ui:BillingPage xmlns="http://xamarin.com/schemas/2014/forms"
|
||||||
|
xmlns:r="clr-namespace:Billing.Languages"
|
||||||
|
xmlns:ui="clr-namespace:Billing.UI"
|
||||||
|
xmlns:v="clr-namespace:Billing.Views"
|
||||||
|
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
|
||||||
|
x:Class="Billing.Views.AddAccountPage"
|
||||||
|
x:Name="addAccountPage"
|
||||||
|
x:DataType="v:AddAccountPage"
|
||||||
|
Title="{r:Text AddAccount}"
|
||||||
|
BindingContext="{x:Reference addAccountPage}">
|
||||||
|
|
||||||
|
<ContentPage.ToolbarItems>
|
||||||
|
<ToolbarItem Order="Primary" IconImageSource="check.png" Command="{Binding CheckAccount}"/>
|
||||||
|
</ContentPage.ToolbarItems>
|
||||||
|
|
||||||
|
<ContentPage.Content>
|
||||||
|
<TableView Intent="Settings">
|
||||||
|
<TableSection>
|
||||||
|
<ui:OptionEntryCell Title="{r:Text AccountName}"
|
||||||
|
Text="{Binding AccountName, Mode=TwoWay}"
|
||||||
|
Keyboard="Text" Placeholder="{r:Text AccountNamePlaceholder}"/>
|
||||||
|
<ui:OptionTextCell Title="{r:Text Icon}"
|
||||||
|
Detail="{Binding AccountIcon}"/>
|
||||||
|
</TableSection>
|
||||||
|
<TableSection>
|
||||||
|
<ui:OptionEntryCell Title="{r:Text Balance}"
|
||||||
|
Text="{Binding Balance, Mode=TwoWay}"
|
||||||
|
Keyboard="Numeric" Placeholder="{r:Text BalancePlaceholder}"/>
|
||||||
|
<ui:OptionTextCell Title="{r:Text Currency}"
|
||||||
|
Detail="{r:Text CNY}"/>
|
||||||
|
</TableSection>
|
||||||
|
<TableSection>
|
||||||
|
<ui:OptionEntryCell Title="{r:Text Memo}"
|
||||||
|
Text="{Binding Memo, Mode=TwoWay}"
|
||||||
|
Keyboard="Plain" Placeholder="{r:Text MemoPlaceholder}"/>
|
||||||
|
</TableSection>
|
||||||
|
</TableView>
|
||||||
|
</ContentPage.Content>
|
||||||
|
</ui:BillingPage>
|
86
Billing.Shared/Views/AddAccountPage.xaml.cs
Normal file
@ -0,0 +1,86 @@
|
|||||||
|
using Billing.Models;
|
||||||
|
using Billing.UI;
|
||||||
|
using System;
|
||||||
|
using Xamarin.Forms;
|
||||||
|
|
||||||
|
namespace Billing.Views;
|
||||||
|
|
||||||
|
public partial class AddAccountPage : BillingPage
|
||||||
|
{
|
||||||
|
private static readonly BindableProperty AccountNameProperty = BindableProperty.Create(nameof(AccountName), typeof(string), typeof(AddAccountPage));
|
||||||
|
private static readonly BindableProperty AccountIconProperty = BindableProperty.Create(nameof(AccountIcon), typeof(string), typeof(AddAccountPage));
|
||||||
|
private static readonly BindableProperty CategoryProperty = BindableProperty.Create(nameof(Category), typeof(string), typeof(AddAccountPage));
|
||||||
|
private static readonly BindableProperty BalanceProperty = BindableProperty.Create(nameof(Balance), typeof(decimal), typeof(AddAccountPage));
|
||||||
|
private static readonly BindableProperty MemoProperty = BindableProperty.Create(nameof(Memo), typeof(string), typeof(AddAccountPage));
|
||||||
|
|
||||||
|
public string AccountName
|
||||||
|
{
|
||||||
|
get => (string)GetValue(AccountNameProperty);
|
||||||
|
set => SetValue(AccountNameProperty, value);
|
||||||
|
}
|
||||||
|
public string AccountIcon
|
||||||
|
{
|
||||||
|
get => (string)GetValue(AccountIconProperty);
|
||||||
|
set => SetValue(AccountIconProperty, value);
|
||||||
|
}
|
||||||
|
public string Category
|
||||||
|
{
|
||||||
|
get => (string)GetValue(CategoryProperty);
|
||||||
|
set => SetValue(CategoryProperty, value);
|
||||||
|
}
|
||||||
|
public decimal Balance
|
||||||
|
{
|
||||||
|
get => (decimal)GetValue(BalanceProperty);
|
||||||
|
set => SetValue(BalanceProperty, value);
|
||||||
|
}
|
||||||
|
public string Memo
|
||||||
|
{
|
||||||
|
get => (string)GetValue(MemoProperty);
|
||||||
|
set => SetValue(MemoProperty, value);
|
||||||
|
}
|
||||||
|
|
||||||
|
private readonly Account account;
|
||||||
|
|
||||||
|
public Command CheckAccount { get; }
|
||||||
|
|
||||||
|
public event EventHandler<AccountEventArgs> AccountChecked;
|
||||||
|
|
||||||
|
public AddAccountPage()
|
||||||
|
{
|
||||||
|
CheckAccount = new Command(OnCheckAccount);
|
||||||
|
InitializeComponent();
|
||||||
|
}
|
||||||
|
|
||||||
|
public AddAccountPage(Account account)
|
||||||
|
{
|
||||||
|
this.account = account;
|
||||||
|
AccountName = account.Name;
|
||||||
|
AccountIcon = account.Icon;
|
||||||
|
Category = account.Category.ToString();
|
||||||
|
Balance = account.Balance;
|
||||||
|
Memo = account.Memo;
|
||||||
|
CheckAccount = new Command(OnCheckAccount);
|
||||||
|
InitializeComponent();
|
||||||
|
}
|
||||||
|
|
||||||
|
private void OnCheckAccount()
|
||||||
|
{
|
||||||
|
AccountChecked?.Invoke(this, new AccountEventArgs
|
||||||
|
{
|
||||||
|
Account = new Account
|
||||||
|
{
|
||||||
|
Id = account?.Id ?? -1,
|
||||||
|
Name = AccountName,
|
||||||
|
Icon = AccountIcon,
|
||||||
|
//Category = Category,
|
||||||
|
Balance = Balance,
|
||||||
|
Memo = Memo
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public class AccountEventArgs : EventArgs
|
||||||
|
{
|
||||||
|
public Account Account { get; set; }
|
||||||
|
}
|
@ -39,7 +39,7 @@
|
|||||||
<StackLayout.GestureRecognizers>
|
<StackLayout.GestureRecognizers>
|
||||||
<TapGestureRecognizer Command="{Binding AddBilling}"/>
|
<TapGestureRecognizer Command="{Binding AddBilling}"/>
|
||||||
</StackLayout.GestureRecognizers>
|
</StackLayout.GestureRecognizers>
|
||||||
<Label Text="{r:Text Memo}" TextColor="{DynamicResource PrimaryColor}"
|
<Label Text="{r:Text TapToMemo}" TextColor="{DynamicResource PrimaryColor}"
|
||||||
VerticalOptions="Center"/>
|
VerticalOptions="Center"/>
|
||||||
<!--<Label Style="{DynamicResource IconLightStyle}"
|
<!--<Label Style="{DynamicResource IconLightStyle}"
|
||||||
Text="{x:Static local:Definition.IconRight}"
|
Text="{x:Static local:Definition.IconRight}"
|
||||||
|
@ -70,9 +70,11 @@
|
|||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<Compile Include="Definition.cs" />
|
<Compile Include="Definition.cs" />
|
||||||
|
<Compile Include="Effects\ShadowEffectPlatform.cs" />
|
||||||
<Compile Include="MainActivity.cs" />
|
<Compile Include="MainActivity.cs" />
|
||||||
<Compile Include="PlatformCulture.cs" />
|
<Compile Include="PlatformCulture.cs" />
|
||||||
<Compile Include="Renderers\LongPressButtonRenderer.cs" />
|
<Compile Include="Renderers\LongPressButtonRenderer.cs" />
|
||||||
|
<Compile Include="Renderers\OptionEntryRenderer.cs" />
|
||||||
<Compile Include="Renderers\TintImageRenderer.cs" />
|
<Compile Include="Renderers\TintImageRenderer.cs" />
|
||||||
<Compile Include="Resources\Resource.designer.cs" />
|
<Compile Include="Resources\Resource.designer.cs" />
|
||||||
<Compile Include="Properties\AssemblyInfo.cs" />
|
<Compile Include="Properties\AssemblyInfo.cs" />
|
||||||
@ -187,6 +189,30 @@
|
|||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<AndroidResource Include="Resources\drawable-xxhdpi\calendar.png" />
|
<AndroidResource Include="Resources\drawable-xxhdpi\calendar.png" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<AndroidResource Include="Resources\drawable\ic_default.png" />
|
||||||
|
</ItemGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<AndroidResource Include="Resources\drawable-xxhdpi\ic_default.png" />
|
||||||
|
</ItemGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<AndroidResource Include="Resources\drawable-xhdpi\ic_default.png" />
|
||||||
|
</ItemGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<AndroidResource Include="Resources\drawable-mdpi\ic_default.png" />
|
||||||
|
</ItemGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<AndroidResource Include="Resources\drawable\check.png" />
|
||||||
|
</ItemGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<AndroidResource Include="Resources\drawable-mdpi\check.png" />
|
||||||
|
</ItemGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<AndroidResource Include="Resources\drawable-xhdpi\check.png" />
|
||||||
|
</ItemGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<AndroidResource Include="Resources\drawable-xxhdpi\check.png" />
|
||||||
|
</ItemGroup>
|
||||||
<Import Project="..\..\Billing.Shared\Billing.Shared.projitems" Label="Shared" />
|
<Import Project="..\..\Billing.Shared\Billing.Shared.projitems" Label="Shared" />
|
||||||
<Import Project="$(MSBuildExtensionsPath)\Xamarin\Android\Xamarin.Android.CSharp.targets" />
|
<Import Project="$(MSBuildExtensionsPath)\Xamarin\Android\Xamarin.Android.CSharp.targets" />
|
||||||
</Project>
|
</Project>
|
33
Billing/Billing.Android/Effects/ShadowEffectPlatform.cs
Normal file
@ -0,0 +1,33 @@
|
|||||||
|
using Android.Graphics;
|
||||||
|
using Billing.Droid.Effects;
|
||||||
|
using Billing.UI;
|
||||||
|
using System;
|
||||||
|
using System.Linq;
|
||||||
|
using Xamarin.Forms;
|
||||||
|
using Xamarin.Forms.Platform.Android;
|
||||||
|
|
||||||
|
[assembly: ResolutionGroupName("Org.Tsanie")]
|
||||||
|
[assembly: ExportEffect(typeof(ShadowEffectPlatform), nameof(ShadowEffect))]
|
||||||
|
namespace Billing.Droid.Effects;
|
||||||
|
|
||||||
|
public class ShadowEffectPlatform : PlatformEffect
|
||||||
|
{
|
||||||
|
protected override void OnAttached()
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
var effect = (ShadowEffect)Element.Effects.FirstOrDefault(e => e is ShadowEffect);
|
||||||
|
var paint = new Paint(PaintFlags.AntiAlias);
|
||||||
|
paint.SetShadowLayer(effect.Radius, (float)effect.Offect.Width, (float)effect.Offect.Height, effect.Color.ToAndroid());
|
||||||
|
Control.SetLayerPaint(paint);
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
Helper.Error("shadow.effect.attached", $"Cannot set property on attached control, error: {ex.Message}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override void OnDetached()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
27
Billing/Billing.Android/Renderers/OptionEntryRenderer.cs
Normal file
@ -0,0 +1,27 @@
|
|||||||
|
using Android.Content;
|
||||||
|
using Android.Graphics.Drawables;
|
||||||
|
using Billing.Droid.Renderers;
|
||||||
|
using Billing.UI;
|
||||||
|
using Xamarin.Forms;
|
||||||
|
using Xamarin.Forms.Platform.Android;
|
||||||
|
|
||||||
|
[assembly: ExportRenderer(typeof(OptionEntry), typeof(OptionEntryRenderer))]
|
||||||
|
namespace Billing.Droid.Renderers;
|
||||||
|
|
||||||
|
public class OptionEntryRenderer : EntryRenderer
|
||||||
|
{
|
||||||
|
public OptionEntryRenderer(Context context) : base(context)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override void OnElementChanged(ElementChangedEventArgs<Entry> e)
|
||||||
|
{
|
||||||
|
base.OnElementChanged(e);
|
||||||
|
|
||||||
|
if (e.NewElement != null)
|
||||||
|
{
|
||||||
|
var drawable = new ColorDrawable(e.NewElement.BackgroundColor.ToAndroid());
|
||||||
|
Control.SetBackground(drawable);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
116
Billing/Billing.Android/Resources/Resource.designer.cs
generated
@ -14,7 +14,7 @@ namespace Billing.Droid
|
|||||||
{
|
{
|
||||||
|
|
||||||
|
|
||||||
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("Xamarin.Android.Build.Tasks", "12.2.99.54")]
|
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("Xamarin.Android.Build.Tasks", "12.2.0.155")]
|
||||||
public partial class Resource
|
public partial class Resource
|
||||||
{
|
{
|
||||||
|
|
||||||
@ -16526,166 +16526,172 @@ namespace Billing.Droid
|
|||||||
public const int calendar = 2131165281;
|
public const int calendar = 2131165281;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070062
|
// aapt resource value: 0x7F070062
|
||||||
public const int design_fab_background = 2131165282;
|
public const int check = 2131165282;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070063
|
// aapt resource value: 0x7F070063
|
||||||
public const int design_ic_visibility = 2131165283;
|
public const int design_fab_background = 2131165283;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070064
|
// aapt resource value: 0x7F070064
|
||||||
public const int design_ic_visibility_off = 2131165284;
|
public const int design_ic_visibility = 2131165284;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070065
|
// aapt resource value: 0x7F070065
|
||||||
public const int design_password_eye = 2131165285;
|
public const int design_ic_visibility_off = 2131165285;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070066
|
// aapt resource value: 0x7F070066
|
||||||
public const int design_snackbar_background = 2131165286;
|
public const int design_password_eye = 2131165286;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070067
|
// aapt resource value: 0x7F070067
|
||||||
public const int ic_arrow_down_24dp = 2131165287;
|
public const int design_snackbar_background = 2131165287;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070068
|
// aapt resource value: 0x7F070068
|
||||||
public const int ic_clock_black_24dp = 2131165288;
|
public const int ic_arrow_down_24dp = 2131165288;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070069
|
// aapt resource value: 0x7F070069
|
||||||
public const int ic_keyboard_black_24dp = 2131165289;
|
public const int ic_clock_black_24dp = 2131165289;
|
||||||
|
|
||||||
// aapt resource value: 0x7F07006A
|
// aapt resource value: 0x7F07006A
|
||||||
public const int ic_mtrl_checked_circle = 2131165290;
|
public const int ic_default = 2131165290;
|
||||||
|
|
||||||
// aapt resource value: 0x7F07006B
|
// aapt resource value: 0x7F07006B
|
||||||
public const int ic_mtrl_chip_checked_black = 2131165291;
|
public const int ic_keyboard_black_24dp = 2131165291;
|
||||||
|
|
||||||
// aapt resource value: 0x7F07006C
|
// aapt resource value: 0x7F07006C
|
||||||
public const int ic_mtrl_chip_checked_circle = 2131165292;
|
public const int ic_mtrl_checked_circle = 2131165292;
|
||||||
|
|
||||||
// aapt resource value: 0x7F07006D
|
// aapt resource value: 0x7F07006D
|
||||||
public const int ic_mtrl_chip_close_circle = 2131165293;
|
public const int ic_mtrl_chip_checked_black = 2131165293;
|
||||||
|
|
||||||
// aapt resource value: 0x7F07006E
|
// aapt resource value: 0x7F07006E
|
||||||
public const int material_cursor_drawable = 2131165294;
|
public const int ic_mtrl_chip_checked_circle = 2131165294;
|
||||||
|
|
||||||
// aapt resource value: 0x7F07006F
|
// aapt resource value: 0x7F07006F
|
||||||
public const int material_ic_calendar_black_24dp = 2131165295;
|
public const int ic_mtrl_chip_close_circle = 2131165295;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070070
|
// aapt resource value: 0x7F070070
|
||||||
public const int material_ic_clear_black_24dp = 2131165296;
|
public const int material_cursor_drawable = 2131165296;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070071
|
// aapt resource value: 0x7F070071
|
||||||
public const int material_ic_edit_black_24dp = 2131165297;
|
public const int material_ic_calendar_black_24dp = 2131165297;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070072
|
// aapt resource value: 0x7F070072
|
||||||
public const int material_ic_keyboard_arrow_left_black_24dp = 2131165298;
|
public const int material_ic_clear_black_24dp = 2131165298;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070073
|
// aapt resource value: 0x7F070073
|
||||||
public const int material_ic_keyboard_arrow_next_black_24dp = 2131165299;
|
public const int material_ic_edit_black_24dp = 2131165299;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070074
|
// aapt resource value: 0x7F070074
|
||||||
public const int material_ic_keyboard_arrow_previous_black_24dp = 2131165300;
|
public const int material_ic_keyboard_arrow_left_black_24dp = 2131165300;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070075
|
// aapt resource value: 0x7F070075
|
||||||
public const int material_ic_keyboard_arrow_right_black_24dp = 2131165301;
|
public const int material_ic_keyboard_arrow_next_black_24dp = 2131165301;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070076
|
// aapt resource value: 0x7F070076
|
||||||
public const int material_ic_menu_arrow_down_black_24dp = 2131165302;
|
public const int material_ic_keyboard_arrow_previous_black_24dp = 2131165302;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070077
|
// aapt resource value: 0x7F070077
|
||||||
public const int material_ic_menu_arrow_up_black_24dp = 2131165303;
|
public const int material_ic_keyboard_arrow_right_black_24dp = 2131165303;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070078
|
// aapt resource value: 0x7F070078
|
||||||
public const int mtrl_dialog_background = 2131165304;
|
public const int material_ic_menu_arrow_down_black_24dp = 2131165304;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070079
|
// aapt resource value: 0x7F070079
|
||||||
public const int mtrl_dropdown_arrow = 2131165305;
|
public const int material_ic_menu_arrow_up_black_24dp = 2131165305;
|
||||||
|
|
||||||
// aapt resource value: 0x7F07007A
|
// aapt resource value: 0x7F07007A
|
||||||
public const int mtrl_ic_arrow_drop_down = 2131165306;
|
public const int mtrl_dialog_background = 2131165306;
|
||||||
|
|
||||||
// aapt resource value: 0x7F07007B
|
// aapt resource value: 0x7F07007B
|
||||||
public const int mtrl_ic_arrow_drop_up = 2131165307;
|
public const int mtrl_dropdown_arrow = 2131165307;
|
||||||
|
|
||||||
// aapt resource value: 0x7F07007C
|
// aapt resource value: 0x7F07007C
|
||||||
public const int mtrl_ic_cancel = 2131165308;
|
public const int mtrl_ic_arrow_drop_down = 2131165308;
|
||||||
|
|
||||||
// aapt resource value: 0x7F07007D
|
// aapt resource value: 0x7F07007D
|
||||||
public const int mtrl_ic_error = 2131165309;
|
public const int mtrl_ic_arrow_drop_up = 2131165309;
|
||||||
|
|
||||||
// aapt resource value: 0x7F07007E
|
// aapt resource value: 0x7F07007E
|
||||||
public const int mtrl_navigation_bar_item_background = 2131165310;
|
public const int mtrl_ic_cancel = 2131165310;
|
||||||
|
|
||||||
// aapt resource value: 0x7F07007F
|
// aapt resource value: 0x7F07007F
|
||||||
public const int mtrl_popupmenu_background = 2131165311;
|
public const int mtrl_ic_error = 2131165311;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070080
|
// aapt resource value: 0x7F070080
|
||||||
public const int mtrl_popupmenu_background_dark = 2131165312;
|
public const int mtrl_navigation_bar_item_background = 2131165312;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070081
|
// aapt resource value: 0x7F070081
|
||||||
public const int mtrl_tabs_default_indicator = 2131165313;
|
public const int mtrl_popupmenu_background = 2131165313;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070082
|
// aapt resource value: 0x7F070082
|
||||||
public const int navigation_empty_icon = 2131165314;
|
public const int mtrl_popupmenu_background_dark = 2131165314;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070083
|
// aapt resource value: 0x7F070083
|
||||||
public const int notification_action_background = 2131165315;
|
public const int mtrl_tabs_default_indicator = 2131165315;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070084
|
// aapt resource value: 0x7F070084
|
||||||
public const int notification_bg = 2131165316;
|
public const int navigation_empty_icon = 2131165316;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070085
|
// aapt resource value: 0x7F070085
|
||||||
public const int notification_bg_low = 2131165317;
|
public const int notification_action_background = 2131165317;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070086
|
// aapt resource value: 0x7F070086
|
||||||
public const int notification_bg_low_normal = 2131165318;
|
public const int notification_bg = 2131165318;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070087
|
// aapt resource value: 0x7F070087
|
||||||
public const int notification_bg_low_pressed = 2131165319;
|
public const int notification_bg_low = 2131165319;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070088
|
// aapt resource value: 0x7F070088
|
||||||
public const int notification_bg_normal = 2131165320;
|
public const int notification_bg_low_normal = 2131165320;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070089
|
// aapt resource value: 0x7F070089
|
||||||
public const int notification_bg_normal_pressed = 2131165321;
|
public const int notification_bg_low_pressed = 2131165321;
|
||||||
|
|
||||||
// aapt resource value: 0x7F07008A
|
// aapt resource value: 0x7F07008A
|
||||||
public const int notification_icon_background = 2131165322;
|
public const int notification_bg_normal = 2131165322;
|
||||||
|
|
||||||
// aapt resource value: 0x7F07008B
|
// aapt resource value: 0x7F07008B
|
||||||
public const int notification_template_icon_bg = 2131165323;
|
public const int notification_bg_normal_pressed = 2131165323;
|
||||||
|
|
||||||
// aapt resource value: 0x7F07008C
|
// aapt resource value: 0x7F07008C
|
||||||
public const int notification_template_icon_low_bg = 2131165324;
|
public const int notification_icon_background = 2131165324;
|
||||||
|
|
||||||
// aapt resource value: 0x7F07008D
|
// aapt resource value: 0x7F07008D
|
||||||
public const int notification_tile_bg = 2131165325;
|
public const int notification_template_icon_bg = 2131165325;
|
||||||
|
|
||||||
// aapt resource value: 0x7F07008E
|
// aapt resource value: 0x7F07008E
|
||||||
public const int notify_panel_notification_icon_bg = 2131165326;
|
public const int notification_template_icon_low_bg = 2131165326;
|
||||||
|
|
||||||
// aapt resource value: 0x7F07008F
|
// aapt resource value: 0x7F07008F
|
||||||
public const int plus = 2131165327;
|
public const int notification_tile_bg = 2131165327;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070090
|
// aapt resource value: 0x7F070090
|
||||||
public const int preference_list_divider_material = 2131165328;
|
public const int notify_panel_notification_icon_bg = 2131165328;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070091
|
// aapt resource value: 0x7F070091
|
||||||
public const int right = 2131165329;
|
public const int plus = 2131165329;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070092
|
// aapt resource value: 0x7F070092
|
||||||
public const int settings = 2131165330;
|
public const int preference_list_divider_material = 2131165330;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070093
|
// aapt resource value: 0x7F070093
|
||||||
public const int test_custom_background = 2131165331;
|
public const int right = 2131165331;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070094
|
// aapt resource value: 0x7F070094
|
||||||
public const int tooltip_frame_dark = 2131165332;
|
public const int settings = 2131165332;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070095
|
// aapt resource value: 0x7F070095
|
||||||
public const int tooltip_frame_light = 2131165333;
|
public const int test_custom_background = 2131165333;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070096
|
// aapt resource value: 0x7F070096
|
||||||
public const int wallet = 2131165334;
|
public const int tooltip_frame_dark = 2131165334;
|
||||||
|
|
||||||
// aapt resource value: 0x7F070097
|
// aapt resource value: 0x7F070097
|
||||||
public const int xamarin_logo = 2131165335;
|
public const int tooltip_frame_light = 2131165335;
|
||||||
|
|
||||||
|
// aapt resource value: 0x7F070098
|
||||||
|
public const int wallet = 2131165336;
|
||||||
|
|
||||||
|
// aapt resource value: 0x7F070099
|
||||||
|
public const int xamarin_logo = 2131165337;
|
||||||
|
|
||||||
static Drawable()
|
static Drawable()
|
||||||
{
|
{
|
||||||
|
BIN
Billing/Billing.Android/Resources/drawable-mdpi/check.png
Normal file
After Width: | Height: | Size: 735 B |
BIN
Billing/Billing.Android/Resources/drawable-mdpi/ic_default.png
Normal file
After Width: | Height: | Size: 454 B |
Before Width: | Height: | Size: 588 B After Width: | Height: | Size: 588 B |
BIN
Billing/Billing.Android/Resources/drawable-xhdpi/check.png
Normal file
After Width: | Height: | Size: 1.5 KiB |
BIN
Billing/Billing.Android/Resources/drawable-xhdpi/ic_default.png
Normal file
After Width: | Height: | Size: 969 B |
Before Width: | Height: | Size: 893 B After Width: | Height: | Size: 893 B |
BIN
Billing/Billing.Android/Resources/drawable-xxhdpi/check.png
Normal file
After Width: | Height: | Size: 2.9 KiB |
BIN
Billing/Billing.Android/Resources/drawable-xxhdpi/ic_default.png
Normal file
After Width: | Height: | Size: 1.6 KiB |
Before Width: | Height: | Size: 1.4 KiB After Width: | Height: | Size: 1.4 KiB |
BIN
Billing/Billing.Android/Resources/drawable/check.png
Normal file
After Width: | Height: | Size: 1.4 KiB |
BIN
Billing/Billing.Android/Resources/drawable/ic_default.png
Normal file
After Width: | Height: | Size: 795 B |
Before Width: | Height: | Size: 734 B After Width: | Height: | Size: 734 B |
@ -65,9 +65,11 @@
|
|||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<Compile Include="Definition.cs" />
|
<Compile Include="Definition.cs" />
|
||||||
|
<Compile Include="Effects\ShadowEffectPlatform.cs" />
|
||||||
<Compile Include="Main.cs" />
|
<Compile Include="Main.cs" />
|
||||||
<Compile Include="AppDelegate.cs" />
|
<Compile Include="AppDelegate.cs" />
|
||||||
<Compile Include="Renderers\LongPressButtonRenderer.cs" />
|
<Compile Include="Renderers\LongPressButtonRenderer.cs" />
|
||||||
|
<Compile Include="Renderers\OptionEntryRenderer.cs" />
|
||||||
<Compile Include="Renderers\TintImageRenderer.cs" />
|
<Compile Include="Renderers\TintImageRenderer.cs" />
|
||||||
<None Include="Entitlements.plist" />
|
<None Include="Entitlements.plist" />
|
||||||
<None Include="Info.plist" />
|
<None Include="Info.plist" />
|
||||||
@ -217,6 +219,24 @@
|
|||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<BundleResource Include="Resources\wallet%403x.png" />
|
<BundleResource Include="Resources\wallet%403x.png" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<BundleResource Include="Resources\ic_default.png" />
|
||||||
|
</ItemGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<BundleResource Include="Resources\ic_default%402x.png" />
|
||||||
|
</ItemGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<BundleResource Include="Resources\ic_default%403x.png" />
|
||||||
|
</ItemGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<BundleResource Include="Resources\check.png" />
|
||||||
|
</ItemGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<BundleResource Include="Resources\check%402x.png" />
|
||||||
|
</ItemGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<BundleResource Include="Resources\check%403x.png" />
|
||||||
|
</ItemGroup>
|
||||||
<Import Project="..\..\Billing.Shared\Billing.Shared.projitems" Label="Shared" />
|
<Import Project="..\..\Billing.Shared\Billing.Shared.projitems" Label="Shared" />
|
||||||
<Import Project="$(MSBuildExtensionsPath)\Xamarin\iOS\Xamarin.iOS.CSharp.targets" />
|
<Import Project="$(MSBuildExtensionsPath)\Xamarin\iOS\Xamarin.iOS.CSharp.targets" />
|
||||||
</Project>
|
</Project>
|
43
Billing/Billing.iOS/Effects/ShadowEffectPlatform.cs
Normal file
@ -0,0 +1,43 @@
|
|||||||
|
using Billing.iOS.Effects;
|
||||||
|
using Billing.UI;
|
||||||
|
using System;
|
||||||
|
using System.Linq;
|
||||||
|
using Xamarin.Forms;
|
||||||
|
using Xamarin.Forms.Platform.iOS;
|
||||||
|
|
||||||
|
[assembly: ResolutionGroupName("Org.Tsanie")]
|
||||||
|
[assembly: ExportEffect(typeof(ShadowEffectPlatform), nameof(ShadowEffect))]
|
||||||
|
namespace Billing.iOS.Effects;
|
||||||
|
|
||||||
|
public class ShadowEffectPlatform : PlatformEffect
|
||||||
|
{
|
||||||
|
protected override void OnAttached()
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
var effect = (ShadowEffect)Element.Effects.FirstOrDefault(e => e is ShadowEffect);
|
||||||
|
if (effect != null)
|
||||||
|
{
|
||||||
|
var layer = Control.Layer;
|
||||||
|
layer.ShadowRadius = effect.Radius;
|
||||||
|
layer.ShadowColor = effect.Color.ToCGColor();
|
||||||
|
layer.ShadowOffset = effect.Offect.ToSizeF();
|
||||||
|
layer.ShadowOpacity = effect.Opacity;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
Helper.Error("shadow.effect.attached", $"Cannot set property on attached control, error: {ex.Message}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override void OnDetached()
|
||||||
|
{
|
||||||
|
var layer = Control?.Layer;
|
||||||
|
if (layer != null)
|
||||||
|
{
|
||||||
|
layer.ShadowColor = Color.Transparent.ToCGColor();
|
||||||
|
layer.ShadowOpacity = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
22
Billing/Billing.iOS/Renderers/OptionEntryRenderer.cs
Normal file
@ -0,0 +1,22 @@
|
|||||||
|
using Billing.iOS.Renderers;
|
||||||
|
using Billing.UI;
|
||||||
|
using UIKit;
|
||||||
|
using Xamarin.Forms;
|
||||||
|
using Xamarin.Forms.Platform.iOS;
|
||||||
|
|
||||||
|
[assembly: ExportRenderer(typeof(OptionEntry), typeof(OptionEntryRenderer))]
|
||||||
|
namespace Billing.iOS.Renderers;
|
||||||
|
|
||||||
|
public class OptionEntryRenderer : EntryRenderer
|
||||||
|
{
|
||||||
|
protected override void OnElementChanged(ElementChangedEventArgs<Entry> e)
|
||||||
|
{
|
||||||
|
base.OnElementChanged(e);
|
||||||
|
|
||||||
|
var control = Control;
|
||||||
|
if (control != null)
|
||||||
|
{
|
||||||
|
control.BorderStyle = UITextBorderStyle.None;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
BIN
Billing/Billing.iOS/Resources/check.png
Normal file
After Width: | Height: | Size: 735 B |
BIN
Billing/Billing.iOS/Resources/check@2x.png
Normal file
After Width: | Height: | Size: 1.5 KiB |
BIN
Billing/Billing.iOS/Resources/check@3x.png
Normal file
After Width: | Height: | Size: 2.9 KiB |
BIN
Billing/Billing.iOS/Resources/ic_default.png
Normal file
After Width: | Height: | Size: 454 B |
BIN
Billing/Billing.iOS/Resources/ic_default@2x.png
Normal file
After Width: | Height: | Size: 969 B |
BIN
Billing/Billing.iOS/Resources/ic_default@3x.png
Normal file
After Width: | Height: | Size: 1.6 KiB |
Before Width: | Height: | Size: 588 B After Width: | Height: | Size: 588 B |
Before Width: | Height: | Size: 893 B After Width: | Height: | Size: 893 B |
Before Width: | Height: | Size: 1.4 KiB After Width: | Height: | Size: 1.4 KiB |