gps_pvt 0.6.2 → 0.6.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 8a67291f7ea2d3146cace6c9e5f9c3262d89c1bd22534d6c147265c6189089c8
4
- data.tar.gz: 211daa142bb6282341367f0ccd375d66a0083e6de01ec7841ac4833795c3a6cc
3
+ metadata.gz: f9ab8f442240a2b92bfcb975ec6cb72000ec7d257bf7d5f41e0765905b9fa020
4
+ data.tar.gz: 52ed9e2141f4e0bc111da34be34b28414557fd02f003c3fbff84db571135ad1a
5
5
  SHA512:
6
- metadata.gz: 80a279b8018856c9d0d73b311c44efd97ce2794dc12353f10462a1b1b65aedc177ae6284fc324feb1980a02da2c2127ab8649058f840fc8279340f1152af3f62
7
- data.tar.gz: ce708fe585b811a99a8e0e42862df7bcac023d44859b17ea08b9e6816425845b5ab0a31b207b79a870ca6d52dc43313b00eb67a5b38746ace843c54264ceca1e
6
+ metadata.gz: 63cc7efd29e6e576c15380bd43550b427015f57d99a545b3373ef829d496e87df799feed2b6499c2bf336619a81bb193ddd1c350990cc85ee7c52a7aadf0d264
7
+ data.tar.gz: 7911e374e8d1f33f283be0fd7a59262bd1bd2d0315d631456e37659b4729812c260f3f65495bb6de851e8ac7246f148d47129080717aeccc715cc1138e17e158
data/exe/to_ubx ADDED
@@ -0,0 +1,213 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'gps_pvt'
4
+ require 'uri'
5
+ require 'gps_pvt/ubx'
6
+
7
+ # Convert file(s) to ubx format
8
+ # TODO currently only RINEX observation file is supported.
9
+
10
+ $stderr.puts <<__STRING__
11
+ Usage: #{__FILE__} GPS_file ... > as_you_like.ubx
12
+ As GPS_file, only rinex_obs(*.YYo) is currently supported.
13
+ (YY = last two digit of year)
14
+ File format is automatically determined based on its extention described in above parentheses.
15
+ If you want to specify its format manually, command options like --rinex_obs=file_name are available.
16
+ Supported RINEX versions are 2 and 3.
17
+ RXM-RAWX and RXM-SFRBX are included in output UBX if corresponding file(s) is given.
18
+ A file having additional ".gz" or ".Z" extension is recognized as a compressed file.
19
+ Major URL such as http(s)://... or ftp://... is acceptable as an input file name.
20
+ __STRING__
21
+
22
+ options = []
23
+ misc_options = {
24
+ :ubx_rawx => false
25
+ }
26
+
27
+ # check options and file format
28
+ files = ARGV.collect{|arg|
29
+ next [arg, nil] unless arg =~ /^--([^=]+)=?/
30
+ k, v = [$1.downcase.to_sym, $']
31
+ next [v, k] if [:rinex_nav, :rinex_obs].include?(k) # file type
32
+ options << [$1.to_sym, $']
33
+ nil
34
+ }.compact
35
+
36
+ # Check file existence and extension
37
+ files.collect!{|fname, ftype|
38
+ ftype ||= case fname
39
+ when /\.\d{2}[nhqg](?:\.gz)?$/; :rinex_nav
40
+ when /\.\d{2}o(?:\.gz)?$/; :rinex_obs
41
+ else
42
+ raise "Format cannot be guessed, use --(format, ex. rinex_obs)=#{fname}"
43
+ end
44
+ fname = proc{
45
+ next fname if File::exist?(fname)
46
+ if uri = URI::parse(fname) and !uri.instance_of?(URI::Generic) then
47
+ next uri
48
+ end
49
+ raise "File not found: #{fname}"
50
+ }.call
51
+ [fname, ftype]
52
+ }
53
+
54
+ options.reject!{|opt|
55
+ case opt[0]
56
+ when :ubx_rawx
57
+ misc_options[opt[0]] = opt[1]
58
+ true
59
+ else
60
+ false
61
+ end
62
+ }
63
+
64
+ rcv = GPS_PVT::Receiver::new(options)
65
+
66
+ obs = []
67
+ rcv.define_singleton_method(:run){|meas, t_meas, *args|
68
+ obs << [t_meas, meas]
69
+ }
70
+
71
+ # parse RINEX NAV
72
+ files.each{|fname, ftype|
73
+ case ftype
74
+ when :rinex_nav; rcv.parse_rinex_nav(fname)
75
+ end
76
+ }
77
+
78
+ # other files
79
+ files.each{|fname, ftype|
80
+ case ftype
81
+ when :rinex_obs; rcv.parse_rinex_obs(fname){}
82
+ end
83
+ }
84
+
85
+ obs.sort!{|a, b| a[0] <=> b[0]} # Sort by measurement time
86
+
87
+ glonass_freq_ch = proc{
88
+ freq0, delta = [:L1_frequency_base, :L1_frequency_gap].collect{|k|
89
+ GPS_PVT::GPS::SpaceNode_GLONASS.send(k)
90
+ }
91
+ proc{|freq| ((freq - freq0) / delta).to_i}
92
+ }.call
93
+
94
+ gen_raw = proc{|t_meas, meas| # Convert to RXM-RAW(0x10)
95
+ meas = meas.to_hash
96
+ ubx = [0xB5, 0x62, 0x02, 0x10, 0, 0]
97
+ ubx += [(t_meas.seconds * 1E3).to_i, t_meas.week].pack("Vv").unpack("C*")
98
+ ubx += [0] * 2
99
+ meas_ubx = meas.collect{|sat, items|
100
+ res = [0] * 24
101
+ setter = proc{|value, offset, len, str, pre_proc|
102
+ array = case value
103
+ when Array; value
104
+ when Symbol
105
+ [items[GPS_PVT::GPS::Measurement.const_get(value)]]
106
+ else
107
+ next nil
108
+ end
109
+ pre_proc.call(array) if pre_proc
110
+ next if array.empty?
111
+ array = array.pack(str).unpack("C*") if str
112
+ res[offset - 8, len] = array
113
+ }
114
+ svid = case sat
115
+ when 1..32, 120..158, 193..202 # GPS, SBAS, QZSS
116
+ sat
117
+ when (0x100 + 1)..(0x100 + 32) # GLONASS
118
+ sat - 0x100 + 64 # => 65..96
119
+ else
120
+ next nil # TODO Galileo, Beidou, ...
121
+ end
122
+
123
+ qi = 6
124
+ setter.call(:L1_CARRIER_PHASE,
125
+ 8, 8, "E", proc{|v| next if v[0]; qi = 4; v.clear})
126
+ setter.call(:L1_PSEUDORANGE,
127
+ 16, 8, "E", proc{|v| next if v[0]; qi = 0; v.clear})
128
+ setter.call(:L1_DOPPLER,
129
+ 24, 4, "e", proc{|v| next if v[0]; qi = 0; v.clear})
130
+ setter.call([svid, qi], 28, 2)
131
+ setter.call(:L1_SIGNAL_STRENGTH_dBHz,
132
+ 30, 1, nil, proc{|v| v.replace(v[0] ? [v[0].to_i] : [])})
133
+ setter.call(:L1_LOCK_SEC,
134
+ 31, 1, nil, proc{|v| v.replace(v[0] ? [(v[0] < 0) ? 1 : 0] : [0])})
135
+
136
+ res
137
+ }.compact
138
+ ubx[6 + 6] = meas_ubx.size
139
+ ubx += meas_ubx.flatten(1)
140
+ ubx += [0, 0]
141
+ GPS_PVT::UBX::update(ubx).pack("C*")
142
+ }
143
+
144
+ gen_rawx = proc{|t_meas, meas| # Convert to RXM-RAWX(0x15)
145
+ meas = meas.to_hash
146
+ ubx = [0xB5, 0x62, 0x02, 0x15, 0, 0]
147
+ ubx += [t_meas.seconds, t_meas.week].pack("Ev").unpack("C*")
148
+ ubx += [0] * 6
149
+ meas_ubx = meas.collect{|sat, items|
150
+ res = [0] * 32
151
+ setter = proc{|value, offset, len, str, pre_proc|
152
+ array = case value
153
+ when Array; value
154
+ when Symbol
155
+ [items[GPS_PVT::GPS::Measurement.const_get(value)]]
156
+ else
157
+ next nil
158
+ end
159
+ pre_proc.call(array) if pre_proc
160
+ next if array.empty?
161
+ array = array.pack(str).unpack("C*") if str
162
+ res[offset - 16, len] = array
163
+ }
164
+ sys, svid = case sat
165
+ when 1..32 # GPS
166
+ [0, sat]
167
+ when 120..158 # SBAS
168
+ [1, sat]
169
+ when 193..202 # QZSS
170
+ [5, sat]
171
+ when (0x100 + 1)..(0x100 + 32) # GLONASS
172
+ setter.call(:L1_FREQUENCY,
173
+ 39, 1, nil, proc{|v| v.replace(v[0] ? glonass_freq_ch.call(v[0]) : [7])})
174
+ [6, sat - 0x100]
175
+ else
176
+ next nil # TODO Galileo, Beidou, ...
177
+ end
178
+ setter.call([sys, svid], 36, 2)
179
+
180
+ trk_stat = 0
181
+ setter.call(:L1_PSEUDORANGE,
182
+ 16, 8, "E", proc{|v| v[0] ? (trk_stat |= 0x1) : v.clear})
183
+ setter.call(:L1_PSEUDORANGE_SIGMA,
184
+ 43, 1, nil, proc{|v|
185
+ b = (Math::log2(v[0] / 1E-2).to_i & 0xF) rescue 0x8
186
+ v.replace((trk_stat & 0x1 == 0x1) ? [b] : [])
187
+ })
188
+ setter.call(:L1_DOPPLER, 32, 4, "e")
189
+ setter.call(:L1_DOPPLER_SIGMA,
190
+ 45, 1, nil, proc{|v| v.replace(v[0] ? [Math::log2(v[0] / 2E-3).to_i & 0xF] : [0x8])})
191
+ setter.call(:L1_CARRIER_PHASE,
192
+ 24, 8, "E", proc{|v| v[0] ? (trk_stat |= 0x2) : v.clear})
193
+ setter.call(:L1_CARRIER_PHASE_SIGMA,
194
+ 44, 1, nil, proc{|v|
195
+ b = ((v[0] / 0.004).to_i & 0xF) rescue 0x8
196
+ v.replace((trk_stat & 0x2 == 0x2) ? [b] : [])
197
+ })
198
+ setter.call(:L1_SIGNAL_STRENGTH_dBHz,
199
+ 42, 1, nil, proc{|v| v.replace(v[0] ? [v[0].to_i] : [])})
200
+ setter.call(:L1_LOCK_SEC,
201
+ 40, 2, "v", proc{|v| v.replace(v[0] ? [(v[0] / 1E-3).to_i] : [])})
202
+ setter.call([trk_stat], 46, 1)
203
+
204
+ res
205
+ }.compact
206
+ ubx[6 + 11] = meas_ubx.size
207
+ ubx += meas_ubx.flatten(1)
208
+ ubx += [0, 0]
209
+ GPS_PVT::UBX::update(ubx).pack("C*")
210
+ }
211
+
212
+ gen = misc_options[:ubx_rawx] ? gen_rawx : gen_raw
213
+ obs.each{|*item| print gen.call(*item)}
@@ -34,6 +34,9 @@
34
34
 
35
35
  #include <cstddef>
36
36
  #include <vector>
37
+ #include <map>
38
+ #include <algorithm>
39
+ #include <stdexcept>
37
40
 
38
41
  /*
39
42
  * perform Neville's interpolation (with derivative)
@@ -118,4 +121,107 @@ Ty interpolate_Neville(
118
121
  return interpolate_Neville(x_given, y_given, x, y_buf, n)[0];
119
122
  }
120
123
 
124
+ template <class Tx, class Ty, class Tx_delta = Tx>
125
+ struct InterpolatableSet {
126
+ struct condition_t {
127
+ std::size_t max_x_size; ///< maximum number of data used for interpolation
128
+ Tx_delta max_dx_range; ///< maximum acceptable absolute difference between x and x0
129
+ };
130
+
131
+ typedef typename std::vector<std::pair<Tx, Ty> > buffer_t;
132
+ buffer_t buf;
133
+ Tx x0, x_lower, x_upper;
134
+ std::vector<Tx_delta> dx;
135
+ bool ready;
136
+
137
+ InterpolatableSet() : x0(), dx(), ready(false) {}
138
+
139
+ /**
140
+ * update interpolation source
141
+ * @param force_update If true, update is forcibly performed irrespective of current state
142
+ * @param cnd condition for source data selection
143
+ */
144
+ InterpolatableSet &update(
145
+ const Tx &x, const std::map<Tx, Ty> &xy_table,
146
+ const condition_t &cnd,
147
+ const bool &force_update = false){
148
+
149
+ do{
150
+ if(force_update){break;}
151
+ if(dx.size() <= 2){break;}
152
+ if(x < x_lower){break;}
153
+ if(x > x_upper){break;}
154
+ return *this;
155
+ }while(false);
156
+
157
+ // If the 1st and 2nd nearest items are changed, then recalculate interpolation targets.
158
+ struct {
159
+ const Tx &x_base;
160
+ bool operator()(
161
+ const typename std::map<Tx, Ty>::value_type &rhs,
162
+ const typename std::map<Tx, Ty>::value_type &lhs) const {
163
+ return std::abs(rhs.first - x_base) < std::abs(lhs.first - x_base);
164
+ }
165
+ } cmp = {(x0 = x)};
166
+
167
+ buf.resize(cnd.max_x_size);
168
+ dx.clear();
169
+ // extract x where x0-dx_range <= x <= x0+dx_range, then sort by ascending order of |x-x0|
170
+ for(typename buffer_t::const_iterator
171
+ it(buf.begin()),
172
+ it_end(std::partial_sort_copy(
173
+ xy_table.lower_bound(x - cnd.max_dx_range),
174
+ xy_table.upper_bound(x + cnd.max_dx_range),
175
+ buf.begin(), buf.end(), cmp));
176
+ it != it_end; ++it){
177
+ dx.push_back(it->first - x0);
178
+ }
179
+ if(dx.size() >= 2){ // calculate a necessary condition to update samples for new x
180
+ // According to Nth nearest points, x range in which the order of extracted samples
181
+ // is retained can be calculated.
182
+ bool ascending(buf[0].first <= buf[1].first);
183
+ Tx &xa(ascending ? x_lower : x_upper), &xb(ascending ? x_upper : x_lower);
184
+ xa = x0;
185
+ for(std::size_t i(2); i < buf.size(); ++i){
186
+ if(ascending ? (dx[1] <= dx[i]) : (dx[1] >= dx[i])){continue;}
187
+ xa = x0 + (dx[1] + dx[i]) / 2;
188
+ break;
189
+ }
190
+ xb = x0 + (dx[0] + dx[1]) / 2;
191
+ }
192
+ ready = (dx.size() >= cnd.max_x_size);
193
+
194
+ return *this;
195
+ }
196
+
197
+ template <class Ty2, class Ty2_Iterator>
198
+ Ty2 interpolate2(
199
+ const Tx &x, const Ty2_Iterator &y,
200
+ Ty2 *derivative = NULL) const {
201
+ int order(dx.size() - 1);
202
+ do{
203
+ if(order > 0){break;}
204
+ if((order == 0) && (!derivative)){return y[0];}
205
+ throw std::range_error("Insufficient records for interpolation");
206
+ }while(false);
207
+ std::vector<Ty2> y_buf(order), dy_buf(order);
208
+ interpolate_Neville(
209
+ dx, y, x - x0, y_buf, order,
210
+ &dy_buf, derivative ? 1 : 0);
211
+ if(derivative){*derivative = dy_buf[0];}
212
+ return y_buf[0];
213
+ }
214
+
215
+ Ty interpolate(const Tx &x, Ty *derivative = NULL) const {
216
+ struct second_iterator : public buffer_t::const_iterator {
217
+ second_iterator(const typename buffer_t::const_iterator &it)
218
+ : buffer_t::const_iterator(it) {}
219
+ const Ty &operator[](const int &n) const {
220
+ return buffer_t::const_iterator::operator[](n).second;
221
+ }
222
+ } y_it(buf.begin());
223
+ return interpolate2(x, y_it, derivative);
224
+ }
225
+ };
226
+
121
227
  #endif /* __INTERPOLATE_H__ */
@@ -41,7 +41,6 @@
41
41
  #include <cstring>
42
42
  #include <map>
43
43
  #include <set>
44
- #include <algorithm>
45
44
  #include <stdexcept>
46
45
 
47
46
  #include "util/text_helper.h"
@@ -61,22 +60,15 @@ struct SP3_Product {
61
60
  typedef std::map<GPS_Time<FloatT>, prop_t> history_t;
62
61
  history_t pos_history;
63
62
  history_t vel_history;
64
-
65
- static const struct interpolate_cnd_t {
66
- std::size_t max_epochs; ///< maximum number of epochs used for interpolation
67
- FloatT max_delta_t; ///< maximum acceptable absolute time difference between t and epoch
68
- } interpolate_cnd_default;
63
+
64
+ typedef InterpolatableSet<GPS_Time<FloatT>, prop_t, FloatT> interpolator_t;
65
+ typedef typename interpolator_t::condition_t interpolate_cnd_t;
66
+ static const interpolate_cnd_t interpolate_cnd_default;
69
67
 
70
68
  mutable struct {
71
- struct target_t {
72
-
73
- typedef typename std::vector<std::pair<GPS_Time<FloatT>, prop_t> > buf_t;
74
- buf_t buf;
75
- GPS_Time<FloatT> t0;
76
- std::vector<FloatT> dt;
77
- bool updated_full_cnd;
69
+ struct target_t : public interpolator_t {
78
70
 
79
- target_t() : t0(0, 0), updated_full_cnd(false) {}
71
+ target_t() : interpolator_t() {}
80
72
 
81
73
  /**
82
74
  * update interpolation source
@@ -88,58 +80,13 @@ struct SP3_Product {
88
80
  const bool &force_update = false,
89
81
  const interpolate_cnd_t &cnd = interpolate_cnd_default){
90
82
 
91
- FloatT t_diff(t0 - t);
92
- if((!force_update)
93
- && ((std::abs(t_diff) <= 10)
94
- || ((dt.size() >= 2)
95
- && (std::abs(t_diff + dt[0]) <= std::abs(t_diff + dt[1])))) ){
96
- return *this;
97
- }
98
-
99
- // If the 1st and 2nd nearest epochs are changed, then recalculate interpolation targets.
100
- struct {
101
- const GPS_Time<FloatT> &t_base;
102
- bool operator()(
103
- const typename history_t::value_type &rhs,
104
- const typename history_t::value_type &lhs) const {
105
- return std::abs(rhs.first - t_base) < std::abs(lhs.first - t_base);
106
- }
107
- } cmp = {(t0 = t)};
108
-
109
- buf.resize(cnd.max_epochs);
110
- dt.clear();
111
- // extract t where t0-dt <= t <= t0+dt, then sort by ascending order of |t-t0|
112
- for(typename buf_t::const_iterator
113
- it(buf.begin()),
114
- it_end(std::partial_sort_copy(
115
- history.lower_bound(t - cnd.max_delta_t),
116
- history.upper_bound(t + cnd.max_delta_t),
117
- buf.begin(), buf.end(), cmp));
118
- it != it_end; ++it){
119
- dt.push_back(it->first - t0);
120
- }
121
- updated_full_cnd = (dt.size() >= cnd.max_epochs);
122
-
83
+ if((!force_update) && (std::abs(t - interpolator_t::x0) <= 10)){return *this;}
84
+ interpolator_t::update(t, history, cnd, force_update);
123
85
  return *this;
124
86
  }
125
87
 
126
- template <class Ty, class Ty_Array>
127
- Ty interpolate(
128
- const GPS_Time<FloatT> &t, const Ty_Array &y,
129
- Ty *derivative = NULL) const {
130
- int order(dt.size() - 1);
131
- do{
132
- if(order > 0){break;}
133
- if((order == 0) && (!derivative)){return y[0];}
134
- throw std::range_error("Insufficient records for interpolation");
135
- }while(false);
136
- std::vector<Ty> y_buf(order), dy_buf(order);
137
- interpolate_Neville(
138
- dt, y, t - t0, y_buf, order,
139
- &dy_buf, derivative ? 1 : 0);
140
- if(derivative){*derivative = dy_buf[0];}
141
- return y_buf[0];
142
- }
88
+ typedef typename interpolator_t::buffer_t buf_t;
89
+
143
90
  Vector3<FloatT> interpolate_xyz(
144
91
  const GPS_Time<FloatT> &t,
145
92
  Vector3<FloatT> *derivative = NULL) const {
@@ -149,8 +96,8 @@ struct SP3_Product {
149
96
  const Vector3<FloatT> &operator[](const int &n) const {
150
97
  return buf_t::const_iterator::operator[](n).second.xyz;
151
98
  }
152
- } xyz(buf.begin());
153
- return interpolate(t, xyz, derivative);
99
+ } xyz(interpolator_t::buf.begin());
100
+ return interpolator_t::interpolate2(t, xyz, derivative);
154
101
  }
155
102
  FloatT interpolate_clk(
156
103
  const GPS_Time<FloatT> &t,
@@ -161,8 +108,8 @@ struct SP3_Product {
161
108
  const FloatT &operator[](const int &n) const {
162
109
  return buf_t::const_iterator::operator[](n).second.clk;
163
110
  }
164
- } clk(buf.begin());
165
- return interpolate(t, clk, derivative);
111
+ } clk(interpolator_t::buf.begin());
112
+ return interpolator_t::interpolate2(t, clk, derivative);
166
113
  }
167
114
  } pos_clk, vel_rate;
168
115
  } subset;
@@ -175,7 +122,7 @@ struct SP3_Product {
175
122
  bool precheck(const GPS_Time<FloatT> &t) const {
176
123
  // Only position/clock is checked, because velocity/rate can be calculated based on pos/clk.
177
124
  subset.pos_clk.update(t, pos_history);
178
- return subset.pos_clk.updated_full_cnd;
125
+ return subset.pos_clk.ready;
179
126
  }
180
127
 
181
128
  typename GPS_SpaceNode<FloatT>::SatelliteProperties::constellation_t
@@ -381,8 +328,11 @@ static typename GPS_Solver_Base<FloatT>::satellite_t select_ ## sys( \
381
328
  template <class FloatT>
382
329
  const typename SP3_Product<FloatT>::per_satellite_t::interpolate_cnd_t
383
330
  SP3_Product<FloatT>::per_satellite_t::interpolate_cnd_default = {
384
- 9, // max_epochs
385
- 60 * 60 * 2, // max_delta_t, default is 2 hr = 15 min interval records; (2 hr * 2 / (9 - 1) = 15 min)
331
+ 9, // maximum number of epochs used for interpolation
332
+ /* maximum acceptable absolute time difference between t and epoch,
333
+ * default is 2 hr = 15 min interval records; (2 hr * 2 / (9 - 1) = 15 min)
334
+ */
335
+ 60 * 60 * 2,
386
336
  };
387
337
 
388
338
  template <class FloatT>
data/gps_pvt.gemspec CHANGED
@@ -53,6 +53,9 @@ Gem::Specification.new do |spec|
53
53
  }.flatten
54
54
  }.call
55
55
 
56
+ spec.rdoc_options << '--exclude=ext/ninja-scan-light'
57
+ spec.extra_rdoc_files = []
58
+
56
59
  # Uncomment to register a new dependency of your gem
57
60
  # spec.add_dependency "example-gem", "~> 1.0"
58
61
  spec.add_development_dependency "rake"
@@ -410,7 +410,7 @@ class Receiver
410
410
  @solver.sbas_space_node.ionospheric_grid_points(prn)].each{|str|
411
411
  $stderr.puts str
412
412
  } if @debug[:SBAS_IGP]
413
- end
413
+ end if t_meas
414
414
  when :GLONASS
415
415
  next unless eph = eph_glonass_list[prn]
416
416
  leap_sec = @solver.gps_space_node.is_valid_utc ?
@@ -508,10 +508,10 @@ class Receiver
508
508
  {
509
509
  :L1_PSEUDORANGE => [16, 8, "E", proc{|v| (trk_stat & 0x1 == 0x1) ? v : nil}],
510
510
  :L1_PSEUDORANGE_SIGMA => [43, 1, nil, proc{|v|
511
- (trk_stat & 0x1 == 0x1) ? (1E-2 * (v[0] & 0xF)) : nil
511
+ (trk_stat & 0x1 == 0x1) ? (1E-2 * (1 << (v[0] & 0xF))) : nil
512
512
  }],
513
513
  :L1_DOPPLER => [32, 4, "e"],
514
- :L1_DOPPLER_SIGMA => [45, 1, nil, proc{|v| 2E-3 * (v[0] & 0xF)}],
514
+ :L1_DOPPLER_SIGMA => [45, 1, nil, proc{|v| 2E-3 * (1 << (v[0] & 0xF))}],
515
515
  :L1_CARRIER_PHASE => [24, 8, "E", proc{|v| (trk_stat & 0x2 == 0x2) ? v : nil}],
516
516
  :L1_CARRIER_PHASE_SIGMA => [44, 1, nil, proc{|v|
517
517
  (trk_stat & 0x2 == 0x2) ? (0.004 * (v[0] & 0xF)) : nil
@@ -1,5 +1,5 @@
1
- # frozen_string_literal: true
2
-
3
- module GPS_PVT
4
- VERSION = "0.6.2"
5
- end
1
+ # frozen_string_literal: true
2
+
3
+ module GPS_PVT
4
+ VERSION = "0.6.3"
5
+ end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: gps_pvt
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.6.2
4
+ version: 0.6.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - fenrir(M.Naruoka)
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2022-08-03 00:00:00.000000000 Z
11
+ date: 2022-08-19 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rake
@@ -44,6 +44,7 @@ email:
44
44
  - fenrir.naru@gmail.com
45
45
  executables:
46
46
  - gps_pvt
47
+ - to_ubx
47
48
  extensions:
48
49
  - ext/gps_pvt/extconf.rb
49
50
  extra_rdoc_files: []
@@ -57,6 +58,7 @@ files:
57
58
  - bin/console
58
59
  - bin/setup
59
60
  - exe/gps_pvt
61
+ - exe/to_ubx
60
62
  - ext/gps_pvt/Coordinate/Coordinate_wrap.cxx
61
63
  - ext/gps_pvt/GPS/GPS_wrap.cxx
62
64
  - ext/gps_pvt/SylphideMath/SylphideMath_wrap.cxx
@@ -109,7 +111,8 @@ metadata:
109
111
  homepage_uri: https://github.com/fenrir-naru/gps_pvt
110
112
  source_code_uri: https://github.com/fenrir-naru/gps_pvt
111
113
  post_install_message:
112
- rdoc_options: []
114
+ rdoc_options:
115
+ - "--exclude=ext/ninja-scan-light"
113
116
  require_paths:
114
117
  - lib
115
118
  required_ruby_version: !ruby/object:Gem::Requirement