Initial version.

This commit is contained in:
Oliver Hauff 2021-05-13 20:03:07 +02:00
parent 193aaa1a56
commit b72c67a53e
228 changed files with 25924 additions and 0 deletions

View file

@ -0,0 +1,155 @@
using System;
using System.Collections.Generic;
using TINK.View;
using Xamarin.Forms;
namespace TINK.ViewModel.Info.BikeInfo
{
public class BikeInfoViewModel
{
/// <summary>
/// Reference on view servcie to show modal notifications and to perform navigation.
/// </summary>
private readonly IViewService m_oViewService;
/// <param name="p_oViewService">Interface to actuate methodes on GUI.</param>
public BikeInfoViewModel(Func<string, ImageSource> imageSourceFunc, IViewService p_oViewService)
{
m_oViewService = p_oViewService
?? throw new ArgumentException("Can not instantiate bike info page view model- object. No view available.");
CarouselItems = new List<CourouselPageItemViewModel>();
CarouselItems.Add(
new CourouselPageItemViewModel(
"Anleitung Benutzung Lastenräder",
$"Diese Anleitung wird einmalig nach der Anmeldung angezeigt.\r\nZum Blättern auf die nächste Seite bitte nach links wischen.\r\nNach Anzeige aller Seiten kann die Anleitung geschlossen werden.",
CarouselItems.Count + 1,
() => CarouselItems.Count,
() => CloseAction()));
CarouselItems.Add(
new CourouselPageItemViewModel(
"Zweirädriges TINK Rad: Hochklappen des Fahrradständers (1/3)",
"So abgestellt hat das zweirädrige Transportrad einen sicheren Stand.",
CarouselItems.Count + 1,
() => CarouselItems.Count,
() => CloseAction(),
imageSourceFunc("trike_stand1_image.4HJ5PY_679_382.png")));
CarouselItems.Add(
new CourouselPageItemViewModel(
"Zweirädriges TINK Rad: Hochklappen des Fahrradständers (2/3)",
"Zum Weiterfahren das Transportrad nach vorne bewegen, bis kein Gewicht mehr auf dem Fahrradständer liegt.",
CarouselItems.Count + 1,
() => CarouselItems.Count,
() => CloseAction(),
imageSourceFunc("trike_stand2_image.RIX2PY_679_382.png")));
CarouselItems.Add(
new CourouselPageItemViewModel(
"Zweirädriges TINK Rad: Hochklappen des Fahrradständers (3/3).",
"Den Fahrradständer mit dem Fuß nach oben drücken, bis er hörbar am Magneten (Pfeil) einrastet. So fällt er unterwegs nicht herunter.",
CarouselItems.Count + 1,
() => CarouselItems.Count,
() => CloseAction(),
imageSourceFunc("trike_stand3_image.FDR7PY_679_382.png")));
CarouselItems.Add(
new CourouselPageItemViewModel(
"Dreirädriges TINK Rad: Lösen und Aktivieren der Feststellbremse (1/3).",
"Die Feststellbremse ist der graue Stift, der aus der Bremse herausragt. Ist sie aktiv, kann das Dreirad nicht wegrollen.",
CarouselItems.Count + 1,
() => CarouselItems.Count,
() => CloseAction(),
imageSourceFunc("trike_brake1_image.HZ17PY_678_382.png")));
CarouselItems.Add(
new CourouselPageItemViewModel(
"Dreirädriges TINK Rad: Lösen und Aktivieren der Feststellbremse (2/3).",
"Lösen der Feststellbremse: Die Bremse vollständig anziehen, bis der Stift wieder auf seine ursprüngliche Position herausspringt.",
CarouselItems.Count + 1,
() => CarouselItems.Count,
() => CloseAction(),
imageSourceFunc("trike_brake2_image.1YBAQY_679_382.png")));
CarouselItems.Add(
new CourouselPageItemViewModel(
"Dreirädriges TINK Rad: Lösen und Aktivieren der Feststellbremse (3/3).",
"Aktivieren der Feststellbremse: Die Bremse vollständig anziehen und den Stift hineindrücken.",
CarouselItems.Count + 1,
() => CarouselItems.Count,
() => CloseAction(),
imageSourceFunc("trike_brake3_image.FJM2PY_679_382.png")));
CarouselItems.Add(
new CourouselPageItemViewModel(
"Höhenregulierung des Sattels (1/3).",
"Hier im Bild ist der Hebel zum Einstellen des Sattels zu sehen.",
CarouselItems.Count + 1,
() => CarouselItems.Count,
() => CloseAction(),
imageSourceFunc("seat1_image.ZQ65PY_680_382.png")));
CarouselItems.Add(
new CourouselPageItemViewModel(
"Höhenregulierung des Sattels (2/3).",
"Durch Drücken des Hebels ist die Sattelhöhe frei verstellbar. Vergleichbar mit einem Bürostuhl bewegt sich der Sattel automatisch nach oben.",
CarouselItems.Count + 1,
() => CarouselItems.Count,
() => CloseAction(),
imageSourceFunc("seat2_image.QQZCQY_679_382.png")));
CarouselItems.Add(
new CourouselPageItemViewModel(
"Höhenregulierung des Sattels (3/3).",
"Durch kräftiges Herunterdrücken des Sattels (und gleichzeitigem Betätigen des Hebels) kann der Sattel nach unten verstellt werden. Tipp: Eventuell draufsetzen und dann den Hebel betätigen, um den Sattel nach unten zu drücken.",
CarouselItems.Count + 1,
() => CarouselItems.Count,
() => CloseAction(),
imageSourceFunc("seat3_image.NQ5FQY_679_382.png")));
CarouselItems.Add(
new CourouselPageItemViewModel(
"Verbinden des Kindergurts (1/3).",
"Der Gurt besteht aus drei Einzelteilen. Zunächst die oberen beiden Einzelstücke nehmen.",
CarouselItems.Count + 1,
() => CarouselItems.Count,
() => CloseAction(),
imageSourceFunc("belt1_image.4XWCQY_679_382.png")));
CarouselItems.Add(
new CourouselPageItemViewModel(
"Verbinden des Kindergurts (2/3).",
"Die beiden Einzelstücke zusammenfügen.",
CarouselItems.Count + 1,
() => CarouselItems.Count,
() => CloseAction(),
imageSourceFunc("belt2_image.X3F1PY_679_382.png")));
CarouselItems.Add(
new CourouselPageItemViewModel(
"Verbinden des Kindergurts (3/3).",
"Das obere und untere Teilstück verbinden (bis zum Einrasten). Lösen der Teilstücke durch Drücken auf den roten Knopf.",
CarouselItems.Count + 1,
() => CarouselItems.Count,
() => CloseAction(),
imageSourceFunc("belt3_image.DYOXPY_679_382.png")));
}
/// <summary> Gets the carousel page items</summary>
public IList<CourouselPageItemViewModel> CarouselItems { get; }
/// <summary>
/// Commang object to bind login button to view model.
/// </summary>
private Action CloseAction
{
get
{
return () => m_oViewService.ShowPage(ViewTypes.MapPage);
}
}
}
}

View file

@ -0,0 +1,81 @@
using System;
using System.Windows.Input;
using Xamarin.Forms;
namespace TINK.ViewModel.Info.BikeInfo
{
public class CourouselPageItemViewModel
{
public CourouselPageItemViewModel(
string p_strTitle,
string p_strLegend,
int p_iCurrentPageIndex,
Func<int> p_iPagesCountProvider,
Action p_oCloseAction,
ImageSource image = null)
{
Title = p_strTitle;
IsImageVisble = image != null;
if (IsImageVisble)
{
Image = image;
}
DescriptionText = p_strLegend;
CurrentPageIndex = p_iCurrentPageIndex;
PagesCountProvider = p_iPagesCountProvider;
CloseAction = p_oCloseAction;
}
/// <summary> Gets the title of the navigation page. </summary>
public string Title { get; }
public bool IsImageVisble { get; }
/// <summary> Gets the image. </summary>
public ImageSource Image { get; }
/// <summary> Gets the text which describes the image. </summary>
public string DescriptionText { get; }
/// <summary> Get the progress of the carousselling progress.</summary>
public double ProgressValue
{
get
{
var l_oCount = PagesCountProvider();
return l_oCount > 0 ? (double)CurrentPageIndex / l_oCount : 0;
}
}
/// <summary> Gets if user can leave carousel page.</summary>
public bool IsCloseVisible
{
get
{
return PagesCountProvider() == CurrentPageIndex;
}
}
/// <summary>
/// Commang object to bind login button to view model.
/// </summary>
public ICommand OnCloseRequest
{
get
{
return new Command(() => CloseAction());
}
}
/// <summary> Returns one based index of the current page. </summary>
private int CurrentPageIndex { get; }
/// <summary> Gets the count of carousel pages. </summary>
private Func<int> PagesCountProvider { get; }
/// <summary> Action to actuate when close is invoked. </summary>
private Action CloseAction { get; }
}
}

View file

@ -0,0 +1,131 @@
using System;
using System.ComponentModel;
using System.Threading.Tasks;
using TINK.Model.Device;
using TINK.Services.CopriApi.ServerUris;
using Xamarin.Essentials;
using Xamarin.Forms;
namespace TINK.ViewModel.Info
{
/// <summary> Manges the tabbed info page. </summary>
public class InfoViewModel : INotifyPropertyChanged
{
/// <summary> Fired whenever a property changed.</summary>
public event PropertyChangedEventHandler PropertyChanged;
/// <summary> Holds the name of the host.</summary>
private string HostName { get; }
/// <summary> Holds value wether site caching is on or off.</summary>
bool IsSiteCachingOn { get; }
/// <summary> Constructs Info view model</summary>
/// <param name="isSiteCachingOn">Holds value wether site caching is on or off.</param>
/// <param name="resourceProvider">Delegate to get an an embedded html ressource. Used as fallback if download from web page does not work and cache is empty.</param>
public InfoViewModel(
string hostName,
bool isSiteCachingOn,
Func<string, string> resourceProvider)
{
HostName = hostName;
IsSiteCachingOn = isSiteCachingOn;
InfoAgb = new HtmlWebViewSource { Html = "<html>Loading...</html>" };
ResourceProvider = resourceProvider
?? throw new ArgumentException($"Can not instantiate {typeof(InfoViewModel)}-object. No ressource provider availalbe.");
}
/// <summary> Called when page is shown. </summary>
public async void OnAppearing()
{
InfoAgb = await GetAgb(HostName, IsSiteCachingOn, ResourceProvider);
InfoPrivacy = new HtmlWebViewSource
{
Html = await ViewModelHelper.GetSource(
$"https://{HostName}/{HostName.GetPrivacyResource()}",
IsSiteCachingOn,
HostName.GetIsCopri() ? () => ResourceProvider("HtmlResouces.V02.InfoDatenschutz.html") : (Func<string>) null) /* offline resources only available for TINK */,
};
InfoImpressum = new HtmlWebViewSource
{
Html = HostName.GetIsCopri()
? ResourceProvider("HtmlResouces.V02.InfoImpressum.html")
: await ViewModelHelper.GetSource($"https://{HostName}/{CopriHelper.SHAREE_SILTEFOLDERNAME}/impress.html", IsSiteCachingOn)
};
}
/// <summary> Gets the AGBs</summary>
/// <param name="resourceProvider"></param>
/// <returns> AGBs</returns>
public static async Task<HtmlWebViewSource> GetAgb(
string hostName,
bool isSiteCachingOn,
Func<string, string> resourceProvider)
{
return new HtmlWebViewSource
{
Html = await ViewModelHelper.GetSource(
$"https://{hostName}/{hostName.GetAGBResource()}",
isSiteCachingOn,
hostName.GetIsCopri() ? () => resourceProvider("HtmlResouces.V02.InfoAGB.html") : (Func<string>) null) /* offline resources only available for TINK */,
};
}
/// <summary> Gets the platfrom specific prefix. </summary>
private Func<string, string> ResourceProvider { get; set; }
/// <summary> Gets the app related information (app version and licenses). </summary>
public HtmlWebViewSource InfoLicenses => new HtmlWebViewSource
{
Html = ResourceProvider("HtmlResouces.V02.InfoLicenses.html")
.Replace("CURRENT_VERSION_TINKAPP", DependencyService.Get<IAppInfo>().Version.ToString())
.Replace("ACTIVE_APPNAME", AppInfo.Name)
};
/// <summary> Privacy text.</summary>
private HtmlWebViewSource infoImpress;
/// <summary> Gets the privacy related information. </summary>
public HtmlWebViewSource InfoImpressum
{
get => infoImpress;
set
{
infoImpress = value;
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(nameof(InfoImpressum)));
}
}
/// <summary> Agb information text.</summary>
private HtmlWebViewSource infoAgb;
/// <summary> Privacy text.</summary>
private HtmlWebViewSource infoPrivacy;
/// <summary> Agb information text.</summary>
public HtmlWebViewSource InfoAgb
{
get => infoAgb;
set
{
infoAgb = value;
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(nameof(InfoAgb)));
}
}
/// <summary> Agb information text.</summary>
public HtmlWebViewSource InfoPrivacy
{
get => infoPrivacy;
set
{
infoPrivacy = value;
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(nameof(InfoPrivacy)));
}
}
}
}