Phillip Trelford's Array

POKE 36879,255

Mario

The Elm programming language has some fun game samples including Mario. Elm’s syntax is quite similar to F#’s so it turned out quite easy to port the Mario sample and use FunScript to compile the F# code to JavaScript:

Mario FunScript

Use the cursor keys to move Mario.

FunScript

With F# and FunScript you get to use Visual Studio (Windows) or Xamarin Studio (Mac), and get Intellisense over your code and JavaScript libraries via a Type Provider to TypeScript declaration files, which is nice.

The sample uses an F# record for state & function composition for Mario’s movement:

type mario = { x:float; y:float; vx:float; vy:float; dir:string }

let jump (_,y) m = if y > 0 && m.y = 0. then  { m with vy = 5. } else m
let gravity m = if m.y > 0. then { m with vy = m.vy - 0.1 } else m
let physics m = { m with x = m.x + m.vx; y = max 0. (m.y + m.vy) }
let walk (x,_) m = 
    { m with vx = float x 
             dir = if x < 0 then "left" elif x > 0 then "right" else m.dir }

let step dir mario = mario |> physics |> walk dir |> gravity |> jump dir

Alternatively the step function can be composed using the forward compose operator:

let step dir = physics >> walk dir >> gravity >> jump dir

FunScript is a lightweight open source F# to JavaScript compiler. It is still very much in development so if you want to take it out for a spin I’d recommend pulling the source directly from Zach’s Github repository (the current Nuget package is pretty old).

WebSharper

Another good option for F# to JavaScript compilation is WebSharper which is a mature, commercial offering from Intellifactory. I’ve ported the sample to WebSharper too:

The source code again is pretty close, with some minor differences in the way the JavaScript API’s are called. I’m pretty new to WebSharper, so found the slightly older WebSharper 2.4 the easiest version to get started with and adapted the HTML5 Canvas sample to get going.

WebSharper vs FunScript

Anton Tayanovskyy recently posted a WebSharper vs FunScript comparison.

To summarize:

  • FunScript aims to provide an easily extensible F# to JavaScript compiler for building client-side apps. The samples use a lightweight command line based web server built by Tomas Petricek so you don’t even need ASP.Net
  • WebSharper is a commercial enterprise scale web development platform with smooth integration with ASP.Net allowing seamless communication between client and server code

Which gives 2 good choices for creating web apps that target JavaScript with F# :)

For some more complete game implementations try:

  • Pacman (FunScript + HTML5 Canvas)
  • Pool (WebSharper + WebGL)

Progressive F# Tutorials NYC 2013

Last week saw the second Progressive F# Tutorials in New York held at the Dumbo loft, a great venue in Brooklyn literally under the Brooklyn Bridge.

Progressive FSharp Tutorials NYC 2013

The tutorials ran over 2 days with 2 keynotes:

  1. F# in an Open Source World – Don Syme, Microsoft Reseach
  2. F# Beyond Windows – Miguel De Icaza, Xamarin & Mono

F# is an open source language with a strong open source community and in his keynote Don talked about how companies and individuals are leveraging F#.

Miguel’s keynote focused on F# in Mono, and how it is now a built-in language in Xamarin Studio allowing F# to target Mac, Linux, iOS, Android and a host of other platforms.

Tracks

The core of the Tutorials is 4 x 4hr deep dive tutorials spread across 2 tracks catering for both beginners and more experienced F# users. This year I teamed up with Rachel Reese and Mathias Brandewinder for 3 sessions on the beginners track.  

F# Koans

The first beginner session was the F# Koans with Chris Marinos which is a great introduction to the language. The F# Koans are a set of failing tests that you implement progressively to learn new aspects of the language.

    [<Koan>]
    let ModifyingTheValueOfVariables() =
        let mutable x = 100
        x <- 200
        AssertEquality x __

In the example above you would write in the expected value for x.

Try F#

In this session lead by Rachel Reese we worked through tutorials on the Try F# site while discussing commercial uses of F#, particularly in Finance

 

Machine Learning

This session introduced F# in the context of Machine Learning, exploring data sets using a CSV type provider and the REPL. Mathias covered Naive Bayes using a set of text messages to classify as Ham or Spam, while l walked through a Decision Tree based classifier applied to a dataset for the Titanic:

Pacman Kata

The last session of the day was a Pacman Kata which culminated in creating your own behaviour for the Ghosts (or Pacman) inside a WPF version of the game using an API developed by Mathias.

Pacman ghosts 

Calling and Extending the F# Compiler

Tomas Petricek and Don Syme gave a deep dive session on the F# compiler. Tomas provided a set of samples that show how to embed the F# compiler into your own applications. During the session I began embedding the F# compiler into my open source spreadsheet project Cellz, so that as well as spreadsheet functions you can write F# expressions inline too:

FSharp in Cellz

Next up

The next Progressive F# Tutorials event will be in London on Oct 31 – Nov 1 where we will be returning to the Crypt.

ProgFsharp London 2013

If you’re interested in coming along to the New York event next year Skills Matter have a great early bird discount on at the moment.

Pacman Kata at Progressive F# Tutorials NYC 2013

I’m a bit of a Pacman fan so when I came across the Pacman Kata in the Kata Catalogue I was hooked:

Pacman finds himself in a grid filled with monsters. Will he be able to eat all the dots on the board before the monsters eat him?

Back in early 2012 we ran a Pacman Kata at the F#unctional Londoners meetup where you start with a maze and sprites and your task is to write a simple AI. After the event I extended the sample to run on Windows 8, Windows Phone as well as Silverlight and WPF, and somehow got a mention from Channel 9.

A few months back Neil Danson ported the sample to iOS, and over the last few weeks I’ve been playing with the HTML 5 canvas and have created a FunScript version too.

When Rich Minerich suggested a version for the Progressive F# Tutorials in New York I jumped at the chance, and teamed up with Mathias Brandewinder to create a fun session centred around Pacman:

 

Code samples from the session: http://trelford.com/Pacman.Kata.zip

Test-driven Pacman

The session began with some good old unit tests:

[<Test>]
let ``pacman should wrap from left to right beyond left extent`` () =
    let p = wrap { x = leftExtent-1; y =0 }
    Assert.AreEqual(rightExtent, p.x)

Followed by automated acceptance tests using TickSpec:

Scenario: Pacman eats dots
  When pacman eats a pac-dot
  Then he scores 10

Scenario: Pacman eats power pellets
  When pacman eats a power pellet
  Then he scores 50

In the sample the scenarios are automated using attribute based step definitions:

type Property = PacDot | PowerPellet

let [<When>] ``pacman eats a pac-dot`` () =
    properties <- PacDot::properties

let [<When>] ``pacman eats a power pellet`` () =
    properties <- PowerPellet::properties

let [<Then>] ``he scores (.*)`` (points:int) =
    let scored =
        properties |> List.sumBy (function
            | PacDot -> 10
            | PowerPellet -> 50
        )
    Assert.AreEqual(points, scored)

Controls

Next up we looked at implementing keyboard controls, first with Mario and then Pacman, both in FunScript:

Pacman keys 

The controls can be composed from simple functions:

let left (dx,_) p = if dx = –1 then {p with x=p.x+dx} else p
let right (dx,_) p = if dx = 1 then {p with x=p.x+dx} else p
let up (_,dy) p = if dy = -1 then {p with y=p.y+dy} else p
let down (_,dy) p = if dy = 1 then {p with y=p.y+dy} else p

let step dir pacman = pacman |> left dir |> right dir |> up dir |> down dir

Ghosts

The grand finale was writing your own AI for the Ghosts (or Pacman) using an API designed by Mathias specifically for the session:

// Decision is based on current move, line of sight and possible moves
member this.Decide (current: Move) (lineOfSight: Sight) (choices: Move Set) =
    n <- n + 1
           
    let inSight (creatures:Creature list) =
        creatures                
        |> List.exists (function PacMan 0 -> true | _ -> false)

    let standard  () =
        let restricted =                 
            choices 
            |> Set.filter (fun c -> not (c = backwards current))
        if (restricted |> Set.count > 0)
        then randomMove restricted
        else randomMove choices

    let home () =
        let s = lineOfSight
        let xs = [Up,s.Up; Down,s.Down; Left,s.Left; Right,s.Right]
        let x = 
            xs 
            |> List.tryFind (fun (d,xs) ->
                xs |> List.exists (snd >> inSight)
            )
        match x with
        | Some (d,_) -> d
        | None -> standard ()

    if (n / 500) % 2 = 0 then home ()
    else standard ()

The simple AI above switches the ghosts between homing in on Pacman and random moves every 500 frame updates (roughly every 8 seconds).

At the end we played off Mathias’s payoff function based Pacman AI against my simple Ghosts on the big screen which ended in a tie :)

Blue ghosts

In the more competitive Pacman session ran by Paulmichael Blasucci and Rich Minerich the final was between Jack Fox and Tyler Smith.

More fun

And there’s more fun to come, Rich Minerich will be running a Pacman competition at the Progressive F# Tutorials in London this year:

ProgFsharp London 2013

and there’s a Pacman Kata scheduled for November at the F#unctional Londoners meetup.