From b2260e5220e7bfbd5098502dbaca0aa68222b79b Mon Sep 17 00:00:00 2001 From: Anton Tananaev Date: Sun, 12 Jul 2020 16:51:58 -0700 Subject: Support alternative location data --- .../org/traccar/protocol/TopinProtocolDecoder.java | 42 ++++++++++++++++++++-- .../traccar/protocol/TopinProtocolDecoderTest.java | 9 +++++ 2 files changed, 48 insertions(+), 3 deletions(-) diff --git a/src/main/java/org/traccar/protocol/TopinProtocolDecoder.java b/src/main/java/org/traccar/protocol/TopinProtocolDecoder.java index c817f500a..4042e348c 100644 --- a/src/main/java/org/traccar/protocol/TopinProtocolDecoder.java +++ b/src/main/java/org/traccar/protocol/TopinProtocolDecoder.java @@ -25,6 +25,7 @@ import org.traccar.NetworkMessage; import org.traccar.Protocol; import org.traccar.helper.BcdUtil; import org.traccar.helper.DateBuilder; +import org.traccar.helper.UnitsConverter; import org.traccar.model.CellTower; import org.traccar.model.Network; import org.traccar.model.Position; @@ -41,6 +42,8 @@ public class TopinProtocolDecoder extends BaseProtocolDecoder { } public static final int MSG_LOGIN = 0x01; + public static final int MSG_GPS_2 = 0x08; + public static final int MSG_GPS_OFFLINE_2 = 0x09; public static final int MSG_GPS = 0x10; public static final int MSG_GPS_OFFLINE = 0x11; public static final int MSG_STATUS = 0x13; @@ -77,6 +80,14 @@ public class TopinProtocolDecoder extends BaseProtocolDecoder { sendResponse(channel, dateBuffer.readableBytes(), type, dateBuffer); } + private double readCoordinate(ByteBuf buf) { + int degrees = buf.readUnsignedByte(); + boolean negative = (buf.getUnsignedByte(buf.readerIndex()) & 0xf0) > 0; + int decimal = buf.readUnsignedMedium() & 0x0fffff; + double result = degrees + decimal * 0.000001; + return negative ? -result : result; + } + @Override protected Object decode( Channel channel, SocketAddress remoteAddress, Object msg) throws Exception { @@ -95,9 +106,7 @@ public class TopinProtocolDecoder extends BaseProtocolDecoder { ByteBuf content = Unpooled.buffer(); content.writeByte(deviceSession != null ? 0x01 : 0x44); sendResponse(channel, length, type, content); - updateTime(channel, MSG_TIME_UPDATE); - return null; } else { deviceSession = getDeviceSession(channel, remoteAddress); @@ -106,7 +115,34 @@ public class TopinProtocolDecoder extends BaseProtocolDecoder { } } - if (type == MSG_GPS || type == MSG_GPS_OFFLINE) { + if (type == MSG_GPS_2 || type == MSG_GPS_OFFLINE_2) { + + if (buf.readableBytes() <= 2) { + return null; + } + + Position position = new Position(getProtocolName()); + position.setDeviceId(deviceSession.getDeviceId()); + + DateBuilder dateBuilder = new DateBuilder() + .setDate(buf.readUnsignedByte(), buf.readUnsignedByte(), buf.readUnsignedByte()) + .setTime(buf.readUnsignedByte(), buf.readUnsignedByte(), buf.readUnsignedByte()); + position.setTime(dateBuilder.getDate()); + + position.setValid(type == MSG_GPS_2); + position.setLatitude(readCoordinate(buf)); + position.setLongitude(readCoordinate(buf)); + + buf.skipBytes(4 + 4); // second coordinates + + position.setSpeed(UnitsConverter.knotsFromKph(buf.readUnsignedByte())); + position.setCourse(buf.readUnsignedByte() * 2); + + position.set(Position.KEY_SATELLITES, buf.readUnsignedByte()); + + return position; + + } else if (type == MSG_GPS || type == MSG_GPS_OFFLINE) { Position position = new Position(getProtocolName()); position.setDeviceId(deviceSession.getDeviceId()); diff --git a/src/test/java/org/traccar/protocol/TopinProtocolDecoderTest.java b/src/test/java/org/traccar/protocol/TopinProtocolDecoderTest.java index 0e04c0a19..8320b1388 100644 --- a/src/test/java/org/traccar/protocol/TopinProtocolDecoderTest.java +++ b/src/test/java/org/traccar/protocol/TopinProtocolDecoderTest.java @@ -10,9 +10,18 @@ public class TopinProtocolDecoderTest extends ProtocolTest { TopinProtocolDecoder decoder = new TopinProtocolDecoder(null); + verifyNull(decoder, binary( + "787801080D0A")); + verifyNull(decoder, binary( "78780d0103593390754169634d0d0a")); + verifyPosition(decoder, binary( + "7878200813081A0733211608C8D1710DED1D1608DFFB710E06D51039050100286489000D0A")); + + verifyPosition(decoder, binary( + "78782008140709121f36300d769f02058cfd300d771202058c6f0000000300005c99000d0a")); + verifyPosition(decoder, binary( "787812100A03170F32179C026B3F3E0C22AD651F34600D0A")); -- cgit v1.2.3