diff --git a/CHANGES.md b/CHANGES.md index 9cd37d0f5e..9a544f449e 100644 --- a/CHANGES.md +++ b/CHANGES.md @@ -15,6 +15,7 @@ Core Grammars: - enh(delphi) add support for character strings with non-decimal numerics [Jonah Jeleniewski][] - fix(javascript) incorrect function name highlighting [CY Fung][] - fix(1c) fix escaped symbols "+-;():=,[]" literals [Vitaly Barilko][] +- fix(swift) correctly highlight generics and conformances in type definitions [Bradley Mackey][] New Grammars: diff --git a/src/languages/swift.js b/src/languages/swift.js index d68503ea6c..95fbb05d70 100644 --- a/src/languages/swift.js +++ b/src/languages/swift.js @@ -457,6 +457,37 @@ export default function(hljs) { end: /}/ }; + const TYPE_DECLARATION = { + begin: [ + /(struct|protocol|class|extension|enum|actor)/, + /\s+/, + Swift.identifier, + /\s*/, + ], + beginScope: { + 1: "keyword", + 3: "title.class" + }, + keywords: KEYWORDS, + contains: [ + GENERIC_PARAMETERS, + ...KEYWORD_MODES, + { + begin: /:/, + end: /\{/, + keywords: KEYWORDS, + contains: [ + { + scope: "title.class.inherited", + match: Swift.typeIdentifier, + }, + ...KEYWORD_MODES, + ], + relevance: 0, + }, + ] + }; + // Add supported submodes to string interpolation. for (const variant of STRING.variants) { const interpolation = variant.contains.find(mode => mode.label === "interpol"); @@ -490,19 +521,7 @@ export default function(hljs) { ...COMMENTS, FUNCTION_OR_MACRO, INIT_SUBSCRIPT, - { - beginKeywords: 'struct protocol class extension enum actor', - end: '\\{', - excludeEnd: true, - keywords: KEYWORDS, - contains: [ - hljs.inherit(hljs.TITLE_MODE, { - className: "title.class", - begin: /[A-Za-z$_][\u00C0-\u02B80-9A-Za-z$_]*/ - }), - ...KEYWORD_MODES - ] - }, + TYPE_DECLARATION, OPERATOR_DECLARATION, PRECEDENCEGROUP, { diff --git a/test/markup/swift/functions.expect.txt b/test/markup/swift/functions.expect.txt index c533960ebd..2398aaef43 100644 --- a/test/markup/swift/functions.expect.txt +++ b/test/markup/swift/functions.expect.txt @@ -23,7 +23,7 @@ subscript<X: A>(_ p: @attribute inout (x: Int, var: Int) = (0, 0)) { } -protocol Comparable: Equatable { +protocol Comparable: Equatable { static func < (lhs: Self, rhs: Self) -> Bool static func <= (lhs: Self, rhs: Self) -> Bool diff --git a/test/markup/swift/ownership.expect.txt b/test/markup/swift/ownership.expect.txt index af5aae9d16..d04b63c1fe 100644 --- a/test/markup/swift/ownership.expect.txt +++ b/test/markup/swift/ownership.expect.txt @@ -5,9 +5,9 @@ doStuffUniquely(with: consume x) _ = copy x doStuff(with: copy x) -struct MoveOnly: ~Copyable {} +struct MoveOnly: ~Copyable {} -struct B: P { +struct B: P { func foo(x: borrowing Foo, y: consuming Foo) } func foo(_: borrowing Foo) @@ -20,4 +20,4 @@ doStuff(with: copy x) consuming func foo() borrowing func foo() mutating func foo() -} \ No newline at end of file +} diff --git a/test/markup/swift/swiftui.expect.txt b/test/markup/swift/swiftui.expect.txt index ba23fe24b6..ce514f88fc 100644 --- a/test/markup/swift/swiftui.expect.txt +++ b/test/markup/swift/swiftui.expect.txt @@ -1,5 +1,5 @@ @main -struct MyApp: App { +struct MyApp: App { var body: some Scene { WindowGroup { #if os(iOS) diff --git a/test/markup/swift/type-definition.expect.txt b/test/markup/swift/type-definition.expect.txt index 1d39754e22..08e5a79ac8 100644 --- a/test/markup/swift/type-definition.expect.txt +++ b/test/markup/swift/type-definition.expect.txt @@ -1,6 +1,61 @@ class TestClass {} +class TestClass: Superclass {} +class TestClass: Superclass, Conform1, Conform2 {} +class TestClass<T> {} +class TestClass<T, U> {} +class TestClass<repeat each T> {} +class TestClass<T> where T: Equatable {} +class TestClass<T>: Superclass where T: Equatable {} + +class +MoreThanOneLine +{} + +class +MoreThanOneLineInherit +: +Superclass +{} + +class +MoreThanOneLineInherit +: +Superclass1, +Superclass2 +{} + +class +MoreThanOneLineInherit: +Superclass +{} + +final class +MoreThanOneLineGeneric<T> +where +T: Param +{} + +class Outer { + class Inner<T> {} + class InnerInherit: Superclass {} +} + struct TestStruct {} +struct TestStruct: Conform {} +struct TestStruct<T, U> {} + enum TestEnum {} +enum TestEnum: Conform {} +enum TestEnum<T, U> {} + actor TestActor {} +actor TestActor: Conform {} +actor TestActor<T, U> {} + extension TestExtension {} +extension TestExtension: Conform {} +extension TestExtension<T, U> {} + protocol TestProtocol {} +protocol TestProtocol: Conform {} +protocol TestProtocol<T, U> {} diff --git a/test/markup/swift/type-definition.txt b/test/markup/swift/type-definition.txt index 6469569a80..ef3edb11aa 100644 --- a/test/markup/swift/type-definition.txt +++ b/test/markup/swift/type-definition.txt @@ -1,6 +1,61 @@ class TestClass {} +class TestClass: Superclass {} +class TestClass: Superclass, Conform1, Conform2 {} +class TestClass {} +class TestClass {} +class TestClass {} +class TestClass where T: Equatable {} +class TestClass: Superclass where T: Equatable {} + +class +MoreThanOneLine +{} + +class +MoreThanOneLineInherit +: +Superclass +{} + +class +MoreThanOneLineInherit +: +Superclass1, +Superclass2 +{} + +class +MoreThanOneLineInherit: +Superclass +{} + +final class +MoreThanOneLineGeneric +where +T: Param +{} + +class Outer { + class Inner {} + class InnerInherit: Superclass {} +} + struct TestStruct {} +struct TestStruct: Conform {} +struct TestStruct {} + enum TestEnum {} +enum TestEnum: Conform {} +enum TestEnum {} + actor TestActor {} +actor TestActor: Conform {} +actor TestActor {} + extension TestExtension {} +extension TestExtension: Conform {} +extension TestExtension {} + protocol TestProtocol {} +protocol TestProtocol: Conform {} +protocol TestProtocol {}