using System; using System.Collections.Generic; using System.Collections.ObjectModel; using System.Linq; using BikeInfo = TINK.Model.Bike.BC.BikeInfo; using BikeInfoMutable = TINK.Model.Bike.BC.BikeInfoMutable; namespace TINK.Model.Bike { /// <summary> Holds entity of bikes. </summary> public class BikeCollectionMutable : ObservableCollection<BikeInfoMutable>, IBikeDictionaryMutable<BikeInfoMutable> { /// <summary> Constructs a mutable bike collection object. </summary> public BikeCollectionMutable() { SelectedBike = null; } /// <summary> /// Updates bikes dictionary from bikes response, i.e. /// - removes bikes which are no more contained in bikes response /// - updates state of all bikes from state contained in bikes response /// </summary> /// <param name="bikesAll"> Object holding bikes info from copri to update from.</param> /// <param name="p_oDateTimeProvider">Provices date time information.</param> public void Update( IEnumerable<BikeInfo> bikesAll) { // Get list of current bikes by state(s) to update. // Needed to remove bikes which switched state and have to be removed from collection. var bikesToBeRemoved = this.Select(x => x.Id).ToList(); foreach (var bikeInfo in (bikesAll ?? new List<BikeInfo>())) { /// Check if bike has to be added to list of existing station. if (ContainsKey(bikeInfo.Id) == false) { // Bike does not yet exist in list of bikes. Add(BikeInfoMutableFactory.Create(bikeInfo)); continue; } // Update bike. GetById(bikeInfo.Id).State.Load(bikeInfo.State); if (bikesToBeRemoved.Contains<string>(bikeInfo.Id)) { // Remove list from obsolete list. bikesToBeRemoved.Remove(bikeInfo.Id); } } // Remove obsolete bikes. foreach (var l_oId in bikesToBeRemoved) { RemoveById(l_oId); } } /// <summary> /// Adds a new bike to collecion of bike. /// </summary> /// <param name="p_oNewBike">New bike to add.</param> /// <exception cref="Exception">Thrown if bike is not unique.</exception> public new void Add(BikeInfoMutable p_oNewBike) { // Ensure that bike id of new bike is is unique foreach (BikeInfoMutable l_oBike in Items) { if (l_oBike.Id == p_oNewBike.Id) { throw new Exception(string.Format("Can not add bike with {0} to collection ob bike. Id is not unnique.", p_oNewBike)); } } base.Add(p_oNewBike); } /// <summary> /// Bike selected by user for regerving or cancel reservation. /// </summary> public BikeInfoMutable SelectedBike { get; private set; } public void SetSelectedBike(string id) { SelectedBike = GetById(id); } /// <summary> /// Gets a bike by its id. /// </summary> /// <param name="id"></param> /// <returns></returns> public BikeInfoMutable GetById(string id) { { return this.FirstOrDefault(bike => bike.Id == id); } } /// <summary> /// Deteermines whether a bike by given key exists. /// </summary> /// <param name="p_strKey">Key to check.</param> /// <returns>True if bike exists.</returns> public bool ContainsKey(string id) { return GetById(id) != null; } /// <summary> /// Removes a bike by its id. /// </summary> /// <param name="id">Id of bike to be removed.</param> public void RemoveById(string id) { var l_oBike = GetById(id); if (l_oBike == null) { // Nothing to do if bike does not exists. return; } Remove(l_oBike); } /// <summary> /// Create mutable objects from immutable objects. /// </summary> private static class BikeInfoMutableFactory { public static BikeInfoMutable Create(BikeInfo bikeInfo) { return (bikeInfo is BluetoothLock.BikeInfo bluetoothLockBikeInfo) ? new BluetoothLock.BikeInfoMutable(bluetoothLockBikeInfo) : new BikeInfoMutable(bikeInfo); } } } }