aBothe / D_Parser

Parser & Resolver & Abstract Completion library for D
Other
30 stars 7 forks source link

Invalid indentation without { } #96

Closed etcimon closed 10 years ago

etcimon commented 10 years ago

When writing:

foreach(field; fields)
    if ((field in data) !is null) 
        ret ~= data[field];
else
    ret ~= string.init;

The identation starting at else is wrong it should be:

foreach(field; fields)
    if ((field in data) !is null) 
        ret ~= data[field];
    else
        ret ~= string.init;
Orvid commented 10 years ago

Well, although in my mind if you write such code, you shouldn't be coding, I will agree that this is a bug :P

etcimon commented 10 years ago

Well, although in my mind if you write such code, you shouldn't be coding, I will agree that this is a bug :P

Nah I refactored this to

    foreach(field; fields) ret ~= data.get(field, string.init);

Looks much better =)

etcimon commented 10 years ago

Do you know how this could be done with std.algorithm.map?

etcimon commented 10 years ago

While we're into indentation, it would be great (imo) if every new line without semi-colon would align to the last dot

e.g.

    auto ret = m_data.keys
        .map!(k => match(k, r)? k : string.init)
            .filter!("a.length > 0")
            .array;

would become:

    auto ret = m_data.keys
                    .map!(k => match(k, r)? k : string.init)
                    .filter!("a.length > 0")
                    .array;

btw I got this error while pressing tab aka aligning it properly:

System.ArgumentOutOfRangeException: must be <= charArrayLength (116) was :4294967236 Parameter name: textIndex at Mono.TextEditor.TextViewMargin.TranslateToUTF8Index(Char[] charArray, UInt32 textIndex, UInt32& curIndex, UInt32& byteIndex) at Mono.TextEditor.TextViewMargin.<>cDisplayClass15.bb(Int32 start, Int32 end) at Mono.TextEditor.TextViewMargin.InternalHandleSelection(Int32 selectionStart, Int32 selectionEnd, Int32 startOffset, Int32 endOffset, HandleSelectionDelegate handleNotSelected, HandleSelectionDelegate handleSelected) at Mono.TextEditor.TextViewMargin.HandleSelection(Int32 lineOffset, Int32 logicalRulerColumn, Int32 selectionStart, Int32 selectionEnd, Int32 startOffset, Int32 endOffset, HandleSelectionDelegate handleNotSelected, HandleSelectionDelegate handleSelected) at Mono.TextEditor.TextViewMargin.CreateLinePartLayout(ISyntaxMode mode, DocumentLine line, Int32 logicalRulerColumn, Int32 offset, Int32 length, Int32 selectionStart, Int32 selectionEnd) at Mono.TextEditor.TextViewMargin.CreateLinePartLayout(ISyntaxMode mode, DocumentLine line, Int32 offset, Int32 length, Int32 selectionStart, Int32 selectionEnd) at Mono.TextEditor.TextViewMargin.GetLayout(DocumentLine line) at Mono.TextEditor.TextViewMargin.ColumnToX(DocumentLine line, Int32 column) at Mono.TextEditor.TextViewMargin.LocationToPoint(DocumentLocation loc, Boolean useAbsoluteCoordinates) at Mono.TextEditor.TextViewMargin.LocationToPoint(DocumentLocation loc) at Mono.TextEditor.TextEditor.LocationToPoint(DocumentLocation loc) at MonoDevelop.SourceEditor.SourceEditorView.CreateCodeCompletionContext(Int32 triggerOffset) at MonoDevelop.SourceEditor.SourceEditorView.get_CurrentCodeCompletionContext() at MonoDevelop.Ide.Gui.Content.CompletionTextEditorExtension.KeyPress(Key key, Char keyChar, ModifierType modifier) at MonoDevelop.D.DEditorCompletionExtension.KeyPress(Key key, Char keyChar, ModifierType modifier) at MonoDevelop.Ide.Gui.Content.TextEditorExtension.KeyPress(Key key, Char keyChar, ModifierType modifier) at MonoDevelop.D.Formatting.Indentation.DTextEditorIndentation.KeyPress(Key key, Char keyChar, ModifierType modifier) at MonoDevelop.Ide.Gui.Content.TextEditorExtension.KeyPress(Key key, Char keyChar, ModifierType modifier) at MonoDevelop.Ide.Gui.Content.TextEditorExtension.KeyPress(Key key, Char keyChar, ModifierType modifier) at MonoDevelop.Ide.Gui.Content.TextEditorExtension.KeyPress(Key key, Char keyChar, ModifierType modifier) at MonoDevelop.Ide.Gui.Content.TextEditorExtension.KeyPress(Key key, Char keyChar, ModifierType modifier) at MonoDevelop.Ide.Gui.Content.TextEditorExtension.KeyPress(Key key, Char keyChar, ModifierType modifier) at MonoDevelop.Debugger.ExceptionCaughtTextEditorExtension.KeyPress(Key key, Char keyChar, ModifierType modifier) at MonoDevelop.SourceEditor.ExtensibleTextEditor.ExtensionKeyPress(Key key, UInt32 ch, ModifierType state)

aBothe commented 10 years ago

Are there other cases than if else if to pay attention on?

etcimon commented 10 years ago

Basically everything seems out of order for bracketless statements

    if (something)
        foreach(something)
            for(;;)
                if ()
                    else
                        woop;
    wat?
etcimon commented 10 years ago

Are there other cases than if else if to pay attention on?

Also the switch cases!

    final switch(arr.front){
        case "key1":
            writeln("woot");
            break;
            case "

should return to the "case" indentation after break; goto; return; continue; (maybe others), as long as it comes from base indentation (not in an if/while/for/foreach/function/etc)

etcimon commented 10 years ago

The behavior for bracketless indentation positions that I'd expect is, they should just fall back to the last if's indentation by default after a semi-colon or a bracket closure, and every time you press enter it should fall back to the previous if's indentation (without skipping a line), until it falls down to the last bracket identation.

I'd be happy if you factored in the period-indentation behavior (when the line is a statement that ends without a semicolon, adjust to the last period)

etcimon commented 10 years ago

Thanks! Did you check the switch/case?

aBothe commented 10 years ago

well it's actually formatting this kinda stuff as soon as you type a colon ':' - but I guess I could hack a special case for 'case' in there as well.

etcimon commented 10 years ago

Well, I can't think of any situation when break; continue; goto *; return *; won't go back an indent tick if followed by a line break, it could be good to apply it.

Orvid commented 10 years ago

Formatting the line when the semicolon is typed is the right way to do it, because it is valid for functions that don't return to be the last statement in a case (provided I remember right anyways), and that also precludes any other random ways that people can find to end a case. Formatting immediately after typing the case token would still be appropriate, although inconsistent with C#.

etcimon commented 10 years ago

Formatting immediately after typing the case token would still be appropriate, although inconsistent with C#.

I would think it's a bonus if you can predict what comes next?

etcimon commented 10 years ago

Well, I can't think of any situation when break; continue; goto ; return ; won't go back an indent tick if followed by a line break, it could be good to apply it.

Here's an illustration of what I mean

switch (test){
    case 1:
        dosomething();
        break;

    ^ cursor goes here