Adding iCloud and Yahoo as special IMAP handling scenario.

This commit is contained in:
Burak Kaan Köse
2025-01-19 23:52:27 +01:00
parent e0f87f1374
commit 05280dfd42
32 changed files with 244 additions and 106 deletions

Binary file not shown.

Before

Width:  |  Height:  |  Size: 12 KiB

After

Width:  |  Height:  |  Size: 4.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 31 KiB

Binary file not shown.

View File

@@ -98,6 +98,8 @@ namespace Wino.Core.UWP.Controls
{ WinoIconGlyph.EventRespond, "\uE924" },
{ WinoIconGlyph.EventReminder, "\uE923" },
{ WinoIconGlyph.EventJoinOnline, "\uE926" },
{ WinoIconGlyph.Yahoo, "\uE92B" },
{ WinoIconGlyph.Apple, "\uE92C" },
};
}
}

View File

@@ -99,6 +99,8 @@ namespace Wino.Core.UWP.Controls
EventReminder,
EventEditSeries,
EventJoinOnline,
Apple,
Yahoo
}
public class WinoFontIcon : FontIcon

View File

@@ -43,38 +43,83 @@
</ContentDialog.Resources>
<Grid MinWidth="400" RowSpacing="12">
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<Grid Visibility="{x:Bind IsProviderSelectionVisible, Mode=OneWay}">
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<!-- Account Name -->
<TextBox
x:Name="AccountNameTextbox"
Header="{x:Bind domain:Translator.NewAccountDialog_AccountName}"
PlaceholderText="{x:Bind domain:Translator.NewAccountDialog_AccountNamePlaceholder}"
TextChanged="AccountNameChanged" />
<!-- Account Name -->
<TextBox
x:Name="AccountNameTextbox"
Header="{x:Bind domain:Translator.NewAccountDialog_AccountName}"
PlaceholderText="{x:Bind domain:Translator.NewAccountDialog_AccountNamePlaceholder}"
TextChanged="InputChanged" />
<!--
TODO: Move Name, Sender Name and Color Picker to another Frame.
Provider selection should be first, then account details.
-->
<!--<Grid Grid.Row="1">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<TextBlock Text="Color" />
<muxc:ColorPicker x:Name="AccountColorPicker" Grid.Column="1" />
</Grid>-->
<!--
TODO: Move Name, Sender Name and Color Picker to another Frame.
Provider selection should be first, then account details.
-->
<!--<Grid Grid.Row="1">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<TextBlock Text="Color" />
<muxc:ColorPicker x:Name="AccountColorPicker" Grid.Column="1" />
</Grid>-->
<ListView
Grid.Row="2"
Padding="0"
ItemTemplate="{StaticResource NewMailProviderTemplate}"
ItemsSource="{x:Bind Providers}"
SelectedItem="{x:Bind SelectedMailProvider, Mode=TwoWay}"
SelectionMode="Single" />
<ListView
Grid.Row="2"
Padding="0"
ItemTemplate="{StaticResource NewMailProviderTemplate}"
ItemsSource="{x:Bind Providers}"
SelectedItem="{x:Bind SelectedMailProvider, Mode=TwoWay}"
SelectionMode="Single" />
</Grid>
<!-- Known special IMAP login details. -->
<Grid RowSpacing="12" Visibility="{x:Bind IsSpecialImapServerPartVisible, Mode=OneWay}">
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<Button Click="BackClicked">
<Button.Content>
<Viewbox Width="16">
<PathIcon Data="F1 M 20 9.375 C 20 9.544271 19.93815 9.690756 19.814453 9.814453 C 19.690754 9.938151 19.54427 10 19.375 10 L 2.138672 10 L 9.814453 17.685547 C 9.93815 17.809244 10 17.955729 10 18.125 C 10 18.294271 9.93815 18.440756 9.814453 18.564453 C 9.690755 18.68815 9.544271 18.75 9.375 18.75 C 9.205729 18.75 9.059244 18.68815 8.935547 18.564453 L 0.214844 9.84375 C 0.143229 9.772136 0.089518 9.700521 0.053711 9.628906 C 0.017904 9.557292 0 9.472656 0 9.375 C 0 9.277344 0.017904 9.192709 0.053711 9.121094 C 0.089518 9.049479 0.143229 8.977865 0.214844 8.90625 L 8.935547 0.185547 C 9.059244 0.06185 9.205729 0 9.375 0 C 9.544271 0 9.690755 0.06185 9.814453 0.185547 C 9.93815 0.309246 10 0.45573 10 0.625 C 10 0.794271 9.93815 0.940756 9.814453 1.064453 L 2.138672 8.75 L 19.375 8.75 C 19.54427 8.75 19.690754 8.81185 19.814453 8.935547 C 19.93815 9.059245 20 9.205729 20 9.375 Z " />
</Viewbox>
</Button.Content>
</Button>
<Image
Width="150"
Height="50"
HorizontalAlignment="Center"
Source="{x:Bind SelectedMailProvider.ProviderImage, Mode=OneWay}" />
<TextBox
x:Name="SpecialImapAddress"
Grid.Row="1"
TextChanged="InputChanged"
Header="E-mail Address"
PlaceholderText="eg. johndoe@testmail.com" />
<PasswordBox
x:Name="AppSpecificPassword"
PasswordChanged="ImapPasswordChanged"
Grid.Row="2"
Header="App-Specific Password" />
<HyperlinkButton
Grid.Row="3"
HorizontalAlignment="Right"
Click="AppSpecificHelpButtonClicked"
Content="How do I get app-specific password?" />
</Grid>
</Grid>
</ContentDialog>

View File

@@ -1,6 +1,9 @@
using System.Collections.Generic;
using System;
using System.Collections.Generic;
using Windows.System;
using Windows.UI.Xaml;
using Windows.UI.Xaml.Controls;
using Wino.Core.Domain.Enums;
using Wino.Core.Domain.Interfaces;
using Wino.Core.Domain.Models.Accounts;
@@ -8,6 +11,16 @@ namespace Wino.Core.UWP.Dialogs
{
public sealed partial class NewAccountDialog : ContentDialog
{
private Dictionary<SpecialImapProvider, string> helpingLinks = new Dictionary<SpecialImapProvider, string>()
{
{ SpecialImapProvider.iCloud, "https://support.apple.com/en-us/102654" },
{ SpecialImapProvider.Yahoo, "http://help.yahoo.com/kb/SLN15241.html" },
};
public static readonly DependencyProperty IsProviderSelectionVisibleProperty = DependencyProperty.Register(nameof(IsProviderSelectionVisible), typeof(bool), typeof(NewAccountDialog), new PropertyMetadata(true));
public static readonly DependencyProperty IsSpecialImapServerPartVisibleProperty = DependencyProperty.Register(nameof(IsSpecialImapServerPartVisible), typeof(bool), typeof(NewAccountDialog), new PropertyMetadata(false));
public static readonly DependencyProperty SelectedMailProviderProperty = DependencyProperty.Register(nameof(SelectedMailProvider), typeof(ProviderDetail), typeof(NewAccountDialog), new PropertyMetadata(null, new PropertyChangedCallback(OnSelectedProviderChanged)));
/// <summary>
/// Gets or sets current selected mail provider in the dialog.
/// </summary>
@@ -17,7 +30,18 @@ namespace Wino.Core.UWP.Dialogs
set { SetValue(SelectedMailProviderProperty, value); }
}
public static readonly DependencyProperty SelectedMailProviderProperty = DependencyProperty.Register(nameof(SelectedMailProvider), typeof(ProviderDetail), typeof(NewAccountDialog), new PropertyMetadata(null, new PropertyChangedCallback(OnSelectedProviderChanged)));
public bool IsProviderSelectionVisible
{
get { return (bool)GetValue(IsProviderSelectionVisibleProperty); }
set { SetValue(IsProviderSelectionVisibleProperty, value); }
}
public bool IsSpecialImapServerPartVisible
{
get { return (bool)GetValue(IsSpecialImapServerPartVisibleProperty); }
set { SetValue(IsSpecialImapServerPartVisibleProperty, value); }
}
// List of available mail providers for now.
@@ -49,12 +73,25 @@ namespace Wino.Core.UWP.Dialogs
if (IsSecondaryButtonEnabled)
{
Result = new AccountCreationDialogResult(SelectedMailProvider.Type, AccountNameTextbox.Text.Trim());
Hide();
if (SelectedMailProvider.SpecialImapProvider != SpecialImapProvider.None)
{
// This step requires app-sepcific password login for some providers.
args.Cancel = true;
IsProviderSelectionVisible = false;
IsSpecialImapServerPartVisible = true;
Validate();
}
else
{
Result = new AccountCreationDialogResult(SelectedMailProvider.Type, AccountNameTextbox.Text.Trim());
Hide();
}
}
}
private void AccountNameChanged(object sender, TextChangedEventArgs e) => Validate();
private void InputChanged(object sender, TextChangedEventArgs e) => Validate();
private void SenderNameChanged(object sender, TextChangedEventArgs e) => Validate();
private void Validate()
@@ -68,7 +105,8 @@ namespace Wino.Core.UWP.Dialogs
{
bool shouldEnable = SelectedMailProvider != null
&& SelectedMailProvider.IsSupported
&& !string.IsNullOrEmpty(AccountNameTextbox.Text);
&& !string.IsNullOrEmpty(AccountNameTextbox.Text)
&& (IsSpecialImapServerPartVisible ? (!string.IsNullOrEmpty(AppSpecificPassword.Password) && EmailValidation.EmailValidator.Validate(SpecialImapAddress.Text)) : true);
IsPrimaryButtonEnabled = shouldEnable;
}
@@ -79,5 +117,22 @@ namespace Wino.Core.UWP.Dialogs
}
private void DialogOpened(ContentDialog sender, ContentDialogOpenedEventArgs args) => Validate();
private void BackClicked(object sender, RoutedEventArgs e)
{
IsSpecialImapServerPartVisible = false;
IsProviderSelectionVisible = true;
Validate();
}
private void ImapPasswordChanged(object sender, RoutedEventArgs e) => Validate();
private async void AppSpecificHelpButtonClicked(object sender, RoutedEventArgs e)
{
var helpUrl = helpingLinks[SelectedMailProvider.SpecialImapProvider];
await Launcher.LaunchUriAsync(new Uri(helpUrl));
}
}
}

View File

@@ -11,6 +11,7 @@ using Windows.UI.Xaml.Controls.Primitives;
using Windows.UI.Xaml.Markup;
using Windows.UI.Xaml.Media;
using Wino.Core.Domain;
using Wino.Core.Domain.Entities.Shared;
using Wino.Core.Domain.Enums;
using Wino.Core.Domain.Models.MailItem;
using Wino.Core.UWP.Controls;
@@ -261,17 +262,31 @@ namespace Wino.Helpers
};
}
public static WinoIconGlyph GetProviderIcon(MailProviderType providerType)
public static WinoIconGlyph GetProviderIcon(MailProviderType providerType, SpecialImapProvider specialImapProvider)
{
return providerType switch
if (specialImapProvider == SpecialImapProvider.None)
{
MailProviderType.Outlook => WinoIconGlyph.Microsoft,
MailProviderType.Gmail => WinoIconGlyph.Google,
MailProviderType.Office365 => WinoIconGlyph.Microsoft,
MailProviderType.IMAP4 => WinoIconGlyph.IMAP,
_ => WinoIconGlyph.None,
};
return providerType switch
{
MailProviderType.Outlook => WinoIconGlyph.Microsoft,
MailProviderType.Gmail => WinoIconGlyph.Google,
MailProviderType.IMAP4 => WinoIconGlyph.IMAP,
_ => WinoIconGlyph.None,
};
}
else
{
return specialImapProvider switch
{
SpecialImapProvider.iCloud => WinoIconGlyph.Apple,
SpecialImapProvider.Yahoo => WinoIconGlyph.Yahoo,
_ => WinoIconGlyph.None,
};
}
}
public static WinoIconGlyph GetProviderIcon(MailAccount account)
=> GetProviderIcon(account.ProviderType, account.SpecialImapProvider);
public static Geometry GetPathGeometry(string pathMarkup)
{

View File

@@ -29,7 +29,7 @@
Header="{x:Bind Account.Name}"
IsClickEnabled="True">
<winuiControls:SettingsCard.HeaderIcon>
<coreControls:WinoFontIcon FontSize="64" Icon="{x:Bind helpers:XamlHelpers.GetProviderIcon(ProviderDetail.Type)}" />
<coreControls:WinoFontIcon FontSize="64" Icon="{x:Bind helpers:XamlHelpers.GetProviderIcon(Account)}" />
</winuiControls:SettingsCard.HeaderIcon>
</winuiControls:SettingsCard>
</DataTemplate>

View File

@@ -215,6 +215,9 @@
<PackageReference Include="CommunityToolkit.Uwp.Controls.TabbedCommandBar">
<Version>8.1.240916</Version>
</PackageReference>
<PackageReference Include="EmailValidation">
<Version>1.2.0</Version>
</PackageReference>
<PackageReference Include="Microsoft.AppCenter.Analytics">
<Version>5.0.6</Version>
</PackageReference>
@@ -262,6 +265,7 @@
</SDKReference>
</ItemGroup>
<ItemGroup>
<Content Include="Assets\Providers\iCloud.png" />
<Content Include="Assets\WinoIcons.ttf" />
</ItemGroup>
<ItemGroup>