aixm 0.3.4 → 0.3.5

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.
@@ -10,7 +10,11 @@ module AIXM
10
10
  # obstacle_group = AIXM.obstacle_group(
11
11
  # source: String or nil # see remarks below
12
12
  # name: String or nil
13
- # )
13
+ # ).tap do |obstacle_group|
14
+ # obstacle_group.xy_accuracy = AIXM.d or nil
15
+ # obstacle_group.z_accuracy = AIXM.d or nil
16
+ # obstacle_group.remarks = String or nil
17
+ # end
14
18
  # obstacle_group.add_obstacle( # add an obstacle to the group
15
19
  # AIXM.obstacle
16
20
  # )
@@ -24,32 +28,33 @@ module AIXM
24
28
  # linked_to: AIXM.obstacle,
25
29
  # link_type: LINK_TYPES
26
30
  # )
27
- # obstacle_group.id # UUID v3 calculated from the group payload
28
- #
29
- # As soon as an obstacle is added to a group, it's extended with new the
30
- # following attributes:
31
- # * group - the group this object belongs to
32
- # * linked_to - obstacle this one is linked to (if any)
33
- # * link_type - type of link between the two obstacles (if any)
34
31
  #
35
- # The source set on the group is handed down to each of it's obstacles and
36
- # will be used there unless the individual obstacle overrides it with a
37
- # different source of it's own.
32
+ # Please note: As soon as an obstacle is added to an obstacle group, the
33
+ # +xy_accuracy+ and +z_accuracy+ of the obstacle group overwrite whatever
34
+ # is set on the individual obstacles!
38
35
  #
39
36
  # @see https://github.com/openflightmaps/ofmx/wiki/Obstacle
40
37
  class ObstacleGroup < Feature
41
38
  public_class_method :new
42
39
 
43
- LINK_TYPES = {
44
- CABLE: :cable,
45
- SOLID: :solid,
46
- OTHER: :other
47
- }.freeze
40
+ # @!method source
41
+ # @return [String] reference to source of the feature data
42
+ # @!method name
43
+ # @return [String] obstacle group name
44
+ # @!method xy_accuracy
45
+ # @return [AIXM::D, nil] margin of error for circular base center point
46
+ # @!method z_accuracy
47
+ # @return [AIXM::D, nil] margin of error for top point
48
+ %i(source name xy_accuracy z_accuracy).each do |method|
49
+ define_method method do
50
+ instance_variable_get(:"@#{method}") || obstacles.first&.send(method)
51
+ end
52
+ end
48
53
 
49
- # @return [String] group name
50
- attr_reader :name
54
+ # @return [String, nil] free text remarks
55
+ attr_reader :remarks
51
56
 
52
- # @return [Array<AIXM::Feature::Obstacle>] obstacles in this group
57
+ # @return [Array<AIXM::Feature::Obstacle>] obstacles in this obstacle group
53
58
  attr_reader :obstacles
54
59
 
55
60
  def initialize(source: nil, name: nil)
@@ -68,18 +73,32 @@ module AIXM
68
73
  @name = value&.uptrans
69
74
  end
70
75
 
71
- # Add an obstacle to the group and optionally link it to another obstacle
72
- # from the group.
76
+ def xy_accuracy=(value)
77
+ fail(ArgumentError, "invalid xy accuracy") unless value.nil? || value.is_a?(AIXM::D)
78
+ @xy_accuracy = value
79
+ end
80
+
81
+ def z_accuracy=(value)
82
+ fail(ArgumentError, "invalid z accuracy") unless value.nil? || value.is_a?(AIXM::D)
83
+ @z_accuracy = value
84
+ end
85
+
86
+ def remarks=(value)
87
+ @remarks = value&.to_s
88
+ end
89
+
90
+ # Add an obstacle to the obstacle group and optionally link it to another
91
+ # obstacle from the obstacle group.
73
92
  #
74
93
  # @param obstacle [AIXM::Feature::Obstacle] obstacle instance
75
94
  # @param linked_to [Symbol, AIXM::Feature::Obstacle, nil] Either:
76
- # * :previous - link to the obstacle last added to the group
95
+ # * :previous - link to the obstacle last added to the obstacle group
77
96
  # * AIXM::Feature::Obstacle - link to this specific obstacle
78
- # @param link_type [Symbol, nil] type of link (see {LINK_TYPES})
97
+ # @param link_type [Symbol, nil] type of link (see
98
+ # {AIXM::Feature::Obstacle::LINK_TYPES})
79
99
  # @return [self]
80
100
  def add_obstacle(obstacle, linked_to: nil, link_type: :other)
81
- obstacle.extend AIXM::Feature::Obstacle::Grouped
82
- obstacle.send(:group=, self)
101
+ obstacle.send(:obstacle_group=, self)
83
102
  if linked_to && link_type
84
103
  obstacle.send(:linked_to=, linked_to == :previous ? @obstacles.last : linked_to)
85
104
  obstacle.send(:link_type=, link_type)
@@ -88,15 +107,37 @@ module AIXM
88
107
  self
89
108
  end
90
109
 
91
- # @return [String] UUID version 3 group identifier
92
- def id
93
- ([name] + @obstacles.map { |o| o.xy.to_s }).to_uuid
110
+ # @return [String] UID markup
111
+ def to_uid
112
+ builder = Builder::XmlMarkup.new(indent: 2)
113
+ builder.OgrUid do |ogr_uid|
114
+ ogr_uid.txtName(name)
115
+ ogr_uid.geoLat(obstacles.first.xy.lat(AIXM.schema))
116
+ ogr_uid.geoLong(obstacles.first.xy.long(AIXM.schema))
117
+ end
94
118
  end
95
- alias_method :to_uid, :id # features need "to_uid" for "==" to work
96
119
 
97
120
  # @return [String] AIXM or OFMX markup
98
121
  def to_xml
99
- @obstacles.map { |o| o.to_xml }.join
122
+ builder = Builder::XmlMarkup.new(indent: 2)
123
+ if AIXM.ofmx?
124
+ builder.comment! "Obstacle group: #{name}".strip
125
+ builder.Ogr({ source: (source if AIXM.ofmx?) }.compact) do |ogr|
126
+ ogr << to_uid.indent(2)
127
+ ogr.codeDatum('WGE')
128
+ if xy_accuracy
129
+ ogr.valGeoAccuracy(xy_accuracy.dist.trim)
130
+ ogr.uomGeoAccuracy(xy_accuracy.unit.upcase.to_s)
131
+ end
132
+ if z_accuracy
133
+ ogr.valElevAccuracy(z_accuracy.to_ft.dist.round)
134
+ ogr.uomElevAccuracy('FT')
135
+ end
136
+ ogr.txtRmk(remarks) if remarks
137
+ end
138
+ end
139
+ obstacles.each { |o| builder << o.to_xml(delegate: false) }
140
+ builder.target!
100
141
  end
101
142
  end
102
143
 
@@ -15,6 +15,21 @@ module AIXM
15
15
  "Ø" => "Oe"
16
16
  }.freeze
17
17
 
18
+ # @!method then_if
19
+ # Same as +Object#then+ but only applied if the condition is true.
20
+ #
21
+ # @example
22
+ # "foobar".then_if(false) { |s| s.gsub(/o/, 'i') } # => "foobar"
23
+ # "foobar".then_if(true) { |s| s.gsub(/o/, 'i') } # => "fiibar"
24
+ #
25
+ # @note This is a refinement for +Object+
26
+ # @return [Object]
27
+ refine Object do
28
+ def then_if(condition, &block)
29
+ condition ? self.then(&block) : self
30
+ end
31
+ end
32
+
18
33
  # @!method to_digest
19
34
  # Builds a 4 byte hex digest from the Array payload.
20
35
  #
@@ -1,3 +1,3 @@
1
1
  module AIXM
2
- VERSION = "0.3.4".freeze
2
+ VERSION = "0.3.5".freeze
3
3
  end
@@ -69,6 +69,11 @@ module AIXM
69
69
  end
70
70
  end
71
71
 
72
+ # @return [AIXM::Component::Geometry::Point] convert to point
73
+ def to_point
74
+ AIXM.point(xy: self)
75
+ end
76
+
72
77
  # @return [AIXM::D] distance as calculated by use of the Haversine formula
73
78
  def distance(other)
74
79
  if self == other
@@ -87,7 +87,7 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
87
87
  <xsd:documentation>Reference to the source AIP document.</xsd:documentation>
88
88
  </xsd:annotation>
89
89
  <xsd:restriction base="xsd:string">
90
- <xsd:pattern value="[A-Z]{2,4}\|(GEN|ENR|AD|AIRAC|VAC)\|.+\|[\d-]+\|\d+"/>
90
+ <xsd:pattern value="[A-Z]{2,4}\|(GEN|ENR|AD|AIRAC|VAC|OTHER)\|.+\|[\d-]+\|\d+"/>
91
91
  </xsd:restriction>
92
92
  </xsd:simpleType>
93
93
  <xsd:simpleType name="codeAcftEngineNoBase">
@@ -172,6 +172,8 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
172
172
  <xsd:enumeration value="EQUIPMENT-RNAV"/>
173
173
  <xsd:enumeration value="EQUIPMENT-833"/>
174
174
  <xsd:enumeration value="PROCEDURE"/>
175
+ <xsd:enumeration value="AIRMODEL"/>
176
+ <xsd:enumeration value="WINCH"/>
175
177
  <xsd:enumeration value="OTHER"/>
176
178
  </xsd:restriction>
177
179
  </xsd:simpleType>
@@ -5377,6 +5377,72 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
5377
5377
  </xsd:sequence>
5378
5378
  <xsd:attributeGroup ref="Changes"/>
5379
5379
  </xsd:complexType>
5380
+ <xsd:complexType name="ObstacleGroupType">
5381
+ <xsd:annotation>
5382
+ <xsd:documentation>Obstacle group</xsd:documentation>
5383
+ </xsd:annotation>
5384
+ <xsd:sequence>
5385
+ <xsd:element name="OgrUid" type="ObstacleGroupUidType">
5386
+ <xsd:annotation>
5387
+ <xsd:documentation>a version of Obstacle group</xsd:documentation>
5388
+ </xsd:annotation>
5389
+ </xsd:element>
5390
+ <xsd:element name="codeDatum" type="codeDatum">
5391
+ <xsd:annotation>
5392
+ <xsd:documentation>Datum</xsd:documentation>
5393
+ </xsd:annotation>
5394
+ </xsd:element>
5395
+ <xsd:element name="valGeoAccuracy" type="valDistHorz" minOccurs="0">
5396
+ <xsd:annotation>
5397
+ <xsd:documentation>Geographical accuracy</xsd:documentation>
5398
+ </xsd:annotation>
5399
+ </xsd:element>
5400
+ <xsd:element name="uomGeoAccuracy" type="uomDistHorz" minOccurs="0">
5401
+ <xsd:annotation>
5402
+ <xsd:documentation>Unit of measurement [geographical accuracy]</xsd:documentation>
5403
+ </xsd:annotation>
5404
+ </xsd:element>
5405
+ <xsd:element name="valElevAccuracy" type="valDistVer" minOccurs="0">
5406
+ <xsd:annotation>
5407
+ <xsd:documentation>Elevation accuracy</xsd:documentation>
5408
+ </xsd:annotation>
5409
+ </xsd:element>
5410
+ <xsd:element name="uomElevAccuracy" type="uomElev" minOccurs="0">
5411
+ <xsd:annotation>
5412
+ <xsd:documentation>Unit of measurement [elevation accuracy]</xsd:documentation>
5413
+ </xsd:annotation>
5414
+ </xsd:element>
5415
+ <xsd:element name="txtRmk" type="txtRmk" minOccurs="0">
5416
+ <xsd:annotation>
5417
+ <xsd:documentation>Remark</xsd:documentation>
5418
+ </xsd:annotation>
5419
+ </xsd:element>
5420
+ </xsd:sequence>
5421
+ <xsd:attribute ref="source"/>
5422
+ </xsd:complexType>
5423
+ <xsd:complexType name="ObstacleGroupUidType">
5424
+ <xsd:annotation>
5425
+ <xsd:documentation>Obstacle group - UID</xsd:documentation>
5426
+ </xsd:annotation>
5427
+ <xsd:sequence>
5428
+ <xsd:element name="txtName" type="txtName">
5429
+ <xsd:annotation>
5430
+ <xsd:documentation>Name</xsd:documentation>
5431
+ </xsd:annotation>
5432
+ </xsd:element>
5433
+ <xsd:element name="geoLat" type="geoLat">
5434
+ <xsd:annotation>
5435
+ <xsd:documentation>Group reference point latitude</xsd:documentation>
5436
+ </xsd:annotation>
5437
+ </xsd:element>
5438
+ <xsd:element name="geoLong" type="geoLong">
5439
+ <xsd:annotation>
5440
+ <xsd:documentation>Group reference point longitude</xsd:documentation>
5441
+ </xsd:annotation>
5442
+ </xsd:element>
5443
+ </xsd:sequence>
5444
+ <xsd:attribute ref="mid"/>
5445
+ </xsd:complexType>
5380
5446
  <xsd:complexType name="ObstacleType">
5381
5447
  <xsd:annotation>
5382
5448
  <xsd:documentation>Obstacle</xsd:documentation>
@@ -5402,7 +5468,7 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
5402
5468
  <xsd:documentation>Type details</xsd:documentation>
5403
5469
  </xsd:annotation>
5404
5470
  </xsd:element>
5405
- <xsd:element name="codeGroup" type="codeYesNo" minOccurs="0">
5471
+ <xsd:element name="codeGroup" type="codeYesNo" minOccurs="0">
5406
5472
  <xsd:annotation>
5407
5473
  <xsd:documentation>Group of obstacles</xsd:documentation>
5408
5474
  </xsd:annotation>
@@ -5432,36 +5498,16 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
5432
5498
  <xsd:documentation>Datum</xsd:documentation>
5433
5499
  </xsd:annotation>
5434
5500
  </xsd:element>
5435
- <xsd:element name="valGeoAccuracy" type="valDistHorz" minOccurs="0">
5436
- <xsd:annotation>
5437
- <xsd:documentation>Geographical accuracy</xsd:documentation>
5438
- </xsd:annotation>
5439
- </xsd:element>
5440
- <xsd:element name="uomGeoAccuracy" type="uomDistHorz" minOccurs="0">
5441
- <xsd:annotation>
5442
- <xsd:documentation>Unit of measurement [geographical accuracy]</xsd:documentation>
5443
- </xsd:annotation>
5444
- </xsd:element>
5445
5501
  <xsd:element name="valElev" type="valDistVer">
5446
5502
  <xsd:annotation>
5447
5503
  <xsd:documentation>Elevation</xsd:documentation>
5448
5504
  </xsd:annotation>
5449
5505
  </xsd:element>
5450
- <xsd:element name="valElevAccuracy" type="valDistVer" minOccurs="0">
5451
- <xsd:annotation>
5452
- <xsd:documentation>Elevation accuracy</xsd:documentation>
5453
- </xsd:annotation>
5454
- </xsd:element>
5455
5506
  <xsd:element name="valHgt" type="valDistVer" minOccurs="0">
5456
5507
  <xsd:annotation>
5457
5508
  <xsd:documentation>Height</xsd:documentation>
5458
5509
  </xsd:annotation>
5459
5510
  </xsd:element>
5460
- <xsd:element name="codeHgtAccuracy" type="codeYesNo" minOccurs="0">
5461
- <xsd:annotation>
5462
- <xsd:documentation>Height accuracy</xsd:documentation>
5463
- </xsd:annotation>
5464
- </xsd:element>
5465
5511
  <xsd:element name="valGeoidUndulation" type="valDistVer" minOccurs="0">
5466
5512
  <xsd:annotation>
5467
5513
  <xsd:documentation>Geoid undulation</xsd:documentation>
@@ -5472,24 +5518,19 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
5472
5518
  <xsd:documentation>Unit of measurement [vertical distance]</xsd:documentation>
5473
5519
  </xsd:annotation>
5474
5520
  </xsd:element>
5475
- <xsd:element name="valRadius" type="valDistHorz">
5476
- <xsd:annotation>
5477
- <xsd:documentation>Radius</xsd:documentation>
5478
- </xsd:annotation>
5479
- </xsd:element>
5480
- <xsd:element name="uomRadius" type="uomDistHorz">
5521
+ <xsd:element name="codeHgtAccuracy" type="codeYesNo" minOccurs="0">
5481
5522
  <xsd:annotation>
5482
- <xsd:documentation>Unit of measurement [radius]</xsd:documentation>
5523
+ <xsd:documentation>Height accuracy</xsd:documentation>
5483
5524
  </xsd:annotation>
5484
5525
  </xsd:element>
5485
- <xsd:element name="codeGroupId" type="uuid" minOccurs="0">
5526
+ <xsd:element name="valRadius" type="valDistHorz" minOccurs="0">
5486
5527
  <xsd:annotation>
5487
- <xsd:documentation>Group identifier (identical on all group members)</xsd:documentation>
5528
+ <xsd:documentation>Radius</xsd:documentation>
5488
5529
  </xsd:annotation>
5489
5530
  </xsd:element>
5490
- <xsd:element name="txtGroupName" type="txtGroupName" minOccurs="0">
5531
+ <xsd:element name="uomRadius" type="uomDistHorz" minOccurs="0">
5491
5532
  <xsd:annotation>
5492
- <xsd:documentation>Group name or short description</xsd:documentation>
5533
+ <xsd:documentation>Unit of measurement [radius]</xsd:documentation>
5493
5534
  </xsd:annotation>
5494
5535
  </xsd:element>
5495
5536
  <xsd:element name="ObsUidLink" type="ObstacleUidType" minOccurs="0">
@@ -5528,13 +5569,17 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
5528
5569
  </xsd:annotation>
5529
5570
  </xsd:element>
5530
5571
  </xsd:sequence>
5531
- <xsd:attribute ref="source"/>
5532
5572
  </xsd:complexType>
5533
5573
  <xsd:complexType name="ObstacleUidType">
5534
5574
  <xsd:annotation>
5535
5575
  <xsd:documentation>Obstacle - UID</xsd:documentation>
5536
5576
  </xsd:annotation>
5537
5577
  <xsd:sequence>
5578
+ <xsd:element name="OgrUid" type="ObstacleGroupUidType">
5579
+ <xsd:annotation>
5580
+ <xsd:documentation>a version of Obstacle group</xsd:documentation>
5581
+ </xsd:annotation>
5582
+ </xsd:element>
5538
5583
  <xsd:element name="geoLat" type="geoLat">
5539
5584
  <xsd:annotation>
5540
5585
  <xsd:documentation>Latitude</xsd:documentation>
@@ -8431,7 +8476,7 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
8431
8476
  <xsd:documentation>Time reference system</xsd:documentation>
8432
8477
  </xsd:annotation>
8433
8478
  </xsd:element>
8434
- <xsd:element name="codeType" type="codeTypeHrNavAid">
8479
+ <xsd:element name="codeType" type="codeTypeHrNavAid" minOccurs="0">
8435
8480
  <xsd:annotation>
8436
8481
  <xsd:documentation>Type</xsd:documentation>
8437
8482
  </xsd:annotation>
@@ -100,6 +100,7 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
100
100
  <xsd:element name="Oaa" type="OrganisationAuthorityAddressType"/>
101
101
  <xsd:element name="Oae" type="AirspaceObstacleType"/>
102
102
  <xsd:element name="Oas" type="OrganisationAuthorityAssociationType"/>
103
+ <xsd:element name="Ogr" type="ObstacleGroupType"/>
103
104
  <xsd:element name="Obs" type="ObstacleType"/>
104
105
  <xsd:element name="Ofa" type="AirspaceAuthorityType"/>
105
106
  <xsd:element name="Oil" type="OilType"/>
@@ -47,8 +47,8 @@ module AIXM
47
47
  def vertical_limits
48
48
  AIXM.vertical_limits(
49
49
  upper_z: AIXM.z(65, :qne),
50
- lower_z: AIXM.z(45, :qne),
51
50
  max_z: AIXM.z(6000, :qnh),
51
+ lower_z: AIXM.z(45, :qne),
52
52
  min_z: AIXM.z(3000, :qfe)
53
53
  )
54
54
  end
@@ -401,6 +401,9 @@ module AIXM
401
401
  AIXM.obstacle_group(
402
402
  name: "Mirmande éoliennes"
403
403
  ).tap do |obstacle_group|
404
+ obstacle_group.xy_accuracy = AIXM.d(50, :m)
405
+ obstacle_group.z_accuracy = AIXM.d(10, :m)
406
+ obstacle_group.remarks = "Extension planned"
404
407
  obstacle_group.add_obstacle(
405
408
  AIXM.obstacle(
406
409
  name: "La Teissonière 1",
@@ -410,8 +413,6 @@ module AIXM
410
413
  z: AIXM.z(1764, :qnh)
411
414
  ).tap do |obstacle|
412
415
  obstacle.height = AIXM.d(80, :m)
413
- obstacle.xy_accuracy = AIXM.d(50, :m)
414
- obstacle.z_accuracy = AIXM.d(10, :m)
415
416
  obstacle.height_accurate = false
416
417
  end
417
418
  )
@@ -424,8 +425,6 @@ module AIXM
424
425
  z: AIXM.z(1738 , :qnh)
425
426
  ).tap do |obstacle|
426
427
  obstacle.height = AIXM.d(80, :m)
427
- obstacle.xy_accuracy = AIXM.d(50, :m)
428
- obstacle.z_accuracy = AIXM.d(10, :m)
429
428
  obstacle.height_accurate = false
430
429
  end
431
430
  )
@@ -436,6 +435,9 @@ module AIXM
436
435
  AIXM.obstacle_group(
437
436
  name: "Droitwich longwave antenna"
438
437
  ).tap do |obstacle_group|
438
+ obstacle_group.xy_accuracy = AIXM.d(0, :m)
439
+ obstacle_group.z_accuracy = AIXM.d(0, :ft)
440
+ obstacle_group.remarks = "Destruction planned"
439
441
  obstacle_group.add_obstacle(
440
442
  AIXM.obstacle(
441
443
  name: "Droitwich LW north",
@@ -445,8 +447,6 @@ module AIXM
445
447
  z: AIXM.z(848 , :qnh)
446
448
  ).tap do |obstacle|
447
449
  obstacle.height = AIXM.d(700, :ft)
448
- obstacle.xy_accuracy = AIXM.d(0, :m)
449
- obstacle.z_accuracy = AIXM.d(0, :ft)
450
450
  obstacle.height_accurate = true
451
451
  end
452
452
  )
@@ -459,8 +459,6 @@ module AIXM
459
459
  z: AIXM.z(848 , :qnh)
460
460
  ).tap do |obstacle|
461
461
  obstacle.height = AIXM.d(700, :ft)
462
- obstacle.xy_accuracy = AIXM.d(0, :m)
463
- obstacle.z_accuracy = AIXM.d(0, :ft)
464
462
  obstacle.height_accurate = true
465
463
  end,
466
464
  linked_to: :previous,