This article shows how to write a command-line timer in Scala. There are simple ways to do this as just a regular Unix/Linux shell script, but I wanted to use Scala, in part so I could try to remember how to use the Java sound libraries. (I also initially thought about writing this is a GUI app, but decided to just make it a command-line app.)
I wanted a simple command-line timer, so I wrote one in Scala.
Usage
My Scala shell script plays a sound file after the number of minutes you specify. It also takes an optional decibal level, so a command to play a “gong” sound after 30 minutes is this:
$ timer 30
This command also says to play the gong sound file in 30 minutes, but to reduce the decibal level with the -20
value:
$ timer 30 -20
Note: I copied my
timer
script to my ~/bin directory, and that directory is in my Unix command line path, so I can run mytimer
script regardless of what directory I’m currently in.
Scala timer shell script source code
Without any introduction, here’s the source code for my Scala “timer” shell script:
#!/bin/sh exec scala -savecompiled "$0" "$@" !# import javax.sound.sampled._ val oneMinute = 60*1000 // usage if (args.length < 1) showUsageAndExit // initialize the values from the user input val minutesToWait = args(0).toInt val gainControl = if (args.length==2) args(1).toInt else -20 println(s"Timer started. Wait time is $minutesToWait minutes.\n") // wait the desired time for (i <- 1 to minutesToWait) { Thread.sleep(oneMinute) println(s"time remaining: ${minutesToWait-i} ...") } // play the sound twice for (i <- 1 to 2) { playSoundfile("/Users/al/bin/gong.wav") Thread.sleep(7*1000) } def playSoundfile(f: String) { val audioInputStream = AudioSystem.getAudioInputStream(new java.io.File(f)) val clip = AudioSystem.getClip clip.open(audioInputStream) val floatGainControl = clip.getControl(FloatControl.Type.MASTER_GAIN).asInstanceOf[FloatControl] floatGainControl.setValue(gainControl) //reduce volume by x decibels (like -10f or -20f) clip.start } def showUsageAndExit { Console.err.println("Usage: timer minutes-before-alarm <gain-control>") Console.err.println(" gain-control should be something like -10 or -20") System.exit(1) }
There’s nothing too special about the code, I just kicked it out pretty fast because I was tired of dealing with my kitchen timer. Because I always have a Mac Terminal window open I thought I’d do this from the command line instead of putting a GUI on it.
Note: If you have any problems with this script, it’s probably with the sound file you’re using. I don’t know all of the details, but I do know that the Java Sound API has a problem with some (many?) files, and it also won’t play MP3 files. I had a problem with an old “.au” sound file, and converted it to a WAV format, and that made it work.