Jump to content
Brian Enos's Forums... Maku mozo!

Open Source Shot Timer


adweisbe

Recommended Posts

I decided I wanted a shot timer recently but the $130 price tag left me asking why I shouldn't just write my own. I started a GPL google code project to create a shot timer that runs on the J2SE 1.6 platform. This should run on any device like a laptop, netbook, or PDA that can run J2SE. Unfortunately this doesn't include the iphone (don't have one), google android (although it could be ported easily), and most cell phones and PDAs (they have J2ME which I won't consider). I think that there will be more devices supporting J2SE in the future so I don't think it necessarily a bad platform to target.

At this point I have the build and test infrastructure, finding and opening audio devices, code for generating and rendering buzzer(s) along a timeline, and code for pulling in captured audio data and providing it to some number of shot detection algorithms and providing the results to inerested listeners. The only missing piece right now is a decent shot detection algorithm. I am going to write one today that does something naive like measuring amplitude spikes or average amplitude above some threshold, but I wanted to throw this out there for the EEs and the like. The code is available @ http://code.google.com/p/openshottimer/

The interface for a shot detection algorithm is:

public class ShotEvent {

       /**
        * The number of this shot in the timeline
        */
       public final int m_shotNum;

       /**
        * Time the shot occured in milliseconds since the beginning of the timeline
        */
       public final long m_time;

       /**
        * Time between this shot and the last shot (or the beginning of the timeline for the first shot).
        * Also in milliseconds
        */
       public final long m_prevTime;


       public ShotEvent(int shotNum, long time, long prevTime) {
           m_shotNum = shotNum;
           m_time = time;
           m_prevTime = prevTime;
       }
   }

   /**
    * Base class for different shot detection algorithms.
    *
    */
   public static abstract class ShotDetector {

       /**
        * Format the audio data is being provided in
        */
       protected final AudioFormat m_format;

       /**
        * Number of samples per second
        */
       protected final float m_sampleRate;

       /**
        * Size of the audio samples in bits
        */
       protected final int m_sampleSizeInBits;

       /**
        * Size of the audio samples in bytes
        */
       protected final int m_sampleSizeInBytes;

       /**
        * Number of audio samples per millisecond at the current sample rate
        */
       protected final double m_samplesPerMillisecond;

       /**
        * List of shots detected by this algorithm
        */
       public final ArrayList<ShotEvent> m_shotEvents = new ArrayList<ShotEvent>();

       public ShotDetector(AudioFormat format) {
           m_format = format;
           m_sampleRate = m_format.getSampleRate();
           m_sampleSizeInBits = m_format.getSampleSizeInBits();
           m_sampleSizeInBytes = m_sampleSizeInBits / 8;

           m_samplesPerMillisecond = (m_sampleRate / 1000);
       }

       abstract protected ShotEvent[] processAudio(final byte data[], final int length);

   }

I am also at the stage where I need to write unit tests so any help with that would be appreciated. Once I have the shot detection working I will do the UI so I am also looking for volunteers in that area.

My goal is to put together a distribution with a usable CLI for Windows by the end of next weekend.

Edited by adweisbe
Link to comment
Share on other sites

  • Replies 220
  • Created
  • Last Reply

Top Posters In This Topic

This looks like a fun exercise but it has been my experience that trying to do any sort of real-time event-driven timing with a non-RTOS is frustrating at best. The shot detection will have to be the leading edge of the shot impulse and that could be missed if Windows decides to be off scratching it's ass at the time.

That said, my real concern is what are you going to run it on? My old timer takes a physical beating at every match. It has been scratched, bumped, dropped, crushed and still keeps running. Heck, if you are running it on a phone, I would be pretty pissed if you got a call during my stage!

Just some random thoughts.

Have Fun,

Chuck

Link to comment
Share on other sites

It's not intended as a match timer. Just an alternative to going out and buying a timer for practice. There is also the opportunity to do other interesting things from a record keeping and analysis perspective.

I am not sure what kind of problems you are talking about with scheduling. The sound card isn't dropping audio (hardware buffers) so I am getting a complete timeline of the audio with no gaps. There is the issue that I can't synchronize the audio stream containing the buzzer with the stream containing the captured audio, but the splits (most important in my mind) are done correctly.

I will have a chance to try it out Tuesday and see what the shots look like when captured.

Link to comment
Share on other sites

Hi there,

Since you started talking about a variety of devices, I thought you were doing your capture algorithm in software. It's great if you have dedicated hardware doing the sound sampling. You should have pretty good shot to shot temporal correlation. As you have discovered, trying to synchronize 2 processes in real time is difficult in a non-RTOS like Winders. An example would be trying to sync a command to hardware (like your sound card) and a timer method in the main app. The hardware gets it's signal but the OS decided to freshen up the swap file, listen to some network stuff, or some such thing and you get severe non-deterministic jitter in the timing of the system.

Please report back as you progress!

Later,

Chuck

Link to comment
Share on other sites

The app doesn't have any timers. It relies on the hardware timer on the sound card that governs the rate at which audio samples are consumed and produced by rendering/capturing. Because the capturing and rendering streams share the same hardware timer governing the rate at which they push/pull audio it is possible to count samples consumed/produced to track the passage of time and schedule/compare events relative to each other. It also obviates the need for real time scheduling since the processing can be done at a later time without the app having to look at wall clock time.

The sync issue is that time 0 (time the first sample is rendered) in the rendering timeline is not the same wall clock time as time 0 (time the first sample is captured) in the capturing timeline because there is no method in the API I am using that allows them to be started at the same time. They will be close, 10s of milliseconds in most cases, but there are no guarantees. This is why splits can be measured with %100 accuracy but the time from the buzzer (which is in the rendering timeline) to the first shot (which is in the capturing timeline) cannot.

I think there are also some misconceptions as to how audio is handled in a non-realtime OS. The sound card pushes/pulls audio to the OS via hardware interrupts that aren't subject to the scheduler. The OS keeps buffers large enough that overflow/underflow is not an issue.

Edited by adweisbe
Link to comment
Share on other sites

Success! I got some samples on an indoor range last night, wrote up a test case, and got a shot detector to pass. It detects the first sample above the threshold and then ignores the next 120 miiliseconds. No trouble with false positives when I flick the mic or rub it on clothing.

Shots show up nice and clear on the el cheapo radio shack mic I used. There is a nice 40 millisecond peak at the beginning that will be good for disambiguating other loud noises from actual shots.

9_shots.png

Going to work on a GUI tonight.

Link to comment
Share on other sites

Would be of any help knowing how Surefire Shot timer works (iphone only)?

http://www.downrange.tv/forum/index.php?topic=4096.0

Probably not much. The only proprietary thing is how to detect shots in PCM audio and I am pretty sure I have a couple ways of doing it that will be similar to the analog shot timers on the market.

Can't decide if I love or hate swing. I only had to put in two hours, but it looks terrible!

ost.png

BTW those splits are me flicking the mic. I can shoot faster then that!

Link to comment
Share on other sites

The .1 release as promised. I tested it on my wife's desktop and it ran fine.

http://openshottimer.googlecode.com/files/ost.jar

You can't adjust the start delay in this version (at least not without editing a configuration file) so I set it to wait 3-5 seconds (random) before buzzing you so you have time to get back in position and relax before the buzzer.

You need to have two things configured correctly for the shot timer to work. You have to have the Java 2 1.6 Standard Edition (J2SE) runtime environment installed. Many of you will already have this installed from using applications like Open Office. This is the software that is able to execute the jar file I linked to above. If you double click on the jar and file nothing comes up and Windows asks you what program you want to open it with then you probably don't have it installed. You can download it from http://java.sun.com/javase/downloads/index.jsp If Windows still acts like it doesn't know how to open a jar file then you will need to point (open with) it to the java.exe in C:\Proram Files\Java\<Java Version>\bin\java.exe so that Windows will know to associate the jar file type with Java.

You also need to have your default audio recording device and default audio playback device correctly configured. That means that they must not be muted and that the microphone is plugged into whatever the default recording device is. How you configure which device is the default device will vary depending on the version of Windows you are using and you can PM me if you need help. Once you have the shot timer running set the recording volume to max and check to see if it registers shots when you tap the mic. You have to click "Buzz me!" for it to start detecting shots. If it doesn't detect taps with the recording volume at max then you have a setup problem that needs to be worked through before you got shooting.

To use it for shooting you want to turn the mic sensitivity down until it stops registering false positives but still registers shots with whatever firearm and environment you are working in. I am working on moving all the device selection and volume adjustment into the shot timer itself so you don't have to hunt down Windows settings in the control panel. It is a lot of work to manipulate those settings and it is even more work to make an interactive display for manipulating them so it will take a while.

If you need help PM me.

Link to comment
Share on other sites

http://code.google.com/p/openshottimer/downloads/list

This version allows you to set the levels and mute on the brazzillion devices that may be present on your system. The second tab is the brazzillion input and output ports that are controllable and the third tab is the controls for the specific output port being used.

ost1.png

ost2.png

ost3.png

I am working on allowing you to select from the various input and output sources graphically in case the default ones aren't the ones you want. That is the last of the things I need to add to allow you to configure the app without rooting around in the control panel for default settings.

After that I will do a code cleanup and refactoring session and then move on to adding more features like customized starts (delay, random, instant), cadence, and logging shot strings.

Link to comment
Share on other sites

All this work to save $130? :roflol:

Just kidding.... I program LoB apps for a living and just can't bring myself to code on my off hours anymore.

Great work. It is always fun when interests coincide.

Regards,

Eric

Link to comment
Share on other sites

  • 6 months later...

I am working on it right now. I estimate about three weeks. I don't actually own a Droid so I will have to test it with a co-worker's phone and won't be doing any live fire testing (just flicking the mic which works well enough). The SDK has a great emulator that lets me do the UI and app life cycle (the hard part) on my computer.

The PC version actually works really well when it comes to shot detection, but the user interface and input adjustment is not user friendly.

Edited by adweisbe
Link to comment
Share on other sites

Sounds great adweisbe!!! :)

I just wanted to let you know that there are more folks with Android phones out there, who are interested in some shooting apps.

I love the idea of a shot timer, but what I'd REALLY be interested in is some kind of stage scoring application. It doesnt have to be capable of trasferring the data to a master device (Laptop, PDA, Android phone, etc.) but it should be able to score multiple shooters on multiple stages. That way we can compare 2 or more shooters at a glance during a match.

That would be great fun!

Link to comment
Share on other sites

I am working on it right now. I estimate about three weeks. I don't actually own a Droid so I will have to test it with a co-worker's phone and won't be doing any live fire testing (just flicking the mic which works well enough). The SDK has a great emulator that lets me do the UI and app life cycle (the hard part) on my computer.

The PC version actually works really well when it comes to shot detection, but the user interface and input adjustment is not user friendly.

Awesome keep me posted. I just got my Droid and would be ecstatic if I had a shot timer app.

Link to comment
Share on other sites

Sounds great adweisbe!!! <img src="http://www.brianenos.com/forums/public/style_emoticons/<#EMO_DIR#>/smile.gif" style="vertical-align:middle" emoid=":)" border="0" alt="smile.gif" />

I just wanted to let you know that there are more folks with Android phones out there, who are interested in some shooting apps.

I love the idea of a shot timer, but what I'd REALLY be interested in is some kind of stage scoring application. It doesnt have to be capable of trasferring the data to a master device (Laptop, PDA, Android phone, etc.) but it should be able to score multiple shooters on multiple stages. That way we can compare 2 or more shooters at a glance during a match.

That would be great fun!

http://www.doublealpha.biz/daa-iphone-applications/ipscore-ipsc-scoring-application

Its not free.....

Flyin

Link to comment
Share on other sites

Sorry John, but that's not for Android phones. That's an Apple app only. Android is an open source OS, and therefore should be rather easy for a programmer type (that which I am not) to build a scoring application.

Yep I know but just wanted to let people know that Iphone had an app out there.

Flyin

Link to comment
Share on other sites

Hi all,

The new timer is available here:

http://code.google.com/p/openshottimer/downloads/list

android_ost.png

I buckled down today and went as far as I could with the app given that the emulator won't let me record audio. It should use audio support if it is available but I have no idea if it will work. If it is too sensitive or not sensitive enough play with your microphone volume. I will add a slider for that later.

If if it can't access the audio hardware an error will pop up and it will start generating fake shots just to prove that the UI works. I will try it out on my co-workers Droid on Monday.

Ariel

Edited by adweisbe
Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now



×
×
  • Create New...