Alex Fernandez

Computer Scientist
Contact 21alex295@gmail.com / Github
Home Blog Resume

The making of: A GPS anchor for my boat

I, as a horrible fisher, need to have some excuses why I don’t catch even the smallest fish on my fishing outings. I usually blame the weather, or any other condition external to me. One of these excuses is that it is hard to keep in the same place while fishing, since even when anchored, the wind moves you out of place, and usually you stop catching fishes. Don’t tell anyone I wasn’t catching anything before that either.

So, one of the solutions for this is having two anchors in your boat (lame). This causes extra issues, like having a too many ropes in your boat and entangling everything. The solution I would like to have is buying a GPS anchor, an electric outboard with an electronic controller that keeps you in the same GPS spot.

The problem with this is, they are expensive, so I though, why not make one myself, seems easy enough… right?

So I created a proto-prototype, to see if the idea is even feasible. To this end I got:

And that’s it for the moment! The basic idea is to have a system that is capable of always aim to the same GPS coordinate. This is doable by attaching the compass to the top rotating part of the stepper motor, you can calculate the angle between your current position and the desired position. In this first stage, I just set up some made up GPS coordinates, and let the system rotate to aim towards that coordinates based. You need to calculate the compass angle generated by the line that crosses both GPS points, and align the compass angle with that by rotating the stepper motor until aligned. Code looks something like this:


#include <QMC5883LCompass.h>

#include <Stepper.h> 

double stepsPerRevolution = 360;
int error = 20;
Stepper myStepper(stepsPerRevolution, 2, 3, 4, 5);  // Pin inversion to make the library work
QMC5883LCompass compass;

void setup() {
  Serial.begin(9600);
  compass.init();
  myStepper.setSpeed(10);  

}

void loop() {

    int x, y, z, a, b;
    char myArray[3];

    compass.read();
  
    x = compass.getX();
    y = compass.getY();
    z = compass.getZ();
    
    a = compass.getAzimuth();
    
    b = compass.getBearing(a);

    compass.getDirection(myArray, a);
  
  
  float heading=atan2(x, y)/0.0174532925;
  if(heading < 0) heading+=360;
  heading=360-heading; // N=0/360, E=90, S=180, W=270

  

  int desired_direction = 180;

  if (heading < desired_direction - error ) {
    myStepper.step(-3);
  }
  
  if (heading > desired_direction + error){
    int new_dir = heading - desired_direction;
    myStepper.step(3);
  }
    Serial.println();
  Serial.print(" Current heading: ");
  Serial.print(heading);

  Serial.print(" Current heading: ");
  Serial.print(heading);

}

This is it for now, still a very early prototype, but very promising 🚀