tcxread 0.1.0 → 0.1.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (3) hide show
  1. checksums.yaml +4 -4
  2. data/lib/tcxread.rb +67 -6
  3. metadata +2 -2
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: dc0fbb7ddc6ca33b8c42dd160de524513ed81570dcf9f82c2b28410af1e036c9
4
- data.tar.gz: 9ee1726006b6f3a267bd3cc72f6accae4c7d275058a0998febdb039d365d8b98
3
+ metadata.gz: e42a89981c1614dec069270cb1315ee64d0c6a172de5c44a5370b5f5c8bd584f
4
+ data.tar.gz: dcee18bb770a1aa020d5ad8f67370f775a6f8d25139c39eb8576e76c463c1efd
5
5
  SHA512:
6
- metadata.gz: a5fcce73beceff1cfd7dadfaf6c5c9afa4c8e599ac2be1cf09181d505140b2d48c464f981705b20cf98b808023cd5bf04d442bdebf671d3b4c529c18270ab3d5
7
- data.tar.gz: 9537cdffd7f6b8973ca497841e8b818b330f318fcbebee83a2120a87a75f6a6b797438f7f074579cb02b811a980968d6307907b552c42597d3da5ae52266009b
6
+ metadata.gz: 72c0b8ba80f7cd524c91417123353e6d9523551050c513d55447ae1c6d73ff8add6af60cc6ec319d26af8aa237e7bcb40771f587653ffe92766f57be7d538194
7
+ data.tar.gz: 42a2ea64072c68e786e002a5dd0fa32c4547ac0503a4eb207537c3d9442148ca958fe9038b44b826033fa94ca4ddf80feaff92f8904745bfdad7aaba96c591ae
data/lib/tcxread.rb CHANGED
@@ -4,16 +4,14 @@ require "nokogiri"
4
4
  # workout data such as activities, laps, tracks, trackpoints, and integral metrics.
5
5
  class TCXRead
6
6
  attr_reader :total_distance_meters, :total_time_seconds, :total_calories,
7
- :total_ascent, :total_descent, :max_altitude, :average_heart_rate
7
+ :total_ascent, :total_descent, :max_altitude, :average_heart_rate,
8
+ :max_watts, :average_watts, :average_cadence
8
9
 
9
- # Initializes the TCXRead with the path to the TCX file.
10
- #
11
- # @param file_path [String] the path to the TCX file.
12
10
  def initialize(file_path)
13
11
  @file_path = file_path
14
12
  @doc = Nokogiri::XML(File.open(file_path))
13
+ @doc.root.add_namespace_definition('ns3', 'http://www.garmin.com/xmlschemas/ActivityExtension/v2')
15
14
 
16
- # Init the properties
17
15
  @total_distance_meters = 0
18
16
  @total_time_seconds = 0
19
17
  @total_calories = 0
@@ -21,6 +19,10 @@ class TCXRead
21
19
  @total_descent = 0
22
20
  @max_altitude = 0
23
21
  @average_heart_rate = 0
22
+ # use NA if no watts exist in the TCX file
23
+ @max_watts = 'NA'
24
+ @average_watts = 'NA'
25
+ @average_cadence = 0
24
26
 
25
27
  parse
26
28
  end
@@ -36,6 +38,8 @@ class TCXRead
36
38
  @total_calories = activities.sum { |activity| activity[:total_calories] }
37
39
  @total_ascent, @total_descent, @max_altitude = calculate_ascent_descent_and_max_altitude_from_activities(activities)
38
40
  @average_heart_rate = calculate_average_heart_rate_from_activities(activities)
41
+ @max_watts, @average_watts = calculate_watts_from_activities(activities)
42
+ @average_cadence = calculate_average_cadence_from_activities(activities)
39
43
  end
40
44
 
41
45
  { activities: activities }
@@ -112,7 +116,8 @@ class TCXRead
112
116
  distance_meters: trackpoint.xpath('xmlns:DistanceMeters').text.to_f,
113
117
  heart_rate: trackpoint.xpath('xmlns:HeartRateBpm/xmlns:Value').text.to_i,
114
118
  cadence: trackpoint.xpath('xmlns:Cadence').text.to_i,
115
- sensor_state: trackpoint.xpath('xmlns:SensorState').text
119
+ sensor_state: trackpoint.xpath('xmlns:SensorState').text,
120
+ watts: trackpoint.xpath('xmlns:Extensions/ns3:TPX/ns3:Watts').text.to_f
116
121
  }
117
122
  end
118
123
  tracks << trackpoints
@@ -226,4 +231,60 @@ class TCXRead
226
231
 
227
232
  heart_rate_count > 0 ? total_heart_rate.to_f / heart_rate_count : 0.0
228
233
  end
234
+
235
+ # Calculates the maximum and average watts from the activities.
236
+ #
237
+ # @param activities [Array<Hash>] an array of activity hashes.
238
+ # @return [Array<Float, Float>] an array containing maximum watts and average watts. Returns 'NA' for both if no watts data is available.
239
+ def calculate_watts_from_activities(activities)
240
+ max_watts = 0
241
+ total_watts = 0
242
+ watts_count = 0
243
+
244
+ activities.each do |activity|
245
+ activity[:laps].each do |lap|
246
+ lap[:tracks].flatten.each do |trackpoint|
247
+ watts = trackpoint[:watts]
248
+ if watts > 0
249
+ total_watts += watts
250
+ watts_count += 1
251
+ max_watts = watts if watts > max_watts
252
+ end
253
+ end
254
+ end
255
+ end
256
+
257
+ if watts_count > 0
258
+ average_watts = total_watts.to_f / watts_count
259
+ max_watts = max_watts
260
+ else
261
+ average_watts = 'NA'
262
+ max_watts = 'NA'
263
+ end
264
+
265
+ [max_watts, average_watts]
266
+ end
267
+
268
+ # Calculates the average cadence from the activities.
269
+ #
270
+ # @param activities [Array<Hash>] an array of activity hashes.
271
+ # @return [Float] the average cadence.
272
+ def calculate_average_cadence_from_activities(activities)
273
+ total_cadence = 0
274
+ cadence_count = 0
275
+
276
+ activities.each do |activity|
277
+ activity[:laps].each do |lap|
278
+ lap[:tracks].flatten.each do |trackpoint|
279
+ cadence = trackpoint[:cadence]
280
+ if cadence > 0
281
+ total_cadence += cadence
282
+ cadence_count += 1
283
+ end
284
+ end
285
+ end
286
+ end
287
+
288
+ cadence_count > 0 ? total_cadence.to_f / cadence_count : 0.0
289
+ end
229
290
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: tcxread
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.0
4
+ version: 0.1.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - firefly-cpp
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2024-07-20 00:00:00.000000000 Z
11
+ date: 2024-07-29 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: nokogiri