OpenMarine

Full Version: Seatalk Wired Autohelm Remote Control
You're currently viewing a stripped down version of our content. View the full version with proper formatting.
I have a wired seatalk remote control connected to a raspberry pi/macarthur hat.  I have edited the seatalk nmea0183-signalk hooks such that I can press the various buttons on the remote control and update variables in signalk which means I am talking.

Now that I am talking, I'm looking for advice on how I can make the compass mode in pypilot react to the +1, +10, -1 and -10 buttons.

I see the recent post about notifications but I'm told that seatalk does not work in version 4 of openplotter (I'm running version 3).  On a spare raspberry pi I installed openplotter 4 and have notifications 4.3 but I cannot find the pypilot options in the drop down actions so maybe that is not fully baked yet.

Hopefully there is some way I can make this work in version 3 while we wait on all the kinks to be worked out on version 4 of openplotter.

Thank you.
Pypilot actions in notifications app are added by the pypilot app, update both apps to last version and they should appear.

Porting all of this to OP3 is a lot of work. What RPi model do you have? we will add seatalk1 support to OP4 for RPI4 soon while we think about how to solve the problem in RPI5.
I have two RPi version 4's with 8 gig memory.  One is installed on my boat using OpenPlotter version 3.  The other I have hear at home as a backup and for testing.  I upgraded the home pi to OpenPlotter version 4 and I thought I installed all the pypilot updates but will try that again.

In the meantime, I did manage to get my SeaTalk autohelm remote control mostly working in OpenPlotter version 3.  I say mostly because there seems to be some weird buffering issue where the code being processed is one button push behind.  For example, I push -1 and the command does not come through.  I push it a second time and the command does come through.  I then push -10, and the -1 command comes through.  When I push -10 a second time, then I get the -10 command and so it goes where everything is one button push behind.

To make this work, I edited the index.js file for seatalk and then added the following program as 0x86.js in the seatalk directory (since /usr/local/bin/pypilot_client does not exist in version 4 this only works in 3).

/**
* Copyright 2024 Signal K <info@signalk.org> and contributors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
*    http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

'use strict'

const utils = require('@signalk/nmea0183-utilities')

/*
86  11  XX  YY        Raymarine Autohelm Wired Remote Control
                      -1  = 86 11 05 fa
                      -10 = 86 11 06 f9
                      +1  = 86 11 07 f8
                      +10 = 86 11 08 f7

                      tack port = 86 11 21 de
                      tack stbd = 86 11 22 dd
*/

module.exports = function (input) {
  const { id, sentence, parts, tags } = input

  if (parts.length != 4) {
    return null
  }

  var auto = parseInt(parts[1], 16)
  var a1 = parseInt(parts[2], 16)
  var a2 = parseInt(parts[3], 16)
  var pathValues = []

  if (auto != 0x11) {
    return null
  }

  var exec = require('child_process').exec
  const execSync = require('child_process').execSync
  var apheading = execSync('/usr/local/bin/pypilot_client ap.heading_command')
  const ahresult = '' + apheading
  var end = ahresult.length
  end--
  var start = -1
  start = ahresult.indexOf('=')
  if (start > 0) {
    start = start + 2
    var oldheading = ahresult.substring(start,end)
    var newheading = Number(oldheading)
    if (a1 == 0x05 && a2 == 0xfa) {
      newheading--
    }
    if (a1 == 0x06 && a2 == 0xf9) {
      newheading = newheading -10
    }
    if (a1 == 0x07 && a2 == 0xf8) {
      newheading++
    }
    if (a1 == 0x08 && a2 == 0xf7) {
      newheading = newheading + 10
    }
    if (a1 == 0x21 && a2 == 0xde) {
      newheading = newheading - 110
    }
    if (a1 == 0x22 && a2 == 0xdd) {
      newheading = newheading + 110
    }
    if (newheading > 359) {
      newheading = newheading - 360
    }
    if (newheading < 0) {
      newheading = newheading + 360
    }
    var nhstring = '/usr/local/bin/pypilot_client ap.heading_command='
    nhstring = nhstring + newheading
    execSync(nhstring)
  }

  pathValues.push({
    path: 'steering/autopilot/target/headingTrue',
    value: utils.transform(utils.float(newheading),'deg', 'rad'),
  })

  return {
    updates: [
    {
      source: tags.source,
      timestamp: tags.timestamp,
      values: pathValues,
    },
    ],
  }
}
It might create quite a bit of lag to invoke pypilot_client for heading changes.

Consider opening a tcp socket directly to pypilot to communicate?