是否有任何工具可以將 ANSI 程式碼文字轉換為類似文字的輸出?tput
上限名稱或類似名稱?
詢問的原因是我想使用script
或類似的方法並查看結果文件,而不必破解 ANSI 序列。我知道一些,但不是全部,文字輸出會更容易閱讀。
在大多數情況下,我可以查看產生 ANSI 文字的腳本或程式的原始程式碼,但如果有一個類似「偵錯」的工具就更好了。
最好的可能是C?變數名稱,即:
^[[K -> <clr_eol>
知道我可以為它編寫一個腳本......例如:
sed 's/$/<newline>/' rec001.txt | \
sed 's/\x07/\n<bell>/g' | \
sed 's/\x1b\[K/\n<clr_eol>/g' | \
sed 's/\x1b\[?12l\x1b\[?25h/\n<cursor_normal>/g' | \
sed 's/\x1b\[\([0-9]\+\);\([0-9]\+\)H/\n<cursor_position(\1, \2)>/g' | \
sed 's/\x1b\[?1049h/\n<enter_ca_mode>/g' | \
sed 's/\x1b\[?25l/\n<cursor_invisible>/g' | \
sed 's/\x0d/<CR>/g' | \
...
這是我做的快速測試的一部分伊爾西記錄。
但想知道是否有現有的工具可以完成這項工作。
作為旁注,我們有aha
,Ansi HTML 轉接器,它將 ANSI 轉換為 HTML。但這不是我正在尋找的適配器。
答案1
有人可能會建議一個程式。這不是一個小問題出色地:
- 「ANSI 序列」在 ECMA-48 中標準化,
- 您的一些範例(例如遊標外觀和進入_ca_模式)不在標準中,
- 一些例如進入_ca_模式
1049
代碼有變化 (\E7\E[?47h
)。如果程式依賴終端描述,則只能識別其中一種變體, - 有些序列是參數化的,這意味著程式必須具有內建規則,或者能夠將終端功能轉換為可以
\E[%i%p1%d;%p2%dH
與輸入相符的正規表示式。
考慮到所有這些,如果有人建議一個程序,它很可能不會解決這些方面,而只是一個沒有顯示器的終端模擬器。
答案2
如果您只想要 ANSI 遊標移動,您可以使用 NPM 模組輕鬆建立解釋器節點反解析器。我為我的 JavaScript 庫使用了相同的模組:jQuery 終端,我在這裡解析和處理 ANSI 轉義和改寫(man 命令的輸出)。
你可以在GitHub上看看我是如何使用解析器的unix_formatting.js(該文件包括 ansi-parser)。您可以嘗試修改程式碼以僅處理文字並忽略顏色(jQuery 終端格式語法)。應該沒那麼難。
如果您想要快速處理,您可以建立腳本,該腳本將僅處理檔案並刪除 jQuery Terminal 使用的格式。這是一個可以解決問題的快速技巧(但您可能最好修改 unix_formatting.js 檔案並刪除所有不需要的內容)。
若要開始使用 jQuery 終端,請使用下列命令:
mkdir ansi-text
cd ansi-text
npm init -y # you need nodeJS installed
npm install jquery.terminal
然後在同一目錄中建立此檔案:
ansi-text.js
#!/usr/bin/env node
// mock jQuery that is not actually required
const $ = global.$ = global.jQuery = {
fn: {
extend: function(obj) {
Object.assign(global.jQuery.fn, obj);
}
},
extend: Object.assign
};
global.navigator = {
userAgent: 'Node'
};
require('jquery.terminal')(global, global.$);
require('jquery.terminal/js/unix_formatting')(global, global.$);
read_stdin().then(function(buff) {
const str = buff.toString();
const formatted = $.terminal.apply_formatters(str);
console.log($.terminal.strip(formatted));
});
function read_stdin() {
return new Promise((resolve) => {
const buff = [];
process.stdin.on('data', data => {
buff.push(data);
}).on('end', () => {
var len = buff.map(x => x.length).reduce((acc, e) => acc + e);
resolve(Buffer.concat(buff, len));
});
});
}
然後您可以建立測試腳本:
測試文件
tput cup 2 3;
echo HELLO;
tput cup 5 20;
echo WORLD;
你可以看到它的工作原理是:
unbuffer ./test.sh | ./ansi-text.js
輸出:
kuba@jcubic:~/projects/jcubic/ansi-text$ unbuffer test.sh | ./ansi-text.js
HELLO
WORLD
kuba@jcubic:~/projects/jcubic/ansi-text$
unbuffer 將使腳本認為它是 TTY (它是 Expect 的一部分)。
JS 程式碼不處理終端的寬度,但在轉換 ANSI 轉義後可以輕鬆添加它。要分割輸出,請使用:$.terminal.split_equal(string, cols)
但您可能可以使用更簡單的東西,因為您不需要處理 jQuery 終端格式,這是函數的主要目的。