From cb1ad79ff44aab408649963a8bee45a521657623 Mon Sep 17 00:00:00 2001 From: Christian Treffs Date: Thu, 16 Nov 2017 23:00:41 +0100 Subject: [PATCH] Swiftlint struct rules applied --- .swiftlint.yml | 4 +- Sources/FirebladeECS/Entity+Component.swift | 14 +- Sources/FirebladeECS/Events.swift | 8 +- Sources/FirebladeECS/Family.swift | 39 +++--- Sources/FirebladeECS/FamilyTraitSet.swift | 28 ++-- Sources/FirebladeECS/Hashing.swift | 4 +- .../FirebladeECS/ManagedContiguousArray.swift | 8 +- Sources/FirebladeECS/Nexus+Component.swift | 16 ++- Sources/FirebladeECS/Nexus+Entity.swift | 2 +- Sources/FirebladeECS/Nexus+Family.swift | 10 +- Sources/FirebladeECS/Nexus.swift | 8 +- Sources/FirebladeECS/SparseSet.swift | 26 ++-- Tests/FirebladeECSTests/NexusTests.swift | 6 +- rules.md | 120 ------------------ 14 files changed, 96 insertions(+), 197 deletions(-) delete mode 100644 rules.md diff --git a/.swiftlint.yml b/.swiftlint.yml index 2408a83..b7c1dca 100644 --- a/.swiftlint.yml +++ b/.swiftlint.yml @@ -28,8 +28,8 @@ opt_in_rules: - multiline_arguments - multiline_parameters - nimble_operator - - no_extension_access_modifier - - no_grouping_extension + #- no_extension_access_modifier + #- no_grouping_extension - number_separator - object_literal - operator_usage_whitespace diff --git a/Sources/FirebladeECS/Entity+Component.swift b/Sources/FirebladeECS/Entity+Component.swift index 0c1cfa6..ac3a018 100644 --- a/Sources/FirebladeECS/Entity+Component.swift +++ b/Sources/FirebladeECS/Entity+Component.swift @@ -23,16 +23,16 @@ public extension Entity { return getComponentFunc } - func get(components _: A.Type, _: B.Type) -> (A, B) where A: Component, B: Component { - let a: A = get(component: A.self)! - let b: B = get(component: B.self)! + func get(components _: A.Type, _: B.Type) -> (A?, B?) where A: Component, B: Component { + let a: A? = get(component: A.self) + let b: B? = get(component: B.self) return (a, b) } - func get(components _: A.Type, _: B.Type, _: C.Type) -> (A, B, C) where A: Component, B: Component, C: Component { - let a: A = get(component: A.self)! - let b: B = get(component: B.self)! - let c: C = get(component: C.self)! + func get(components _: A.Type, _: B.Type, _: C.Type) -> (A?, B?, C?) where A: Component, B: Component, C: Component { + let a: A? = get(component: A.self) + let b: B? = get(component: B.self) + let c: C? = get(component: C.self) return (a, b, c) } } diff --git a/Sources/FirebladeECS/Events.swift b/Sources/FirebladeECS/Events.swift index 6c41db2..828e80c 100644 --- a/Sources/FirebladeECS/Events.swift +++ b/Sources/FirebladeECS/Events.swift @@ -27,20 +27,20 @@ public struct ComponentRemoved: ECSEvent { let from: EntityIdentifier } -struct FamilyMemberAdded: ECSEvent { +public struct FamilyMemberAdded: ECSEvent { let member: EntityIdentifier let toFamily: FamilyTraitSet } -struct FamilyMemberRemoved: ECSEvent { +public struct FamilyMemberRemoved: ECSEvent { let member: EntityIdentifier let from: FamilyTraitSet } -struct FamilyCreated: ECSEvent { +public struct FamilyCreated: ECSEvent { let family: FamilyTraitSet } -struct FamilyDestroyed: ECSEvent { +public struct FamilyDestroyed: ECSEvent { let family: FamilyTraitSet } diff --git a/Sources/FirebladeECS/Family.swift b/Sources/FirebladeECS/Family.swift index 659a4d2..4039441 100644 --- a/Sources/FirebladeECS/Family.swift +++ b/Sources/FirebladeECS/Family.swift @@ -23,27 +23,28 @@ public final class Family { let hash: FamilyTraitSetHash = traits.hashValue nexus?.onFamilyDeinit(traitHash: hash) } -} - -extension Family { - - public var count: Int { - return nexus?.members(of: self).count ?? 0 - } - - public final func canBecomeMember(_ entity: Entity) -> Bool { - return nexus?.canBecomeMember(entity, in: self) ?? false - } - - public final func isMember(_ entity: Entity) -> Bool { - return nexus?.isMember(entity, in: self) ?? false - } - - public final func isMember(_ entityId: EntityIdentifier) -> Bool { - return nexus?.isMember(entityId, in: self) ?? false - } var memberIds: UniformEntityIdentifiers { return nexus!.members(of: self) } } + +public extension Family { + + var count: Int { + return nexus?.members(of: self).count ?? 0 + } + + final func canBecomeMember(_ entity: Entity) -> Bool { + return nexus?.canBecomeMember(entity, in: self) ?? false + } + + final func isMember(_ entity: Entity) -> Bool { + return nexus?.isMember(entity, in: self) ?? false + } + + final func isMember(_ entityId: EntityIdentifier) -> Bool { + return nexus?.isMember(entityId, in: self) ?? false + } + +} diff --git a/Sources/FirebladeECS/FamilyTraitSet.swift b/Sources/FirebladeECS/FamilyTraitSet.swift index 9d534fa..db9b8b4 100644 --- a/Sources/FirebladeECS/FamilyTraitSet.swift +++ b/Sources/FirebladeECS/FamilyTraitSet.swift @@ -7,11 +7,11 @@ public struct FamilyTraitSet { - fileprivate let requiresAll: ComponentSet - fileprivate let excludesAll: ComponentSet - fileprivate let needsAtLeastOne: ComponentSet - fileprivate let setHash: Int - fileprivate let isEmptyAny: Bool + private let requiresAll: ComponentSet + private let excludesAll: ComponentSet + private let needsAtLeastOne: ComponentSet + private let setHash: Int + private let isEmptyAny: Bool public init(requiresAll: [Component.Type], excludesAll: [Component.Type], needsAtLeastOne: [Component.Type] = []) { @@ -30,30 +30,28 @@ public struct FamilyTraitSet { self.needsAtLeastOne = one self.excludesAll = none } -} -// MARK: - match -extension FamilyTraitSet { + // MARK: - match public func isMatch(components: ComponentSet) -> Bool { return hasAll(components) && hasNone(components) && hasOne(components) } - fileprivate func hasAll(_ components: ComponentSet) -> Bool { + private func hasAll(_ components: ComponentSet) -> Bool { return requiresAll.isSubset(of: components) } - fileprivate func hasNone(_ components: ComponentSet) -> Bool { + private func hasNone(_ components: ComponentSet) -> Bool { return excludesAll.isDisjoint(with: components) } - fileprivate func hasOne(_ components: ComponentSet) -> Bool { - if needsAtLeastOne.isEmpty { return true } + private func hasOne(_ components: ComponentSet) -> Bool { + if needsAtLeastOne.isEmpty { + return true + } return !needsAtLeastOne.isDisjoint(with: components) } -} -// MARK: - valid -fileprivate extension FamilyTraitSet { + // MARK: - valid static func isValid(requiresAll: ComponentSet, excludesAll: ComponentSet, atLeastOne: ComponentSet) -> Bool { return validAtLeastOneNonEmpty(requiresAll, atLeastOne) && requiresAll.isDisjoint(with: atLeastOne) && diff --git a/Sources/FirebladeECS/Hashing.swift b/Sources/FirebladeECS/Hashing.swift index 721a277..ed5eba4 100644 --- a/Sources/FirebladeECS/Hashing.swift +++ b/Sources/FirebladeECS/Hashing.swift @@ -42,7 +42,7 @@ public func hash(combine seed: Int, _ value: Int) -> Int { /// - Returns: combined hash value. public func hash(combine hashValues: S) -> Int where S.Element == Int { /// http://www.boost.org/doc/libs/1_65_1/doc/html/hash/reference.html#boost.hash_range_idp517643120 - return hashValues.reduce(0, { hash(combine: $0, $1) }) + return hashValues.reduce(0) { hash(combine: $0, $1) } } /// Calculates the combined hash value of the elements. This implementation is based on boost::hash_range. @@ -51,7 +51,7 @@ public func hash(combine hashValues: S) -> Int where S.Element == I /// - Returns: combined hash value. public func hash(combine hashables: H) -> Int where H.Element == Hashable { /// http://www.boost.org/doc/libs/1_65_1/doc/html/hash/reference.html#boost.hash_range_idp517643120 - return hashables.reduce(0, { hash(combine: $0, $1.hashValue) }) + return hashables.reduce(0) { hash(combine: $0, $1.hashValue) } } // MARK: - entity component hash diff --git a/Sources/FirebladeECS/ManagedContiguousArray.swift b/Sources/FirebladeECS/ManagedContiguousArray.swift index 0317408..ddc8b3a 100644 --- a/Sources/FirebladeECS/ManagedContiguousArray.swift +++ b/Sources/FirebladeECS/ManagedContiguousArray.swift @@ -22,8 +22,8 @@ public class ManagedContiguousArray: UniformStorage { public static var chunkSize: Int = 4096 public typealias Index = Int public typealias Element = Any - fileprivate var size: Int = 0 - fileprivate var store: ContiguousArray = [] + private var size: Int = 0 + private var store: ContiguousArray = [] public init(minCount: Int = chunkSize) { store = ContiguousArray(repeating: nil, count: minCount) @@ -46,7 +46,9 @@ public class ManagedContiguousArray: UniformStorage { store[index] = element } public func has(_ index: Index) -> Bool { - if store.count <= index { return false } + if store.count <= index { + return false + } return store[index] != nil } diff --git a/Sources/FirebladeECS/Nexus+Component.swift b/Sources/FirebladeECS/Nexus+Component.swift index f62de69..931fb68 100644 --- a/Sources/FirebladeECS/Nexus+Component.swift +++ b/Sources/FirebladeECS/Nexus+Component.swift @@ -12,7 +12,9 @@ extension Nexus { } public func has(componentId: ComponentIdentifier, entityIdx: EntityIndex) -> Bool { - guard let uniforms = componentsByType[componentId] else { return false } + guard let uniforms = componentsByType[componentId] else { + return false + } return uniforms.has(entityIdx) } @@ -67,7 +69,9 @@ extension Nexus { } public func get(component componentId: ComponentIdentifier, for entityId: EntityIdentifier) -> Component? { - guard let uniformComponents: UniformComponents = componentsByType[componentId] else { return nil } + guard let uniformComponents: UniformComponents = componentsByType[componentId] else { + return nil + } return uniformComponents.get(at: entityId.index) as? Component } @@ -76,8 +80,10 @@ extension Nexus { return get(componentId: componentId, entityIdx: entityId.index) } - fileprivate func get(componentId: ComponentIdentifier, entityIdx: EntityIndex) -> C? where C: Component { - guard let uniformComponents: UniformComponents = componentsByType[componentId] else { return nil } + private func get(componentId: ComponentIdentifier, entityIdx: EntityIndex) -> C? where C: Component { + guard let uniformComponents: UniformComponents = componentsByType[componentId] else { + return nil + } return uniformComponents.get(at: entityIdx) as? C } @@ -131,7 +137,7 @@ extension Nexus { report("clearing components form entity \(entityId) with no components") return true } - let removedAll: Bool = allComponents.reduce(true, { $0 && remove(component: $1, from: entityId) }) + let removedAll: Bool = allComponents.reduce(true) { $0 && remove(component: $1, from: entityId) } return removedAll } diff --git a/Sources/FirebladeECS/Nexus+Entity.swift b/Sources/FirebladeECS/Nexus+Entity.swift index 1fefaa0..e226aa3 100644 --- a/Sources/FirebladeECS/Nexus+Entity.swift +++ b/Sources/FirebladeECS/Nexus+Entity.swift @@ -12,7 +12,7 @@ extension Nexus { return entityStorage.filter { isValid(entity: $0.identifier) } } - fileprivate func nextEntityIdx() -> EntityIndex { + private func nextEntityIdx() -> EntityIndex { guard let nextReused: EntityIdentifier = freeEntities.popLast() else { return entityStorage.count } diff --git a/Sources/FirebladeECS/Nexus+Family.swift b/Sources/FirebladeECS/Nexus+Family.swift index f416495..4c84d58 100644 --- a/Sources/FirebladeECS/Nexus+Family.swift +++ b/Sources/FirebladeECS/Nexus+Family.swift @@ -52,7 +52,9 @@ public extension Nexus { func isMember(_ entityId: EntityIdentifier, in family: Family) -> Bool { let traitHash: FamilyTraitSetHash = family.traits.hashValue - guard let members: UniformEntityIdentifiers = familyMembersByTraitHash[traitHash] else { return false } + guard let members: UniformEntityIdentifiers = familyMembersByTraitHash[traitHash] else { + return false + } return members.has(entityId.index) } @@ -79,7 +81,9 @@ extension Nexus { let entityIdx: EntityIndex = entityId.index let traits: FamilyTraitSet = family.traits let traitHash: FamilyTraitSetHash = traits.hashValue - guard let componentIds: ComponentIdentifiers = componentIdsByEntity[entityIdx] else { return } + guard let componentIds: ComponentIdentifiers = componentIdsByEntity[entityIdx] else { + return + } let is_Member: Bool = isMember(entityId, in: family) if !isValid(entity: entityId) && is_Member { @@ -104,7 +108,7 @@ extension Nexus { } // MARK: - fileprivate extensions -fileprivate extension Nexus { +private extension Nexus { func get(family traits: FamilyTraitSet) -> Family? { let traitHash: FamilyTraitSetHash = traits.hashValue diff --git a/Sources/FirebladeECS/Nexus.swift b/Sources/FirebladeECS/Nexus.swift index 0c021de..3bd4f06 100644 --- a/Sources/FirebladeECS/Nexus.swift +++ b/Sources/FirebladeECS/Nexus.swift @@ -73,12 +73,12 @@ public class Nexus { freeEntities.removeAll() assert(entityStorage.isEmpty) - assert(componentsByType.values.reduce(0, { $0 + $1.count }) == 0) - assert(componentIdsByEntity.values.reduce(0, { $0 + $1.count }) == 0) + assert(componentsByType.values.reduce(0) { $0 + $1.count } == 0) + assert(componentIdsByEntity.values.reduce(0) { $0 + $1.count } == 0) assert(componentIdsByEntityLookup.isEmpty) assert(freeEntities.isEmpty) - assert(familiesByTraitHash.values.reduce(0, { $0 + $1.count }) == 0) - assert(familyMembersByTraitHash.values.reduce(0, { $0 + $1.count }) == 0) + assert(familiesByTraitHash.values.reduce(0) { $0 + $1.count } == 0) + assert(familyMembersByTraitHash.values.reduce(0) { $0 + $1.count } == 0) componentsByType.removeAll() componentIdsByEntity.removeAll() diff --git a/Sources/FirebladeECS/SparseSet.swift b/Sources/FirebladeECS/SparseSet.swift index 4fba428..e9fc996 100644 --- a/Sources/FirebladeECS/SparseSet.swift +++ b/Sources/FirebladeECS/SparseSet.swift @@ -7,12 +7,12 @@ public class SparseSet: UniformStorage, Sequence { public typealias Index = Int - fileprivate typealias DenseIndex = Int - fileprivate var size: Int = 0 - fileprivate var dense: ContiguousArray - fileprivate var sparse: [Index: DenseIndex] + private typealias DenseIndex = Int + private var size: Int = 0 + private var dense: ContiguousArray + private var sparse: [Index: DenseIndex] - fileprivate typealias Pair = (key: Index, value: Element) + private typealias Pair = (key: Index, value: Element) public init() { dense = ContiguousArray() @@ -33,7 +33,9 @@ public class SparseSet: UniformStorage, Sequence { } public func add(_ element: Element, at index: Index) { - if has(index) { return } + if has(index) { + return + } sparse[index] = count let entry: Pair = Pair(key: index, value: element) dense.append(entry) @@ -41,12 +43,16 @@ public class SparseSet: UniformStorage, Sequence { } public func get(at index: Index) -> Element? { - guard has(index) else { return nil } + guard has(index) else { + return nil + } return dense[sparse[index]!]!.value } public func remove(at index: Index) { - guard has(index) else { return } + guard has(index) else { + return + } let removeIdx: DenseIndex = sparse[index]! let lastIdx: DenseIndex = count - 1 dense.swapAt(removeIdx, lastIdx) @@ -81,7 +87,9 @@ public class SparseSet: UniformStorage, Sequence { } mutating public func next() -> Element? { - guard let next: Pair = iterator.next() as? Pair else { return nil } + guard let next: Pair = iterator.next() as? Pair else { + return nil + } return next.value as? Element } diff --git a/Tests/FirebladeECSTests/NexusTests.swift b/Tests/FirebladeECSTests/NexusTests.swift index d184c94..8917230 100644 --- a/Tests/FirebladeECSTests/NexusTests.swift +++ b/Tests/FirebladeECSTests/NexusTests.swift @@ -127,9 +127,9 @@ class NexusTests: XCTestCase { XCTAssert(e0.numComponents == 2) let (name, position) = e0.get(components: Name.self, Position.self) - XCTAssert(name.name == "myName") - XCTAssert(position.x == 99) - XCTAssert(position.y == 111) + XCTAssert(name?.name == "myName") + XCTAssert(position?.x == 99) + XCTAssert(position?.y == 111) e0.destroy() diff --git a/rules.md b/rules.md deleted file mode 100644 index 2f8d8b3..0000000 --- a/rules.md +++ /dev/null @@ -1,120 +0,0 @@ -+------------------------------------------+--------+-------------+------------------------+-------------+---------------+ -| identifier | opt-in | correctable | enabled in your config | kind | configuration | -+------------------------------------------+--------+-------------+------------------------+-------------+---------------+ -| array_init | yes | no | yes | lint | warning | -| attributes | yes | no | yes | style | warning, a... | -| block_based_kvo | no | no | yes | idiomatic | warning | -| class_delegate_protocol | no | no | yes | lint | warning | -| closing_brace | no | yes | yes | style | warning | -| closure_end_indentation | yes | no | yes | style | warning | -| closure_parameter_position | no | no | yes | style | warning | -| closure_spacing | yes | yes | yes | style | warning | -| colon | no | yes | yes | style | warning, f... | -| comma | no | yes | yes | style | warning | -| compiler_protocol_init | no | no | yes | lint | warning | -| conditional_returns_on_newline | yes | no | no | style | warning | -| contains_over_first_not_nil | yes | no | no | performance | warning | -| control_statement | no | no | yes | style | warning | -| custom_rules | no | no | yes | style | user-defin... | -| cyclomatic_complexity | no | no | yes | metrics | warning: 1... | -| discarded_notification_center_observer | no | no | yes | lint | warning | -| discouraged_direct_init | no | no | yes | lint | warning, t... | -| dynamic_inline | no | no | yes | lint | error | -| empty_count | yes | no | yes | performance | error | -| empty_enum_arguments | no | yes | yes | style | warning | -| empty_parameters | no | yes | yes | style | warning | -| empty_parentheses_with_trailing_closure | no | yes | yes | style | warning | -| explicit_enum_raw_value | yes | no | no | idiomatic | warning | -| explicit_init | yes | yes | yes | idiomatic | warning | -| explicit_top_level_acl | yes | no | no | idiomatic | warning | -| explicit_type_interface | yes | no | no | idiomatic | warning | -| extension_access_modifier | yes | no | yes | idiomatic | warning | -| fallthrough | no | no | yes | idiomatic | warning | -| fatal_error_message | yes | no | yes | idiomatic | warning | -| file_header | yes | no | no | style | warning, r... | -| file_length | no | no | yes | metrics | warning: 4... | -| first_where | yes | no | yes | performance | warning | -| for_where | no | no | yes | idiomatic | warning | -| force_cast | no | no | yes | idiomatic | error | -| force_try | no | no | yes | idiomatic | error | -| force_unwrapping | yes | no | no | idiomatic | warning | -| function_body_length | no | no | yes | metrics | warning: 4... | -| function_parameter_count | no | no | yes | metrics | warning: 5... | -| generic_type_name | no | no | yes | idiomatic | (min_lengt... | -| identifier_name | no | no | yes | style | (min_lengt... | -| implicit_getter | no | no | yes | style | warning | -| implicit_return | yes | yes | no | style | warning | -| implicitly_unwrapped_optional | yes | no | no | idiomatic | warning, m... | -| is_disjoint | no | no | yes | idiomatic | warning | -| joined_default_parameter | yes | yes | no | idiomatic | warning | -| large_tuple | no | no | yes | metrics | warning: 2... | -| leading_whitespace | no | yes | yes | style | warning | -| legacy_cggeometry_functions | no | yes | yes | idiomatic | warning | -| legacy_constant | no | yes | yes | idiomatic | warning | -| legacy_constructor | no | yes | yes | idiomatic | warning | -| legacy_nsgeometry_functions | no | yes | yes | idiomatic | warning | -| let_var_whitespace | yes | no | yes | style | warning | -| line_length | no | no | yes | metrics | warning: 2... | -| literal_expression_end_indentation | yes | no | yes | style | warning | -| mark | no | yes | yes | lint | warning | -| multiline_arguments | yes | no | no | style | warning, f... | -| multiline_parameters | yes | no | no | style | warning | -| multiple_closures_with_trailing_closure | no | no | yes | style | warning | -| nesting | no | no | yes | metrics | (type_leve... | -| nimble_operator | yes | yes | yes | idiomatic | warning | -| no_extension_access_modifier | yes | no | no | idiomatic | error | -| no_grouping_extension | yes | no | no | idiomatic | warning | -| notification_center_detachment | no | no | yes | lint | warning | -| number_separator | yes | yes | yes | style | warning, m... | -| object_literal | yes | no | yes | idiomatic | warning, i... | -| opening_brace | no | yes | yes | style | warning | -| operator_usage_whitespace | yes | yes | yes | style | warning | -| operator_whitespace | no | no | yes | style | warning | -| overridden_super_call | yes | no | yes | lint | warning, e... | -| override_in_extension | yes | no | no | lint | warning | -| pattern_matching_keywords | yes | no | yes | idiomatic | warning | -| private_outlet | yes | no | yes | lint | warning, a... | -| private_over_fileprivate | no | yes | yes | idiomatic | warning, v... | -| private_unit_test | no | no | yes | lint | warning: X... | -| prohibited_super_call | yes | no | yes | lint | warning, e... | -| protocol_property_accessors_order | no | yes | yes | style | warning | -| quick_discouraged_call | yes | no | no | lint | warning | -| quick_discouraged_focused_test | yes | no | no | lint | warning | -| quick_discouraged_pending_test | yes | no | no | lint | warning | -| redundant_discardable_let | no | yes | yes | style | warning | -| redundant_nil_coalescing | yes | yes | yes | idiomatic | warning | -| redundant_optional_initialization | no | yes | yes | idiomatic | warning | -| redundant_string_enum_value | no | no | yes | idiomatic | warning | -| redundant_void_return | no | yes | yes | idiomatic | warning | -| return_arrow_whitespace | no | yes | yes | style | warning | -| shorthand_operator | no | no | yes | style | error | -| single_test_class | yes | no | no | style | warning | -| sorted_first_last | yes | no | no | performance | warning | -| sorted_imports | yes | yes | yes | style | warning | -| statement_position | no | yes | yes | style | (statement... | -| strict_fileprivate | yes | no | no | idiomatic | warning | -| superfluous_disable_command | no | no | yes | lint | error | -| switch_case_alignment | no | no | yes | style | warning | -| switch_case_on_newline | yes | no | no | style | warning | -| syntactic_sugar | no | no | yes | idiomatic | warning | -| todo | no | no | yes | lint | warning | -| trailing_closure | yes | no | no | style | warning | -| trailing_comma | no | yes | yes | style | warning, m... | -| trailing_newline | no | yes | yes | style | warning | -| trailing_semicolon | no | yes | yes | idiomatic | warning | -| trailing_whitespace | no | yes | yes | style | warning, i... | -| type_body_length | no | no | yes | metrics | warning: 2... | -| type_name | no | no | yes | idiomatic | (min_lengt... | -| unneeded_break_in_switch | no | no | yes | idiomatic | warning | -| unneeded_parentheses_in_closure_argument | yes | yes | yes | style | warning | -| unused_closure_parameter | no | yes | yes | lint | warning | -| unused_enumerated | no | no | yes | idiomatic | warning | -| unused_optional_binding | no | no | yes | style | warning, i... | -| valid_ibinspectable | no | no | yes | lint | warning | -| vertical_parameter_alignment | no | no | yes | style | warning | -| vertical_parameter_alignment_on_call | yes | no | yes | style | warning | -| vertical_whitespace | no | yes | yes | style | warning, m... | -| void_return | no | yes | yes | style | warning | -| weak_delegate | no | no | yes | lint | warning | -| xctfail_message | no | no | yes | idiomatic | warning | -+------------------------------------------+--------+-------------+------------------------+-------------+---------------+