add openhack files

This commit is contained in:
Ryan Peters
2022-11-03 16:41:13 -04:00
commit b2c9f7e29f
920 changed files with 118861 additions and 0 deletions

View File

@ -0,0 +1,442 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT license. See LICENSE file in the project root for details.
using System;
using System.Globalization;
using System.Collections.Generic;
using System.Threading.Tasks;
using CoreAnimation;
using CoreLocation;
using Foundation;
using MapKit;
using UIKit;
using MyDriving.DataObjects;
using MyDriving.ViewModel;
using Plugin.Permissions;
using Plugin.Permissions.Abstractions;
using MyDriving.Utils;
using Microsoft.WindowsAzure.MobileServices;
using MyDriving.iOS.Helpers;
using MyDriving.AzureClient;
namespace MyDriving.iOS
{
partial class CurrentTripViewController : UIViewController
{
CarAnnotation currentLocationAnnotation;
TripMapViewDelegate mapDelegate;
List<CLLocationCoordinate2D> route;
public CurrentTripViewController(IntPtr handle) : base(handle)
{
}
public CurrentTripViewModel CurrentTripViewModel { get; set; }
public PastTripsDetailViewModel PastTripsDetailViewModel { get; set; }
public override async void ViewDidLoad()
{
base.ViewDidLoad();
NavigationItem.RightBarButtonItem = null;
if (PastTripsDetailViewModel == null)
await ConfigureCurrentTripUserInterface();
else
await ConfigurePastTripUserInterface();
}
public override async void ViewDidAppear(bool animated)
{
base.ViewDidAppear(animated);
PopRecordButtonAnimation();
if (CurrentTripViewModel != null)
{
await CurrentTripViewModel.ExecuteStartTrackingTripCommandAsync().ContinueWith(async (task) =>
{
// If we don't have permission from the user, prompt a dialog requesting permission.
await PromptPermissionsChangeDialog();
});
if (!CurrentTripViewModel.Geolocator.IsGeolocationEnabled)
{
tripMapView.Camera.CenterCoordinate = new CLLocationCoordinate2D(47.6204, -122.3491);
tripMapView.Camera.Altitude = 5000;
}
}
}
#region Current Trip User Interface Logic
async Task ConfigureCurrentTripUserInterface()
{
// Configure map
mapDelegate = new TripMapViewDelegate(true);
tripMapView.Delegate = mapDelegate;
tripMapView.ShowsUserLocation = false;
tripMapView.Camera.Altitude = 5000;
// Setup record button
recordButton.Hidden = false;
recordButton.Layer.CornerRadius = recordButton.Frame.Width/2;
recordButton.Layer.MasksToBounds = true;
recordButton.Layer.BorderColor = UIColor.White.CGColor;
recordButton.Layer.BorderWidth = 0;
recordButton.TouchUpInside += RecordButton_TouchUpInside;
// Hide slider
tripSlider.Hidden = true;
wayPointA.Hidden = true;
wayPointB.Hidden = true;
UpdateRecordButton(false);
tripInfoView.Alpha = 0;
ResetTripInfoView();
CurrentTripViewModel = new CurrentTripViewModel();
CurrentTripViewModel.Geolocator.PositionChanged += Geolocator_PositionChanged;
}
void AnimateTripInfoView()
{
tripInfoView.FadeIn(0.3, 0);
}
void ResetMapViewState()
{
InvokeOnMainThread(() =>
{
route = null;
tripMapView.RemoveAnnotations(tripMapView.Annotations);
if (tripMapView.Overlays != null && tripMapView.Overlays.Length > 0)
{
tripMapView.RemoveOverlays(tripMapView.Overlays[0]);
}
});
}
void ResetTripInfoView()
{
labelOneValue.Text = "N/A";
labelTwoValue.Text = "0";
labelThreeValue.Text = "0:00";
labelFourValue.Text = "N/A";
}
void UpdateRecordButton(bool isRecording)
{
//Corner Radius
var radiusAnimation = CABasicAnimation.FromKeyPath("cornerRadius");
radiusAnimation.TimingFunction = CAMediaTimingFunction.FromName(CAMediaTimingFunction.EaseIn);
radiusAnimation.From = NSNumber.FromNFloat(recordButton.Layer.CornerRadius);
//Border Thickness
var borderAnimation = CABasicAnimation.FromKeyPath("borderWidth");
borderAnimation.TimingFunction = CAMediaTimingFunction.FromName(CAMediaTimingFunction.EaseIn);
radiusAnimation.From = NSNumber.FromNFloat(recordButton.Layer.BorderWidth);
//Animation Group
var animationGroup = CAAnimationGroup.CreateAnimation();
animationGroup.Animations = new CAAnimation[] {radiusAnimation, borderAnimation};
animationGroup.Duration = 0.6;
animationGroup.FillMode = CAFillMode.Forwards;
recordButton.Layer.CornerRadius = isRecording ? 4 : recordButton.Frame.Width/2;
recordButton.Layer.BorderWidth = isRecording ? 2 : 3;
recordButton.Layer.AddAnimation(animationGroup, "borderChanges");
}
async Task PromptPermissionsChangeDialog()
{
var status = await CrossPermissions.Current.CheckPermissionStatusAsync(Permission.Location);
if (status == PermissionStatus.Denied)
{
InvokeOnMainThread(() =>
{
var alertController = UIAlertController.Create("Location Permission Denied",
"Tracking your location is required to record trips. Visit the Settings app to change the permission status.",
UIAlertControllerStyle.Alert);
alertController.AddAction(UIAlertAction.Create("Change Permission", UIAlertActionStyle.Default,
obj =>
{
var url = NSUrl.FromString(UIApplication.OpenSettingsUrlString);
UIApplication.SharedApplication.OpenUrl(url);
}));
alertController.AddAction(UIAlertAction.Create("OK", UIAlertActionStyle.Cancel, null));
PresentViewController(alertController, true, null);
tripMapView.Camera.CenterCoordinate = new CLLocationCoordinate2D(47.6204, -122.3491);
tripMapView.Camera.Altitude = 5000;
});
}
}
async void RecordButton_TouchUpInside(object sender, EventArgs e)
{
if (!CurrentTripViewModel.Geolocator.IsGeolocationEnabled)
{
Acr.UserDialogs.UserDialogs.Instance.Alert(
"Please ensure that geolocation is enabled and permissions are allowed for MyDriving to start a recording.",
"Geolocation Disabled", "OK");
return;
}
if (!CurrentTripViewModel.IsRecording)
{
if (!await CurrentTripViewModel.StartRecordingTrip())
return;
UpdateRecordButton(true);
ResetTripInfoView();
AnimateTripInfoView();
if (CurrentTripViewModel.CurrentTrip.HasSimulatedOBDData)
NavigationItem.Title = "Current Trip (Sim OBD)";
var endpoint = "A";
var annotation = new WaypointAnnotation(CurrentTripViewModel.CurrentPosition.ToCoordinate(), endpoint);
tripMapView.AddAnnotation(annotation);
}
else
{
if (await CurrentTripViewModel.StopRecordingTrip())
{
ResetMapViewState();
InvokeOnMainThread(delegate
{
mapDelegate = new TripMapViewDelegate(true);
tripMapView.Delegate = mapDelegate;
});
UpdateRecordButton(false);
tripInfoView.Alpha = 0;
NavigationItem.Title = "Current Trip";
await CurrentTripViewModel.SaveRecordingTripAsync();
var vc =
Storyboard.InstantiateViewController("tripSummaryViewController") as TripSummaryViewController;
vc.ViewModel = CurrentTripViewModel;
PresentModalViewController(vc, true);
}
}
}
void Geolocator_PositionChanged(object sender, Plugin.Geolocator.Abstractions.PositionEventArgs e)
{
var coordinate = e.Position.ToCoordinate();
UpdateCarAnnotationPosition(coordinate);
if (CurrentTripViewModel.IsRecording)
{
// Update trip information
labelOneValue.Text = CurrentTripViewModel.FuelConsumption;
labelOneTitle.Text = CurrentTripViewModel.FuelConsumptionUnits;
labelThreeValue.Text = CurrentTripViewModel.ElapsedTime;
labelTwoValue.Text = CurrentTripViewModel.CurrentTrip.Distance.ToString("F");
labelTwoTitle.Text =
CultureInfo.CurrentCulture.TextInfo.ToTitleCase(CurrentTripViewModel.CurrentTrip.Units.ToLower());
labelFourValue.Text = CurrentTripViewModel.EngineLoad;
// If we already haven't starting tracking route yet, start that.
if (route == null)
StartTrackingRoute(coordinate);
// Draw from last known coordinate to new coordinate.
else
DrawNewRouteWaypoint(coordinate);
}
}
void StartTrackingRoute(CLLocationCoordinate2D coordinate)
{
route = new List<CLLocationCoordinate2D>();
var count = CurrentTripViewModel.CurrentTrip.Points.Count;
if (count == 0)
{
route.Add(coordinate);
}
else
{
var firstPoint = CurrentTripViewModel.CurrentTrip.Points?[0];
var firstCoordinate = new CLLocationCoordinate2D(firstPoint.Latitude, firstPoint.Longitude);
route.Add(firstCoordinate);
}
}
#endregion
#region Past Trip User Interface Logic
async Task ConfigurePastTripUserInterface()
{
NavigationItem.Title = PastTripsDetailViewModel.Title;
sliderView.Hidden = false;
tripSlider.Hidden = false;
wayPointA.Layer.CornerRadius = wayPointA.Frame.Width / 2;
wayPointA.Layer.BorderWidth = 2;
wayPointA.Layer.BorderColor = UIColor.White.CGColor;
wayPointB.Layer.CornerRadius = wayPointB.Frame.Width / 2;
wayPointB.Layer.BorderWidth = 2;
wayPointB.Layer.BorderColor = UIColor.White.CGColor;
var success = await PastTripsDetailViewModel.ExecuteLoadTripCommandAsync(PastTripsDetailViewModel.Trip.Id);
if(!success)
{
NavigationController.PopViewController(true);
return;
}
// Setup map
mapDelegate = new TripMapViewDelegate(false);
tripMapView.Delegate = mapDelegate;
tripMapView.ShowsUserLocation = false;
if (PastTripsDetailViewModel.Trip == null || PastTripsDetailViewModel.Trip.Points == null || PastTripsDetailViewModel.Trip.Points.Count == 0)
return;
var coordinateCount = PastTripsDetailViewModel.Trip.Points.Count;
// Draw endpoints
var startEndpoint = new WaypointAnnotation(PastTripsDetailViewModel.Trip.Points[0].ToCoordinate(), "A");
tripMapView.AddAnnotation(startEndpoint);
var endEndpoint =
new WaypointAnnotation(PastTripsDetailViewModel.Trip.Points[coordinateCount - 1].ToCoordinate(), "B");
tripMapView.AddAnnotation(endEndpoint);
// Draw route
tripMapView.DrawRoute(PastTripsDetailViewModel.Trip.Points.ToCoordinateArray());
// Draw car
var carCoordinate = PastTripsDetailViewModel.Trip.Points[0];
currentLocationAnnotation = new CarAnnotation(carCoordinate.ToCoordinate(), UIColor.Blue);
tripMapView.AddAnnotation(currentLocationAnnotation);
// Configure slider area
ConfigureSlider();
ConfigureWayPointButtons();
ConfigurePoiAnnotations();
recordButton.Hidden = true;
tripMapView.SetVisibleMapRect(
MKPolyline.FromCoordinates(PastTripsDetailViewModel.Trip.Points.ToCoordinateArray()).BoundingMapRect,
new UIEdgeInsets(25, 25, 25, 25), false);
tripMapView.CenterCoordinate = carCoordinate.ToCoordinate();
UpdateTripStatistics(carCoordinate);
NSNotificationCenter.DefaultCenter.AddObserver(new NSString("RefreshTripUnits"), HandleTripUnitsChanged);
}
void HandleTripUnitsChanged(NSNotification obj)
{
UpdateTripStatistics(PastTripsDetailViewModel.CurrentPosition);
}
void UpdateTripStatistics(TripPoint point)
{
PastTripsDetailViewModel.CurrentPosition = point;
labelOneTitle.Text = PastTripsDetailViewModel.FuelConsumptionUnits;
labelOneValue.Text = PastTripsDetailViewModel.FuelConsumption;
labelTwoTitle.Text = PastTripsDetailViewModel.DistanceUnits;
labelTwoValue.Text = PastTripsDetailViewModel.Distance;
labelThreeTitle.Text = "Elapsed Time";
labelThreeValue.Text = PastTripsDetailViewModel.ElapsedTime;
labelFourTitle.Text = PastTripsDetailViewModel.SpeedUnits;
labelFourValue.Text = PastTripsDetailViewModel.Speed;
}
void ConfigureSlider()
{
tripSlider.MinValue = 0;
tripSlider.MaxValue = PastTripsDetailViewModel.Trip.Points.Count - 1;
tripSlider.Value = 0;
tripSlider.ValueChanged += TripSlider_ValueChanged;
}
void ConfigureWayPointButtons()
{
startTimeLabel.Hidden = false;
endTimeLabel.Hidden = false;
startTimeLabel.Text = PastTripsDetailViewModel.Trip.StartTimeDisplay;
endTimeLabel.Text = PastTripsDetailViewModel.Trip.EndTimeDisplay;
wayPointA.TouchUpInside += delegate
{
tripSlider.Value = 0;
TripSlider_ValueChanged(this, null);
};
wayPointB.TouchUpInside += delegate
{
tripSlider.Value = tripSlider.MaxValue;
TripSlider_ValueChanged(this, null);
};
}
void ConfigurePoiAnnotations()
{
foreach (var poi in PastTripsDetailViewModel.POIs)
{
var poiAnnotation = new PoiAnnotation(poi, poi.ToCoordinate());
tripMapView.AddAnnotation(poiAnnotation);
}
}
void TripSlider_ValueChanged(object sender, EventArgs e)
{
var value = (int) tripSlider.Value;
var tripPoint = PastTripsDetailViewModel.Trip.Points[value];
UpdateCarAnnotationPosition(tripPoint.ToCoordinate());
UpdateTripStatistics(tripPoint);
}
void PopRecordButtonAnimation()
{
if (recordButton.Hidden && PastTripsDetailViewModel == null)
recordButton.Pop(0.5, 0, 1);
}
#endregion
#region Shared User Interface Logic
void UpdateCarAnnotationPosition(CLLocationCoordinate2D coordinate)
{
if (currentLocationAnnotation != null)
tripMapView.RemoveAnnotation(currentLocationAnnotation);
var color = CurrentTripViewModel != null && CurrentTripViewModel.IsRecording ? UIColor.Red : UIColor.Blue;
currentLocationAnnotation = new CarAnnotation(coordinate, color);
tripMapView.AddAnnotation(currentLocationAnnotation);
tripMapView.Camera.CenterCoordinate = coordinate;
}
void DrawNewRouteWaypoint(CLLocationCoordinate2D coordinate)
{
route.Add(coordinate);
if (tripMapView.Overlays != null)
tripMapView.RemoveOverlays(tripMapView.Overlays);
tripMapView.DrawRoute(route.ToArray());
}
#endregion
}
}

View File

@ -0,0 +1,173 @@
// WARNING
//
// This file has been generated automatically by Visual Studio from the outlets and
// actions declared in your storyboard file.
// Manual changes to this file will not be maintained.
//
using Foundation;
using System;
using System.CodeDom.Compiler;
using UIKit;
namespace MyDriving.iOS
{
[Register ("CurrentTripViewController")]
partial class CurrentTripViewController
{
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UILabel endTimeLabel { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UILabel labelFourTitle { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UILabel labelFourValue { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UILabel labelOneTitle { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UILabel labelOneValue { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UILabel labelThreeTitle { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UILabel labelThreeValue { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UILabel labelTwoTitle { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UILabel labelTwoValue { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UIButton recordButton { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UIView sliderView { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UILabel startTimeLabel { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UIView tripInfoView { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
MyDriving.iOS.TripMapView tripMapView { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UISlider tripSlider { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UIButton wayPointA { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UIButton wayPointB { get; set; }
void ReleaseDesignerOutlets ()
{
if (endTimeLabel != null) {
endTimeLabel.Dispose ();
endTimeLabel = null;
}
if (labelFourTitle != null) {
labelFourTitle.Dispose ();
labelFourTitle = null;
}
if (labelFourValue != null) {
labelFourValue.Dispose ();
labelFourValue = null;
}
if (labelOneTitle != null) {
labelOneTitle.Dispose ();
labelOneTitle = null;
}
if (labelOneValue != null) {
labelOneValue.Dispose ();
labelOneValue = null;
}
if (labelThreeTitle != null) {
labelThreeTitle.Dispose ();
labelThreeTitle = null;
}
if (labelThreeValue != null) {
labelThreeValue.Dispose ();
labelThreeValue = null;
}
if (labelTwoTitle != null) {
labelTwoTitle.Dispose ();
labelTwoTitle = null;
}
if (labelTwoValue != null) {
labelTwoValue.Dispose ();
labelTwoValue = null;
}
if (recordButton != null) {
recordButton.Dispose ();
recordButton = null;
}
if (sliderView != null) {
sliderView.Dispose ();
sliderView = null;
}
if (startTimeLabel != null) {
startTimeLabel.Dispose ();
startTimeLabel = null;
}
if (tripInfoView != null) {
tripInfoView.Dispose ();
tripInfoView = null;
}
if (tripMapView != null) {
tripMapView.Dispose ();
tripMapView = null;
}
if (tripSlider != null) {
tripSlider.Dispose ();
tripSlider = null;
}
if (wayPointA != null) {
wayPointA.Dispose ();
wayPointA = null;
}
if (wayPointB != null) {
wayPointB.Dispose ();
wayPointB = null;
}
}
}
}

View File

@ -0,0 +1,48 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT license. See LICENSE file in the project root for details.
using System;
using UIKit;
namespace MyDriving.iOS
{
public partial class TripSummaryViewController : UIViewController
{
public TripSummaryViewController(IntPtr handle) : base(handle)
{
}
public ViewModel.CurrentTripViewModel ViewModel { get; set; }
public override void ViewDidLoad()
{
lblDateTime.Text = $"{DateTime.Now.ToString("M")} {DateTime.Now.ToString("t")}";
lblDistance.Text = ViewModel.TripSummary.TotalDistanceDisplay;
lblDuration.Text = ViewModel.TripSummary.TotalTimeDisplay;
lblFuelConsumed.Text = ViewModel.TripSummary.FuelDisplay;
lblTopSpeed.Text = ViewModel.TripSummary.MaxSpeedDisplay;
lblDistance.Alpha = 0;
lblDuration.Alpha = 0;
lblTopSpeed.Alpha = 0;
lblFuelConsumed.Alpha = 0;
lblTopSpeed.Alpha = 0;
}
public override void ViewDidAppear(bool animated)
{
base.ViewDidAppear(animated);
lblDistance.FadeIn(0.4, 0.1f);
lblDuration.FadeIn(0.4, 0.2f);
lblTopSpeed.FadeIn(0.4, 0.3f);
lblFuelConsumed.FadeIn(0.4, 0.4f);
lblTopSpeed.FadeIn(0.4, 0.5f);
}
async partial void BtnClose_TouchUpInside(UIButton sender)
{
await DismissViewControllerAsync(true);
}
}
}

View File

@ -0,0 +1,78 @@
// WARNING
//
// This file has been generated automatically by Visual Studio from the outlets and
// actions declared in your storyboard file.
// Manual changes to this file will not be maintained.
//
using Foundation;
using System;
using System.CodeDom.Compiler;
using UIKit;
namespace MyDriving.iOS
{
[Register ("TripSummaryViewController")]
partial class TripSummaryViewController
{
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UIButton btnClose { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UILabel lblDateTime { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UILabel lblDistance { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UILabel lblDuration { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UILabel lblFuelConsumed { get; set; }
[Outlet]
[GeneratedCode ("iOS Designer", "1.0")]
UIKit.UILabel lblTopSpeed { get; set; }
[Action ("BtnClose_TouchUpInside:")]
[GeneratedCode ("iOS Designer", "1.0")]
partial void BtnClose_TouchUpInside (UIKit.UIButton sender);
void ReleaseDesignerOutlets ()
{
if (btnClose != null) {
btnClose.Dispose ();
btnClose = null;
}
if (lblDateTime != null) {
lblDateTime.Dispose ();
lblDateTime = null;
}
if (lblDistance != null) {
lblDistance.Dispose ();
lblDistance = null;
}
if (lblDuration != null) {
lblDuration.Dispose ();
lblDuration = null;
}
if (lblFuelConsumed != null) {
lblFuelConsumed.Dispose ();
lblFuelConsumed = null;
}
if (lblTopSpeed != null) {
lblTopSpeed.Dispose ();
lblTopSpeed = null;
}
}
}
}

View File

@ -0,0 +1,152 @@
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT license. See LICENSE file in the project root for details.
using System;
using CoreGraphics;
using Foundation;
using ObjCRuntime;
using UIKit;
using MyDriving.ViewModel;
using SDWebImage;
namespace MyDriving.iOS
{
public partial class TripsTableViewController : UITableViewController
{
const string TripCellWithImageIdentifier = "TRIP_CELL_WITHIMAGE_IDENTIFIER";
const string TripCellIdentifier = "TRIP_CELL_IDENTIFIER";
const string PastTripSegueIdentifier = "pastTripSegue";
public TripsTableViewController(IntPtr handle) : base(handle)
{
}
public PastTripsViewModel ViewModel { get; set; }
public override async void ViewDidLoad()
{
base.ViewDidLoad();
ViewModel = new PastTripsViewModel();
await ViewModel.ExecuteLoadPastTripsCommandAsync();
TableView.ReloadData();
TableView.TableFooterView = new UIView(new CGRect(0, 0, 0, 0));
RefreshControl.AddTarget(this, new Selector("RefreshSource"), UIControlEvent.ValueChanged);
NSNotificationCenter.DefaultCenter.AddObserver(new NSString("RefreshPastTripsTable"),
HandleReloadTableNotification);
}
public override void PrepareForSegue(UIStoryboardSegue segue, NSObject sender)
{
if (segue.Identifier == PastTripSegueIdentifier)
{
var controller = segue.DestinationViewController as CurrentTripViewController;
var indexPath = TableView.IndexPathForCell(sender as UITableViewCell);
var trip = ViewModel.Trips[indexPath.Row];
controller.PastTripsDetailViewModel = new PastTripsDetailViewModel(trip);
}
}
[Export("RefreshSource")]
async void RefreshControl_ValueChanged()
{
await ViewModel.ExecuteLoadPastTripsCommandAsync();
InvokeOnMainThread(delegate
{
TableView.ReloadData();
RefreshControl.EndRefreshing();
});
}
async void HandleReloadTableNotification(NSNotification obj)
{
await ViewModel.ExecuteLoadPastTripsCommandAsync();
InvokeOnMainThread(delegate { TableView.ReloadData(); });
}
#region UITableViewSource
public override nint RowsInSection(UITableView tableView, nint section)
{
return ViewModel.Trips.Count;
}
public override UITableViewCell GetCell(UITableView tableView, NSIndexPath indexPath)
{
if (ViewModel.CanLoadMore && !ViewModel.IsBusy && ViewModel.Trips.Count > 0 && indexPath.Row == ViewModel.Trips.Count - 1)
{
ViewModel.ExecuteLoadMorePastTripsCommandAsync().ContinueWith((t) =>
{
InvokeOnMainThread(delegate { TableView.ReloadData(); });
}, scheduler: System.Threading.Tasks.TaskScheduler.Current);
}
var trip = ViewModel.Trips[indexPath.Row];
if (string.IsNullOrEmpty(trip.MainPhotoUrl))
{
var cell = tableView.DequeueReusableCell(TripCellIdentifier) as TripTableViewCell;
if (cell == null)
{
cell = new TripTableViewCell(new NSString(TripCellIdentifier));
}
cell.LocationName = trip.Name;
cell.TimeAgo = trip.TimeAgo;
cell.Distance = trip.TotalDistance;
return cell;
}
else
{
var cell = tableView.DequeueReusableCell(TripCellWithImageIdentifier) as TripTableViewCellWithImage;
if (cell == null)
{
cell = new TripTableViewCellWithImage(new NSString(TripCellWithImageIdentifier));
}
cell.DisplayImage.SetImage(new NSUrl(trip.MainPhotoUrl));
cell.LocationName = trip.Name;
cell.TimeAgo = trip.TimeAgo;
cell.Distance = trip.TotalDistance;
return cell;
}
}
public override nfloat GetHeightForRow(UITableView tableView, NSIndexPath indexPath)
{
var trip = ViewModel.Trips[indexPath.Row];
if (string.IsNullOrEmpty(trip.MainPhotoUrl))
return 70;
else
return 221;
}
public override bool CanEditRow(UITableView tableView, NSIndexPath indexPath)
{
return true;
}
public override async void CommitEditingStyle(UITableView tableView, UITableViewCellEditingStyle editingStyle,
NSIndexPath indexPath)
{
switch (editingStyle)
{
case UITableViewCellEditingStyle.Delete:
var trip = ViewModel.Trips[indexPath.Row];
if(await ViewModel.ExecuteDeleteTripCommand(trip))
tableView.DeleteRows(new[] {indexPath}, UITableViewRowAnimation.Automatic);
break;
}
}
#endregion
}
}

View File

@ -0,0 +1,21 @@
// WARNING
//
// This file has been generated automatically by Visual Studio from the outlets and
// actions declared in your storyboard file.
// Manual changes to this file will not be maintained.
//
using Foundation;
using System;
using System.CodeDom.Compiler;
using UIKit;
namespace MyDriving.iOS
{
[Register ("TripsTableViewController")]
partial class TripsTableViewController
{
void ReleaseDesignerOutlets ()
{
}
}
}