@@ -223,6 +223,9 @@ object Scanners {
223223 val oldSyntax = ctx.settings.oldSyntax.value
224224 val newSyntax = ctx.settings.newSyntax.value
225225
226+ /** A switch whether operators at the start of lines can be infix operators */
227+ private var allowLeadingInfixOperators = true
228+
226229 /** All doc comments kept by their end position in a `Map` */
227230 private [this ] var docstringMap : SortedMap [Int , Comment ] = SortedMap .empty
228231
@@ -382,6 +385,30 @@ object Scanners {
382385 next.token = EMPTY
383386 }
384387
388+ def insertNL (nl : Token ): Unit = {
389+ next.copyFrom(this )
390+ // todo: make offset line-end of previous line?
391+ offset = if (lineStartOffset <= offset) lineStartOffset else lastLineStartOffset
392+ token = nl
393+ }
394+
395+
396+ /** A leading symbolic or backquoted identifier is treated as an infix operator
397+ * if it is followed by at least one ' ' and a token on the same line
398+ * that can start an expression.
399+ */
400+ def isLeadingInfixOperator =
401+ allowLeadingInfixOperators &&
402+ (token == BACKQUOTED_IDENT ||
403+ token == IDENTIFIER && isOperatorPart(name(name.length - 1 ))) &&
404+ (ch == ' ' ) && {
405+ val lookahead = lookaheadScanner
406+ lookahead.allowLeadingInfixOperators = false
407+ // force a NEWLINE a after current token if it is on its own line
408+ lookahead.nextToken()
409+ canStartExpressionTokens.contains(lookahead.token)
410+ }
411+
385412 /** Insert NEWLINE or NEWLINES if
386413 * - we are after a newline
387414 * - we are within a { ... } or on toplevel (wrt sepRegions)
@@ -393,10 +420,15 @@ object Scanners {
393420 (canStartStatTokens contains token) &&
394421 (sepRegions.isEmpty || sepRegions.head == RBRACE ||
395422 sepRegions.head == ARROW && token == CASE )) {
396- next copyFrom this
397- // todo: make offset line-end of previous line?
398- offset = if (lineStartOffset <= offset) lineStartOffset else lastLineStartOffset
399- token = if (pastBlankLine()) NEWLINES else NEWLINE
423+ if (pastBlankLine())
424+ insertNL(NEWLINES )
425+ else if (! isLeadingInfixOperator)
426+ insertNL(NEWLINE )
427+ else if (isScala2Mode || oldSyntax)
428+ ctx.warning(em """ Line starts with an operator;
429+ |it is now treated as a continuation of the expression on the previous line,
430+ |not as a separate statement. """ ,
431+ source.atSpan(Span (offset)))
400432 }
401433
402434 postProcessToken()
0 commit comments