/* +------------------------------------------------------------------------+
   |                     Mobile Robot Programming Toolkit (MRPT)            |
   |                          https://www.mrpt.org/                         |
   |                                                                        |
   | Copyright (c) 2005-2023, Individual contributors, see AUTHORS file     |
   | See: https://www.mrpt.org/Authors - All rights reserved.               |
   | Released under BSD License. See: https://www.mrpt.org/License          |
   +------------------------------------------------------------------------+ */

#include "obs-precomp.h"  // Precompiled headers
//
#include <mrpt/math/matrix_serialization.h>	 // for << of matrices
#include <mrpt/obs/gnss_messages_topcon.h>

#include <ostream>

using namespace std;
using namespace mrpt::obs::gnss;

Message_TOPCON_PZS::Message_TOPCON_PZS() : gnss_message(TOPCON_PZS) {}

void Message_TOPCON_PZS::dumpToStream(std::ostream& out) const
{
	out << "\n[TopCon PZS datum]\n";
	out << mrpt::format(
		"  Longitude: %.09f deg  Latitude: %.09f deg Height: %.03f m (%.03f m "
		"without NBeam) \n",
		longitude_degrees, latitude_degrees, height_meters, RTK_height_meters);

	out << mrpt::format(
		" PZL-ID: %i  Angle trans: %.05f deg\n ", (int)nId, angle_transmitter);

	out << mrpt::format(" Fix: %i  ", (int)Fix);
	out << mrpt::format(" Error: %i ", (int)error);
	out << mrpt::format(
		" Battery levels: TX=%i  RX=%i\n ", TXBattery, RXBattery);

	out << mrpt::format(
		" hasCartesianPosVel= %s", hasCartesianPosVel ? "YES -> " : "NO\n");
	if (hasCartesianPosVel)
	{
		out << mrpt::format(
			" x=%f  y=%f  z=%f\n", cartesian_x, cartesian_y, cartesian_z);
		out << mrpt::format(
			" vx=%f  vy=%f  vz=%f\n", cartesian_vx, cartesian_vy, cartesian_vz);
	}
	out << mrpt::format("hasPosCov = %s", hasPosCov ? "YES\n" : "NO\n");
	if (hasPosCov)
		out << mrpt::format("%s\n", pos_covariance.inMatlabFormat().c_str());

	out << mrpt::format("hasVelCov = %s", hasVelCov ? "YES\n" : "NO\n");
	if (hasVelCov)
		out << mrpt::format("%s\n", vel_covariance.inMatlabFormat().c_str());

	out << mrpt::format("hasStats = %s", hasStats ? "YES: " : "NO\n");
	if (hasStats)
		out << mrpt::format(
			"GPS sats used: %i  GLONASS sats used: %i  RTK Fix progress:%i%%\n",
			(int)stats_GPS_sats_used, (int)stats_GLONASS_sats_used,
			(int)stats_rtk_fix_progress);
}

void Message_TOPCON_PZS::internal_writeToStream(
	mrpt::serialization::CArchive& out) const
{
	out << latitude_degrees << longitude_degrees << height_meters
		<< RTK_height_meters << PSigma << angle_transmitter << nId << Fix
		<< TXBattery << RXBattery << error << hasCartesianPosVel << cartesian_x
		<< cartesian_y << cartesian_z << cartesian_vx << cartesian_vy
		<< cartesian_vz << hasPosCov << pos_covariance << hasVelCov
		<< vel_covariance << hasStats << stats_GPS_sats_used
		<< stats_GLONASS_sats_used << stats_rtk_fix_progress;
}

void Message_TOPCON_PZS::internal_readFromStream(
	mrpt::serialization::CArchive& in)
{
	in >> latitude_degrees >> longitude_degrees >> height_meters >>
		RTK_height_meters >> PSigma >> angle_transmitter >> nId >> Fix >>
		TXBattery >> RXBattery >> error >> hasCartesianPosVel >> cartesian_x >>
		cartesian_y >> cartesian_z >> cartesian_vx >> cartesian_vy >>
		cartesian_vz >> hasPosCov >> pos_covariance >> hasVelCov >>
		vel_covariance >> hasStats >> stats_GPS_sats_used >>
		stats_GLONASS_sats_used >> stats_rtk_fix_progress;
}

// -------------
Message_TOPCON_SATS::Message_TOPCON_SATS() : gnss_message(TOPCON_SATS) {}
void Message_TOPCON_SATS::dumpToStream(std::ostream& out) const
{
	out << "\n[TopCon SATS datum]\n";
	out << mrpt::format(
		"  USI   ELEV    AZIM      (%u entries) \n",
		static_cast<unsigned int>(USIs.size()));

	ASSERT_(USIs.size() == AZs.size() && USIs.size() == ELs.size());
	for (size_t i = 0; i < USIs.size(); i++)
		out << mrpt::format(
			" %03i   %02i    %03i\n", (int)USIs[i], (int)ELs[i], (int)AZs[i]);
}

void Message_TOPCON_SATS::internal_writeToStream(
	mrpt::serialization::CArchive& out) const
{
	out << USIs << ELs << AZs;
}

void Message_TOPCON_SATS::internal_readFromStream(
	mrpt::serialization::CArchive& in)
{
	in >> USIs >> ELs >> AZs;
}
