Pregunta

I have the following code in a WP7 app, and am starting to look at F#.. I can't find any GeoCoordinate examples, can anyone give me an idea of how this code would look in F#? Or point me to an example? I've had a look at some tutorials, books and Pluralsight, so think I am just starting to grasp the basics..but can't seem to get my head around this! All the examples I can seem to find are based around mathematical problem spaces. Any help or advice is much appreciated!

public partial class MainPage : PhoneApplicationPage
{
    GeoCoordinateWatcher watcher;
    // Constructor
    public MainPage()
    {
        InitializeComponent();
        SupportedOrientations = SupportedPageOrientation.Portrait | SupportedPageOrientation.Landscape;
    }

    private void btnStart_Click(object sender, RoutedEventArgs e)
    {
        //Reinitialize the GeoCoordinateWatcher
        watcher = new GeoCoordinateWatcher(GeoPositionAccuracy.High);
        watcher.MovementThreshold = 100;//distance in meters

        //Add event handlers for StatusChanged and PositionChanged Events
        watcher.StatusChanged += new EventHandler<GeoPositionStatusChangedEventArgs>(watcher_StatusChanged);
        watcher.PositionChanged += new EventHandler<GeoPositionChangedEventArgs<GeoCoordinate>>(watcher_PositionChanged);

        //Start data acquisition
        watcher.Start();

        //hide button
        btnStart.Visibility = Visibility.Collapsed;


    }

    #region Event Handlers
    /// <summary>
    /// Handler for the StatusChanged event. This invokes MyStatusChanged on the UI thread
    /// and passes the GeoPositionStatusChangedEventArgs
    /// </summary>
    /// <param name="sender"></param>
    /// <param name="e"></param>
    void watcher_StatusChanged(object sender, GeoPositionStatusChangedEventArgs e)
    {
        Deployment.Current.Dispatcher.BeginInvoke(() => MyStatusChanged(e));
    }
    /// <summary>
    /// Handler for the PositionChanged Event. This invokes MyPositionChanged on the UI thread and 
    /// passes the GeoPositionStatusChangedEventArgs
    /// </summary>
    /// <param name="sender"></param>
    /// <param name="e"></param>
    void watcher_PositionChanged(object sender, GeoPositionChangedEventArgs<GeoCoordinate> e)
    {
        Deployment.Current.Dispatcher.BeginInvoke(() => MyPositionChanged(e));
    }
    #endregion

    /// <summary>
    /// Custom method called from the PositionChanged event handler
    /// </summary>
    /// <param name="e"></param>
    /// <returns></returns>
    void MyPositionChanged(GeoPositionChangedEventArgs<GeoCoordinate> e)
    {
        //update the map to show the current location
        GeoCoordinate geo = new GeoCoordinate(e.Position.Location.Latitude, e.Position.Location.Longitude);
        Location ppLoc = new Location(e.Position.Location.Latitude, e.Position.Location.Longitude);
        mapMain.SetView(geo, 10);
        //update pushpin location and show
        MapLayer.SetPosition(ppLocation, ppLoc);
        ppLocation.Visibility = System.Windows.Visibility.Visible;
    }
    /// <summary>
    /// Custom method called from the StatusChanged event handler
    /// </summary>
    /// <param name="e"></param>
    /// <returns></returns>
    void MyStatusChanged(GeoPositionStatusChangedEventArgs e)
    {
        switch (e.Status)
        {
            case GeoPositionStatus.Disabled:
                //the location service is disabled or unsupported, alert the user
                tbStatus.Text = "Sorry we can't find you on this device";
                break;
            case GeoPositionStatus.Initializing:
                //location service is initializing
                //disable the start location button
                tbStatus.Text = "Looking For you...";
                break;
            case GeoPositionStatus.NoData:
                //location service is working but no data found, alert the user and enable the stop location button
                tbStatus.Text = "can't find you yet...";
                ResetMap();
                break;
            case GeoPositionStatus.Ready:
                //location service is receiving data, show the current position and enable the stop location button
                tbStatus.Text = "We found you!";
                break;
        }

    }

    void ResetMap()
    {
        Location ppLoc = new Location(0, 0);
        GeoCoordinate goe = new GeoCoordinate(0.0,0.0);
        mapMain.SetView(goe, 1);

        //update pushpin location and show
        MapLayer.SetPosition(ppLocation, ppLoc);
        ppLocation.Visibility = System.Windows.Visibility.Collapsed;
    }
}
¿Fue útil?

Solución

I think that this is due to the fact that F# is touted as a language that you can process a large amount of information without being very verbose. While you can build small user interface elements using F# by calling relevant libraries, the intention is for you to build UI's with C# / ASP.NET/ etc. So, it wouldn't really make sense with your application because all you are doing is building a small UI and connecting events of that UI to a larger library of geoprocessing capabilities.

But if you wanted to collect information from that library (or a similar one) of all the points of interest nearby, then sort them according to distance from the user and his potential for 'liking' that point of interest based on some algorithm designed to compare a random point of interest with catagories or prior ratings then F# would be a good choice. You can rapidly describe those data structures, manipulate them, and return the result of it's processing back to your user interface.

This is why instructions such as the one shown here can be helpful. While very light on calling or creating a user interface (the C# code just display some text passed from the F# code), it can be used to create a backend for your phone application.

Otros consejos

The sample you posted is a lot of code, so I don't expect that anybody will translate that to F# for you. Calling .NET functionality from F# is generally quite similar to how you'd call it from C# (at least initially, before you learn how to use some advanced F# patterns), so the translation should be pretty direct.

The F# version of code that initializes the GeoCoordinateWatcher is probably going to look like this:

let watcher = new GeoCoordinateWatcher(GeoPositionAccuracy.High)
watcher.MovementThreshold <- 100

// Add event handlers for StatusChanged and PositionChanged Events 
watcher.StatusChanged.Add(fun eargs ->
  MyStatusChanged(eargs) )
watcher.PositionChanged.Add(fun eargs ->
  MyPositionChanged(eargs) ) 

// Start data acquisition 
watcher.Start()

In general, F# has a couple of nice features that simplify user interface programming. As far as I know, there isn't a guide on developing Windows Phone applications in F#, specifically, but MSDN has a section that describes development of Silverlight applications, and most of the patterns will be the same:

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top