# Delete Line (DL)

> Delete n lines at the cursor, pulling the lines below it up.

- **Sequence:** `CSI Pn M`
- **Defaults:** Pn = 1
- **ECMA-48:** [§8.3.32 DL – Delete Line, p. 39](https://archive.org/details/ecma-48-5th-edition-june-1991/page/n52/mode/1up)
- **DEC STD 070:** [§5.11 Delete Line, p. 5-148](https://archive.org/details/bitsavers_decstandar0VideoSystemsReferenceManualDec91_74264381/page/n402/mode/1up)
- **VT220:** [§4.11 Editing](https://vt100.net/docs/vt220-rm/chapter4.html#S4.11)
- **VT510:** [DL—Delete Line](https://vt100.net/docs/vt510-rm/DL.html)

Delete `Pn` lines, starting with the line the cursor is on. The lines below
them, up to the bottom margin, move up to close the gap, and blank lines
appear at the bottom margin. A `0` is taken as `1`, and asking for more lines
than there are between the cursor and the bottom margin deletes only those.

As with [IL](https://control-codes.page/csi/il/index.html.md), only the scrolling region is affected, the part of
each line between the left and right margins if those are set, and DL does
nothing if the cursor is outside the region. The VT510 manual adds that the
new blank lines have no visual character attributes.

Afterwards the cursor is at the left margin of the line it was on, which is
what DEC STD 070 specifies.

[SU](https://control-codes.page/csi/su/index.html.md) also moves lines up, but from the top of the scrolling
region, wherever the cursor is.

## Validation

### DL-1: Delete one line

Input, one step per line:

```text
1\r\n2\r\n3\r\n4
\e[2;3H
\e[M
```

Expected screen:

```text
|1____|
|3____|
|4____|
|_____|
cursor 2,1
```

### DL-2: More lines than there are

Input, one step per line:

```text
1\r\n2\r\n3\r\n4
\e[2;1H
\e[9M
```

Expected screen:

```text
|1____|
|_____|
|_____|
|_____|
```

### DL-3: Only the scrolling region moves

Input, one step per line:

```text
1\r\n2\r\n3\r\n4
\e[1;3r   # region is lines 1 to 3; homes the cursor
\e[M
```

Expected screen:

```text
|2____|
|3____|
|_____|
|4____|
```

### DL-4: Nothing happens outside the scrolling region

Input, one step per line:

```text
1\r\n2\r\n3\r\n4
\e[2;3r   # region is lines 2 and 3; homes the cursor, above it
\e[M
```

Expected screen:

```text
|1____|
|2____|
|3____|
|4____|
cursor 1,1
```

### DL-5: Inside left and right margins

Input, one step per line:

```text
abcde\r\nfghij\r\nklmno\r\npqrst\r\nuvwxy
\e[?69h   # allow left and right margins
\e[2;4s   # margins at columns 2 and 4
\e[2;3H   # on the h
\e[M
```

Expected screen:

```text
|abcde|
|flmnj|
|kqrso|
|pvwxt|
|u___y|
cursor 2,2
```

---

This is the Markdown version of <https://control-codes.page/csi/dl/>. On that page every validation case runs live in libghostty-vt, the terminal emulation core of Ghostty, compiled to WebAssembly.

The validation cases are written in the notation described in <https://control-codes.page/notation/index.html.md>.
