Bash: làm thế nào để biết đầu ra của lệnh cuối có kết thúc bằng một dòng mới hay không?


10

Hầu hết thời gian đầu ra của một lệnh kết thúc bằng ký tự dòng mới. Nhưng đôi khi không, vì vậy dấu nhắc shell tiếp theo được in cùng dòng với đầu ra.

Thí dụ:

root @ tên máy chủ [~] # echo -n xin chào
helloroot @ tên máy chủ [~] #

Tôi luôn thấy điều đó thật khó chịu.
Bây giờ, tôi chỉ có thể thêm "\ n" vào đầu biến PS1, nhưng hầu hết thời gian sẽ in thêm một dòng tôi không cần.

Có thể biết liệu đầu ra của lệnh cuối cùng kết thúc với một dòng mới hay không?


Giải pháp:
(Cảm ơn Dennis)

PS1='$(printf "%$((`tput cols`-1))s\r")\u@\h [\w]\$ '

Điều này nên được chuyển đến superuser.
ℝaphink

Tôi thích phiên bản của bạn! Bạn đã sử dụng $()ở một nơi và backticks ở một nơi khác. Bạn có thể sử dụng $()trong cả hai.
Tạm dừng cho đến khi có thông báo mới.

Tôi biết. Nhưng đối với tôi nó dễ đọc hơn theo cách đó
GetFree

Tôi sẽ không sử dụng tput colsbởi vì dù sao nó cũng chỉ xuất ra giá trị của biến COLUMNS và nó chậm hơn vì nó không phải là vỏ dựng sẵn. Bạn cũng sẽ muốn bao gồm \e[K(tương đương tput el) để xóa khoảng trắng được chèn để bạn không nhận được một khoảng trắng theo sau khi sao chép và dán trong trường hợp mặc định. Cuối cùng, bạn cần kèm theo tất cả phép thuật này giữa \[\]nếu không, bash sẽ cố gắng đoán thứ hai vị trí con trỏ của bạn và nó sẽ gây rối khi bạn chỉnh sửa lệnh / lịch sử của mình.
dlitz

1
Toàn bộ điều có thể được thực hiện như chỉ:PS1='\[\e[7m%\e[m$( printf "%*s" "$((COLUMNS-1))" "" )\r\e[K\]\u@\h [\w]\$ '
dlitz

Câu trả lời:


6

Tôi đã thử nghiệm những điều sau đây để mô phỏng tính năng từ zshtrong Bash:

$ unset PROMPT_SP; for ((i = 1; i <= $COLUMNS + 52; i++ )); do PROMPT_SP+=' '; done
$ PS1='\[\e[7m%\e[m\]${PROMPT_SP: -$COLUMNS+1}\015$ '

Nó phát hành một ký hiệu phần trăm video đảo ngược, theo sau là một loạt các khoảng trắng để làm cho nó được bọc sang dòng tiếp theo, sau đó trở lại vận chuyển, tiếp theo là ký hiệu đô la và khoảng trắng. Bạn có thể thêm thoát nhanh chóng sau "\ 015" để tùy chỉnh lời nhắc của mình.

Sử dụng điều này phụ thuộc vào cách thiết bị đầu cuối của bạn xử lý gói lề phải (lề tự động). Độ dài của PromPTinks là tùy ý, nhưng tối thiểu phải là 80 hoặc bất kỳ chiều rộng thiết bị đầu cuối thông thường của bạn là gì. Bạn có thể cần mã cứng giá trị đó nếu $ COLUMNS chưa được đặt vào thời điểm forvòng lặp được chạy ~/.bashrc. Bạn có thể muốn shopt -s checkwinsizenếu nó chưa được thiết lập.


Tôi tự hỏi tại sao ai đó hạ thấp từng câu trả lời . Hmmm ... không có lời giải thích. Thật hữu ích.
Tạm dừng cho đến khi có thông báo mới.

Đây là một cách khác, không sử dụng vòng lặp, để tạo chuỗi pad:printf -v PROMPT_SP '%*s' $((COLUMNS + 52)) ''
Tạm dừng cho đến khi có thông báo mới.

"Dấu hiệu phần trăm video đảo ngược" là gì? Từ "video" khiến tôi bối rối và tôi không thể tìm thấy câu trả lời trên Google.
davidchambers

1
@davidchambers: Nền của nhân vật được hiển thị bằng màu nền trước và chính ký tự được hiển thị bằng màu nền. Xem man 5 terminfovà tìm kiếm "video đảo ngược" để xem một số tài liệu sử dụng thuật ngữ này.
Tạm dừng cho đến khi có thông báo mới.

0

Không, điều đó là không thể. Bản thân Bash không xử lý hoặc xem đầu ra của chương trình mà nó đã bắt đầu.

Nó chỉ xảy ra với tôi rằng thể viết một chương trình để thiết lập PROMPT_COMMAND, nó sẽ kiểm tra vị trí hiện tại của con trỏ và đưa ra một dòng mới nếu con trỏ không ở cạnh trái.


Ý tưởng tốt. Vấn đề duy nhất là ... có thể biết vị trí con trỏ không?
GetFree

0

zshcố gắng giải quyết vấn đề của bạn Nếu đầu ra cuối cùng kết thúc mà không có dòng mới, bạn sẽ nhận được:

$ echo -n 'abc'
abc%
$ 

Trường hợp %sử dụng nền / tiền cảnh đảo ngược. Không chắc chắn nếu nó di động bashtheo bất kỳ cách nào.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.