Пример #1
0
        public void Pressure_by_depth_calc_test()
        {
            // Reference values according to
            // Algorithms for computation of fundamental properties of seawater.
            // Unesco technical papers in marine science vol. 44, 1983, pp. 28
            // https://darchive.mblwhoilibrary.org/bitstream/handle/1912/2470/059832eb.pdf

            double ref_salinity    = 35.0;
            double ref_temperature = 0.0;

            double[] ref_pressures = new double[] { 5E4, 1E5, 2E5, 3E5, 4E5, 5E5, 6E5, 7E5, 8E5, 9E5, 1E6 };
            double[] ref_lats_deg  = new double[] { 0.0, 30.0, 45.0, 60.0, 90.0 };
            double[,] ref_dpt_lat = { { 496.65, 992.12, 1979.55, 2962.43, 3940.88, 4915.04, 5885.03, 6850.95, 7812.93, 8771.07, 9725.47 },
                                      { 496.00, 990.81, 1976.94, 2958.52, 3935.68, 4908.56, 5877.27, 6841.92, 7802.63, 8759.51, 9712.65 },
                                      { 495.34, 989.50, 1974.33, 2954.61, 3930.49, 4902.08, 5869.51, 6832.89, 7792.33, 8747.95, 9699.84 },
                                      { 494.69, 988.19, 1971.72, 2950.71, 3925.30, 4895.60, 5861.76, 6823.86, 7782.04, 8736.40, 9687.84 },
                                      { 494.03, 986.88, 1969.11, 2946.81, 3920.10, 4889.13, 5854.01, 6814.84, 7771.76, 8724.85, 9674.23 } };

            for (int l_idx = 0; l_idx < ref_lats_deg.Length; l_idx++)
            {
                for (int p_idx = 0; p_idx < ref_pressures.Length; p_idx++)
                {
                    double g = PHX.Gravity_constant_wgs84_calc(ref_lats_deg[l_idx]);

                    // taking the water density in the midpoint to consider the compression of water
                    double rho   = PHX.Water_density_calc(ref_temperature, ref_pressures[p_idx] / 2.0, ref_salinity);
                    double h_est = PHX.Depth_by_pressure_calc(ref_pressures[p_idx], 0.0, rho, g);

                    // calculated values should deviate less than 0.07% of reference values
                    Assert.AreEqual(h_est, ref_dpt_lat[l_idx, p_idx], ref_dpt_lat[l_idx, p_idx] * 0.0007);
                }
            }
        }
Пример #2
0
        private void OnLBLA(object[] parameters)
        {
            // IC_D2H_LBLA $PRWLA,bID,baseLat,baseLon,[baseDpt],baseBat,pingerDataID,pingerData,TOAsecond,MSR_dB
            BaseIDs baseID = (parameters[0] == null) ? BaseIDs.BASE_INVALID : (BaseIDs)(int)parameters[0];

            double baseLat   = doubleNullChecker(parameters[1]);
            double baseLon   = doubleNullChecker(parameters[2]);
            double baseDepth = (parameters[3] == null) ? RWLT.DEFAULT_BASE_DPT_M : (double)parameters[3];

            double        baseBat = doubleNullChecker(parameters[4]);
            PingerDataIDs pDataID = (parameters[5] == null) ? PingerDataIDs.DID_INVALID : (PingerDataIDs)(int)parameters[5];
            double        pData   = doubleNullChecker(parameters[6]);
            double        TOAs    = doubleNullChecker(parameters[7]);
            double        MSR     = doubleNullChecker(parameters[8]);

            if ((baseID != BaseIDs.BASE_INVALID) &&
                (!double.IsNaN(baseLat)) &&
                (!double.IsNaN(baseLon)) &&
                (!double.IsNaN(baseDepth)))
            {
                if ((baseID == auxGNSSBuoyID) && (!AUXGNSSUsed))
                {
                    GNSS_RMCSentenceReceived(this,
                                             new RMCMessageEventArgs(0xFF,
                                                                     TalkerIdentifiers.GN,
                                                                     GetTimeStamp(),
                                                                     baseLat,
                                                                     baseLon,
                                                                     double.NaN,
                                                                     double.NaN,
                                                                     double.NaN,
                                                                     true));
                }

                LocationUpdatedEvent.Rise(this, new LocationUpdatedEventArgs(baseID.ToString().Replace('_', ' '),
                                                                             baseLat, baseLon, baseDepth,
                                                                             true,
                                                                             GetTimeStamp()));

                if (!double.IsNaN(MSR))
                {
                    BaseMSRs[baseID].Value = MSR;
                }

                if (!double.IsNaN(baseBat))
                {
                    BaseBatVoltages[baseID].Value = baseBat;
                }

                if (gravityAccNeedsUpdate)
                {
                    gravityAcc            = PHX.Gravity_constant_wgs84_calc(baseLat);
                    gravityAccNeedsUpdate = false;
                }

                if (pDataID == PingerDataIDs.DID_BAT)
                {
                    TargetBatVoltage.Value = pData;
                }
                else if (pDataID == PingerDataIDs.DID_TMP)
                {
                    TargetTemperature.Value = pData;
                    if (IsAutoSoundSpeed && TargetPressure.IsInitialized)
                    {
                        Soundspeed = PHX.Speed_of_sound_UNESCO_calc(TargetTemperature.Value, TargetPressure.Value / 2.0, salinity);
                    }
                }
                else if (pDataID == PingerDataIDs.DID_PRS)
                {
                    TargetPressure.Value = pData;
                    if (TargetTemperature.IsInitialized)
                    {
                        if (IsAutoSoundSpeed)
                        {
                            Soundspeed = PHX.Speed_of_sound_UNESCO_calc(TargetTemperature.Value, TargetPressure.Value / 2.0, salinity);
                        }

                        double rho = PHX.Water_density_calc(TargetTemperature.Value, TargetPressure.Value / 2.0, salinity);
                        // p0 is zero, because pinger calibrates surface pressure on start and transmits pressure relative to the surface
                        TargetDepth.Value = PHX.Depth_by_pressure_calc(TargetPressure.Value, 0, rho, gravityAcc);
                    }
                    else if (TargetPressure.IsInitialized)
                    {
                        TargetDepth.Value = PHX.Depth_by_pressure_calc(TargetPressure.Value, 0, PHX.PHX_FWTR_DENSITY_KGM3, gravityAcc);
                    }
                }
                else if (pDataID == PingerDataIDs.DID_CODE)
                {
                    TargetAlarm.Value = (PingerCodeIDs)Enum.ToObject(typeof(PingerCodeIDs), Convert.ToInt32(pData));
                }

                var bases = baseProcessor.ProcessBase(baseID, baseLat, baseLon, baseDepth, TOAs);
                if (bases != null)
                {
                    TryLocate(bases);
                }
            }

            OnSystemUpdate();
        }