about summary refs log tree commit diff
path: root/website/sandbox/chord-drill-sergeant/src/Piano.elm
diff options
context:
space:
mode:
authorWilliam Carroll <wpcarro@gmail.com>2020-04-11T09·45+0100
committerWilliam Carroll <wpcarro@gmail.com>2020-04-11T09·45+0100
commit3562343c196b381fea7ebff9fc8612ac0ad927ff (patch)
tree6c6132c50a35556f657f3c936cd624cf58100085 /website/sandbox/chord-drill-sergeant/src/Piano.elm
parent3dac2f10ff4f7f6c5f82cacd27e09c079dcd0367 (diff)
Generate all known chords and display randomly selected chords
First of all, Elm's purity is beautiful. I think every language should model
their error messages and develop experience after Elm. If I didn't have to
download packages, I don't think I would need an internet connection to
troubleshoot my program's errors. This is how helpful I find the compiler.

Now that that's out of the way, here's what I've changed since we've last
corresponded:
- Use Elm's Browser.element to create a reactive application with state
- Write a function to generate all of the chords about which CDS knows
- Move some code out of Main.elm into other modules
- Depend on List.Extra, Random, Random.Extra

What's left:
- Lots of work
- Instead of clicking a button to show a new chord, use a timer
- Add mobile-first styling (probably add TailwindCSS)
- Persist settings in LocalStorage (and then eventually create user accounts)
- Allow users to curate the list of chords they're interested in practicing
- Deploy the website and dogfood it

Unknowns:
- How can I handle tempo? I don't expect setInterval to be enough (maybe it
  is)...
Diffstat (limited to 'website/sandbox/chord-drill-sergeant/src/Piano.elm')
-rw-r--r--website/sandbox/chord-drill-sergeant/src/Piano.elm69
1 files changed, 46 insertions, 23 deletions
diff --git a/website/sandbox/chord-drill-sergeant/src/Piano.elm b/website/sandbox/chord-drill-sergeant/src/Piano.elm
index 7c44f4bf4f6f..ba034d47cccf 100644
--- a/website/sandbox/chord-drill-sergeant/src/Piano.elm
+++ b/website/sandbox/chord-drill-sergeant/src/Piano.elm
@@ -5,42 +5,65 @@ import Html exposing (..)
 import Html.Attributes exposing (..)
 import Html.Events exposing (..)
 
+import Theory
+
 {-| These are the white keys on most modern pianos. -}
-natural : Html a
-natural =
-  li [ style "background-color" "white"
+natural : Bool -> Html a
+natural isHighlit =
+  li [ style "background-color" (if isHighlit then "red" else "white")
      , style "height" "20px"
      , style "border-top" "1px solid black"
+     , style "border-bottom" "1px solid black"
      ] []
 
 {-| These are the black keys on most modern pianos. -}
-accidental : Html a
-accidental =
-  li [ style "background-color" "black"
+accidental : Bool -> Html a
+accidental isHighlit =
+  li [ style "background-color" (if isHighlit then "red" else "black")
      , style "height" "10px"
      , style "width" "66%"
      ] []
 
 {-| A section of the piano consisting of all twelve notes. The name octave
 implies eight notes, which most scales (not the blues scale) honor. -}
-octave : List (Html a)
-octave = [ natural
-         , accidental
-         , natural
-         , accidental
-         , natural
-         , natural
-         , accidental
-         , natural
-         , accidental
-         , natural
-         , accidental
-         , natural
-         ]
+octave : List Theory.Note -> List (Html a)
+octave highlight =
+  let
+    isHighlit note = List.member note highlight
+  in
+    [ natural (isHighlit Theory.C)
+    , accidental (isHighlit Theory.C_sharp)
+    , natural (isHighlit Theory.D)
+    , accidental (isHighlit Theory.D_sharp)
+    , natural (isHighlit Theory.E)
+    , natural (isHighlit Theory.F)
+    , accidental (isHighlit Theory.F_sharp)
+    , natural (isHighlit Theory.G)
+    , accidental (isHighlit Theory.G_sharp)
+    , natural (isHighlit Theory.A)
+    , accidental (isHighlit Theory.A_sharp)
+    , natural (isHighlit Theory.B)
+    ]
+
+indexForNote : Theory.Note -> Int
+indexForNote note =
+  case note of
+    Theory.C       -> 0
+    Theory.C_sharp -> 1
+    Theory.D       -> 2
+    Theory.D_sharp -> 3
+    Theory.E       -> 4
+    Theory.F       -> 5
+    Theory.F_sharp -> 6
+    Theory.G       -> 7
+    Theory.G_sharp -> 8
+    Theory.A       -> 9
+    Theory.A_sharp -> 10
+    Theory.B       -> 11
 
 {-| Return the HTML that renders a piano representation. -}
-render : Html a
-render =
+render : { highlight : List Theory.Note } -> Html a
+render {highlight} =
   ul [ style "width" "100px"
      , style "list-style" "none"
-     ] (octave |> List.repeat 3 |> List.concat)
+     ] (octave highlight |> List.reverse |> List.repeat 1 |> List.concat)