1   /* Copyright 2002-2025 CS GROUP
2    * Licensed to CS GROUP (CS) under one or more
3    * contributor license agreements.  See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * CS licenses this file to You under the Apache License, Version 2.0
6    * (the "License"); you may not use this file except in compliance with
7    * the License.  You may obtain a copy of the License at
8    *
9    *   http://www.apache.org/licenses/LICENSE-2.0
10   *
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS,
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   * See the License for the specific language governing permissions and
15   * limitations under the License.
16   */
17  package org.orekit.files.ccsds.ndm.tdm;
18  
19  import java.io.IOException;
20  
21  import org.orekit.files.ccsds.definitions.TimeConverter;
22  import org.orekit.files.ccsds.section.AbstractWriter;
23  import org.orekit.files.ccsds.section.KvnStructureKey;
24  import org.orekit.files.ccsds.section.XmlStructureKey;
25  import org.orekit.files.ccsds.utils.FileFormat;
26  import org.orekit.files.ccsds.utils.generation.Generator;
27  import org.orekit.time.AbsoluteDate;
28  import org.orekit.utils.units.Unit;
29  
30  
31  /**
32   * Writer for CCSDS Tracking Data Message observation block.
33   *
34   * @author Luc Maisonobe
35   * @since 11.0
36   */
37  class ObservationsBlockWriter extends AbstractWriter {
38  
39      /** Observation block. */
40      private final ObservationsBlock observationsBlock;
41  
42      /** Converter for dates. */
43      private final TimeConverter timeConverter;
44  
45      /** Metadata to use for interpreting observations. */
46      private final TdmMetadata metadata;
47  
48      /** Converter for {@link RangeUnits#RU Range Units}. */
49      private final RangeUnitsConverter converter;
50  
51      /** Simple constructor.
52       * @param observationsBlock observation block to write
53       * @param timeConverter converter for dates
54       * @param metadata metadata to use for interpreting observations
55       * @param converter converter for {@link RangeUnits#RU Range Units} (may be null if there
56       * are no range observations in {@link RangeUnits#RU Range Units})
57       */
58      ObservationsBlockWriter(final ObservationsBlock observationsBlock, final TimeConverter timeConverter,
59                              final TdmMetadata metadata, final RangeUnitsConverter converter) {
60          super(XmlStructureKey.data.name(), KvnStructureKey.DATA.name());
61          this.observationsBlock = observationsBlock;
62          this.timeConverter     = timeConverter;
63          this.metadata          = metadata;
64          this.converter         = converter;
65      }
66  
67      /** {@inheritDoc} */
68      @Override
69      protected void writeContent(final Generator generator) throws IOException {
70  
71          generator.writeComments(observationsBlock.getComments());
72  
73          // write the data
74          for (final Observation observation : observationsBlock.getObservations()) {
75              final ObservationType type     = observation.getType();
76              final AbsoluteDate    date     = observation.getEpoch();
77              final double          siValue  = observation.getMeasurement();
78              final double          rawValue = type.siToRaw(converter, metadata, date, siValue);
79              if (generator.getFormat() == FileFormat.KVN) {
80                  final StringBuilder builder = new StringBuilder();
81                  builder.append(generator.dateToString(timeConverter, date));
82                  builder.append(' ');
83                  builder.append(generator.doubleToString(rawValue));
84                  generator.writeEntry(observation.getType().name(), builder.toString(), null, false);
85              } else {
86                  generator.enterSection(TdmDataKey.observation.name());
87                  generator.writeEntry(TdmDataKey.EPOCH.name(), timeConverter, date, true, true);
88                  generator.writeEntry(type.name(), rawValue, Unit.ONE, true);
89                  generator.exitSection();
90              }
91          }
92  
93      }
94  
95  }