diff --git a/compiler/src/dotty/tools/dotc/parsing/Parsers.scala b/compiler/src/dotty/tools/dotc/parsing/Parsers.scala index 4de9b5230f8d..3fcaec91e737 100644 --- a/compiler/src/dotty/tools/dotc/parsing/Parsers.scala +++ b/compiler/src/dotty/tools/dotc/parsing/Parsers.scala @@ -348,6 +348,7 @@ object Parsers { if in.isNewLine then in.nextToken() else accept(SEMI) def acceptStatSepUnlessAtEnd(altEnd: Token = EOF): Unit = + in.observeOutdented() if (!isStatSeqEnd) in.token match { case EOF => diff --git a/compiler/src/dotty/tools/dotc/parsing/Scanners.scala b/compiler/src/dotty/tools/dotc/parsing/Scanners.scala index a7513b8a722b..b426cdcfa201 100644 --- a/compiler/src/dotty/tools/dotc/parsing/Scanners.scala +++ b/compiler/src/dotty/tools/dotc/parsing/Scanners.scala @@ -555,6 +555,13 @@ object Scanners { token = INDENT end observeIndented + /** Insert an token if next token closes an indentation region */ + def observeOutdented(): Unit = currentRegion match + case r: Indented if !r.isOutermost && closingRegionTokens.contains(token) => + currentRegion = r.enclosing + insert(OUTDENT, offset) + case _ => + /** - Join CASE + CLASS => CASECLASS, CASE + OBJECT => CASEOBJECT, SEMI + ELSE => ELSE, COLON + => COLONEOL * - Insert missing OUTDENTs at EOF */ diff --git a/docs/docs/reference/other-new-features/indentation-new.md b/docs/docs/reference/other-new-features/indentation-new.md index 4d30850fa6a8..700bb973609a 100644 --- a/docs/docs/reference/other-new-features/indentation-new.md +++ b/docs/docs/reference/other-new-features/indentation-new.md @@ -77,6 +77,8 @@ There are two rules: If the indentation width of the token on the next line is still less than the new current indentation width, step (2) repeats. Therefore, several `` tokens may be inserted in a row. + An `` is also inserted if the next statement following a statement sequence starting with an `` closes an indentation region, i.e. is one of `then`, `else`, `do`, `catch`, `finally`, `yield`, `}` or `case`. + It is an error if the indentation width of the token following an `` does not match the indentation of some previous line in the enclosing indentation region. For instance, the following would be rejected. ```scala diff --git a/tests/neg/spaces-vs-tabs.check b/tests/neg/spaces-vs-tabs.check index 3827221ff95c..51c2689f57bc 100644 --- a/tests/neg/spaces-vs-tabs.check +++ b/tests/neg/spaces-vs-tabs.check @@ -17,15 +17,11 @@ | Previous indent : 2 tabs | Latest indent : 1 tab, 2 spaces -- Error: tests/neg/spaces-vs-tabs.scala:8:1 --------------------------------------------------------------------------- -8 | else () // error // error +8 | else () // error | ^ | Incompatible combinations of tabs and spaces in indentation prefixes. | Previous indent : 2 tabs | Latest indent : 1 space --- [E040] Syntax Error: tests/neg/spaces-vs-tabs.scala:8:6 ------------------------------------------------------------- -8 | else () // error // error - | ^ - | ';' expected, but '(' found -- Error: tests/neg/spaces-vs-tabs.scala:14:2 -------------------------------------------------------------------------- 14 | else 2 // error // error | ^ diff --git a/tests/neg/spaces-vs-tabs.scala b/tests/neg/spaces-vs-tabs.scala index cf24f8290904..d30d44c827fe 100644 --- a/tests/neg/spaces-vs-tabs.scala +++ b/tests/neg/spaces-vs-tabs.scala @@ -5,7 +5,7 @@ object Test println(2) // error println(3) // error println(4) // error - else () // error // error + else () // error object Test2 diff --git a/tests/pos/i7421.scala b/tests/pos/i7421.scala new file mode 100644 index 000000000000..247285bdc9b6 --- /dev/null +++ b/tests/pos/i7421.scala @@ -0,0 +1,17 @@ +object Main { + + def main(args: Array[String]): Unit = { + if (args.length > 0) then + { + println(args) + } else { + println("Hello world!") + } + if (args.length > 0) + { + println(args) + } else { + println("Hello world!") + } + } +} \ No newline at end of file