Skip to content

Commit

Permalink
Fit and finish for when-to-go-home feature
Browse files Browse the repository at this point in the history
  • Loading branch information
meirtsvi committed Feb 5, 2012
1 parent cbf5b2e commit a934c5c
Show file tree
Hide file tree
Showing 16 changed files with 1,202 additions and 579 deletions.
2 changes: 2 additions & 0 deletions WazeScheduledTaskAgent/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
Bin/
obj/
156 changes: 156 additions & 0 deletions WazeScheduledTaskAgent/BackgroundNavigator.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,156 @@
using System;
using System.Text.RegularExpressions;
using System.Threading;
using System.IO;
using System.IO.IsolatedStorage;
using System.Device.Location;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Ink;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;

namespace WazeScheduledTaskAgent
{
public class BackgroundNavigator
{

/// <summary>
/// Returns the current cached location from GPS
/// </summary>
/// <returns></returns>
public static GeoCoordinate GetCurrentLocation()
{
//// Simulate location in debugger:
//if (System.Diagnostics.Debugger.IsAttached)
//{
// return new GeoCoordinate((double)32095676 / (double)1000000, (double)34798484 / (double)1000000);
//}

GeoCoordinateWatcher watcher = new GeoCoordinateWatcher(GeoPositionAccuracy.High);
watcher.TryStart(true,TimeSpan.FromSeconds(13));

return watcher.Position.Location;
}

/// <summary>
/// Return the Home location from favorites
/// </summary>
/// <param name="homeName"></param>
/// <returns></returns>
public static GeoCoordinate GetHomeLocation(string homeName)
{
FileStream historyFile = null;
try
{
var store = IsolatedStorageFile.GetUserStoreForApplication();

historyFile = store.OpenFile("/history", FileMode.Open);
}
catch (FileNotFoundException)
{
System.Diagnostics.Debug.WriteLine("Can't find history file");
return GeoCoordinate.Unknown;

}
catch (Exception)
{
return GeoCoordinate.Unknown;
}

StreamReader sr = new StreamReader(historyFile);

while (!sr.EndOfStream)
{
string line = sr.ReadLine();
string[] tokens = line.Split(new[] { ',' }, StringSplitOptions.None);
string placeName = tokens[5];
if ((placeName.ToLower() == homeName) || (placeName == "home"))
{

double destLongitude = double.Parse(tokens[7]) / 1000000;
double destLatitude = double.Parse(tokens[6]) / 1000000;
sr.Dispose();

return new GeoCoordinate(destLatitude, destLongitude);
}
}

return GeoCoordinate.Unknown;
}


/// <summary>
/// Gets the estimated route time in minutes
/// </summary>
/// <param name="from"></param>
/// <param name="to"></param>
/// <returns>Route time in minutes</returns>
public static int GetRouteTime(GeoCoordinate from, GeoCoordinate to)
{
string requestStr = string.Format("http://www.waze.co.il/RoutingManager/routingRequest?from=x%3A{0}+y%3A{1}&to=x%3A{2}+y%3A{3}&returnJSON=false&returnGeometries=false&returnInstructions=false&timeout=60000&nPaths=1",
from.Longitude, from.Latitude, to.Longitude, to.Latitude);

try
{
HttpWebResponse resp = null;
ManualResetEvent mre = new ManualResetEvent(false);
HttpWebRequest req = (HttpWebRequest)HttpWebRequest.Create(requestStr);
req.BeginGetResponse(delegate(IAsyncResult result)
{
try
{
resp = (HttpWebResponse)req.EndGetResponse(result);
mre.Set();
}
catch (Exception we)
{
System.Diagnostics.Debug.WriteLine(we.ToString());

resp = null;
mre.Set();
}
}, null);

// we can't wait more then 14 seconds or else the OS will kill us.
if (!mre.WaitOne(14000))
return -1;

StreamReader sr = new StreamReader(resp.GetResponseStream());
string respString = sr.ReadToEnd();

System.Diagnostics.Debug.WriteLine("Response String:" + Environment.NewLine + respString);

int arrivingTime = 0;
Regex regex = new Regex("\"crossTime\":([0-9]+)");
MatchCollection matchCol = regex.Matches(respString);
foreach (Match match in matchCol)
{
int crossTime = int.Parse(match.Groups[1].Value);
arrivingTime += crossTime;
}

sr.Dispose();

return arrivingTime / 60;
}
catch (Exception exc)
{

System.Diagnostics.Debug.WriteLine(exc.ToString());

if (System.Diagnostics.Debugger.IsAttached)
{
// An unhandled exception has occurred; break into the debugger
System.Diagnostics.Debugger.Break();
}

return -1;
}
}
}
}
37 changes: 37 additions & 0 deletions WazeScheduledTaskAgent/Properties/AssemblyInfo.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Resources;

// General Information about an assembly is controlled through the following
// set of attributes. Change these attribute values to modify the information
// associated with an assembly.
[assembly: AssemblyTitle("WazeScheduledTaskAgent")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("")]
[assembly: AssemblyProduct("WazeScheduledTaskAgent")]
[assembly: AssemblyCopyright("Copyright 2012")]
[assembly: AssemblyTrademark("")]
[assembly: AssemblyCulture("")]

// Setting ComVisible to false makes the types in this assembly not visible
// to COM components. If you need to access a type in this assembly from
// COM, set the ComVisible attribute to true on that type.
[assembly: ComVisible(false)]

// The following GUID is for the ID of the typelib if this project is exposed to COM
[assembly: Guid("e465278b-e963-4436-b385-21f882188220")]

// Version information for an assembly consists of the following four values:
//
// Major Version
// Minor Version
// Build Number
// Revision
//
// You can specify all the values or you can default the Revision and Build Numbers
// by using the '*' as shown below:
[assembly: AssemblyVersion("1.0.0.0")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: NeutralResourcesLanguageAttribute("en-US")]
181 changes: 181 additions & 0 deletions WazeScheduledTaskAgent/ScheduledAgent.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,181 @@
using System;
using System.Threading;
using System.IO;
using System.IO.IsolatedStorage;
using System.Linq;
using System.Windows;
using Microsoft.Phone.Scheduler;
using Microsoft.Phone.Shell;
using Microsoft.Phone.Controls;
using System.Windows.Resources;
using System.Device.Location;

namespace WazeScheduledTaskAgent
{
public class ScheduledAgent : ScheduledTaskAgent
{
private static volatile bool _classInitialized;

/// <remarks>
/// ScheduledAgent constructor, initializes the UnhandledException handler
/// </remarks>
public ScheduledAgent()
{
if (!_classInitialized)
{
_classInitialized = true;
// Subscribe to the managed exception handler
Deployment.Current.Dispatcher.BeginInvoke(delegate
{
Application.Current.UnhandledException += ScheduledAgent_UnhandledException;
});
}
}

/// Code to execute on Unhandled Exceptions
private void ScheduledAgent_UnhandledException(object sender, ApplicationUnhandledExceptionEventArgs e)
{
if (System.Diagnostics.Debugger.IsAttached)
{
// An unhandled exception has occurred; break into the debugger
System.Diagnostics.Debugger.Break();
}
}

/// <summary>
/// Agent that runs a scheduled task
/// </summary>
/// <param name="task">
/// The invoked task
/// </param>
/// <remarks>
/// This method is called when a periodic or resource intensive task is invoked
/// </remarks>
protected override void OnInvoke(ScheduledTask task)
{
string langHomeName = string.Empty;
string interval = string.Empty;

try
{
// Get data from storage:
//

Mutex mLiveTileStorageMutex = new Mutex(true,"LiveTileStorageMutex");

try
{

mLiveTileStorageMutex.WaitOne();

// Save the home name in selected language so the task can search for it later on.
using (IsolatedStorageFileStream fsHomeName = IsolatedStorageFile.GetUserStoreForApplication().OpenFile("LiveTile\\HomeName",FileMode.Open,FileAccess.Read))
{
using (StreamReader sr = new StreamReader(fsHomeName))
{
langHomeName = sr.ReadLine();
}

}

// Save the refresh interval so the task can search for it later on.
using (IsolatedStorageFileStream fsInterval = IsolatedStorageFile.GetUserStoreForApplication().OpenFile("LiveTile\\Interval",FileMode.Open,FileAccess.Read))
{
using (StreamReader sr = new StreamReader(fsInterval))
{
interval = sr.ReadLine();
}

}
}
finally
{
mLiveTileStorageMutex.ReleaseMutex();
}


string tileData = string.Empty;

// Get current location:
GeoCoordinate from = BackgroundNavigator.GetCurrentLocation();

// Find home location:

GeoCoordinate to = BackgroundNavigator.GetHomeLocation(langHomeName);

// Calculate time to home:

int etaMin = 0;

if (from == GeoCoordinate.Unknown)
{
tileData = "No GPS available";
}
else if (to == GeoCoordinate.Unknown)
{
// default back message in case user did not set home:
tileData = "Please set 'Home' favorite";
}
else
{
etaMin = BackgroundNavigator.GetRouteTime(from, to);

// Prepare data for tile:
if (etaMin >= 0)
{
tileData = etaMin + " min" + Environment.NewLine + "Last Update:" + Environment.NewLine + DateTime.Now.ToShortTimeString();
}
else
{
etaMin = 0;
tileData = "Failed to find route";
}

}

// Update Tile:

// On the front tile we can show a max of 99 min.
int frontETA = (etaMin < 100) ? etaMin : 99;

string taskName = "Waze Periodic Task";

ShellTile currentTiles = ShellTile.ActiveTiles.First();
StandardTileData tilesUpdatedData = new StandardTileData
{
Title = "Waze",
BackgroundImage = new Uri("waze_logo.png", UriKind.Relative),
Count = frontETA,
BackTitle = "Home ETA",
BackContent = tileData

};

currentTiles.Update(tilesUpdatedData);

int userInterval = int.Parse(interval);

if (userInterval < 30)
{
// Update the Tile again in selected interval min (Won't work for marketplace app) if less than 30:
ScheduledActionService.LaunchForTest(taskName, TimeSpan.FromMinutes(userInterval));
}

}
catch (Exception exc)
{
System.Diagnostics.Debug.WriteLine(exc.ToString());

if (System.Diagnostics.Debugger.IsAttached)
{
// An unhandled exception has occurred; break into the debugger
System.Diagnostics.Debugger.Break();
}
}
finally
{
NotifyComplete();
}
}
}
}
Loading

0 comments on commit a934c5c

Please sign in to comment.