Skip to content

Instantly share code, notes, and snippets.

@sensq
Last active October 19, 2016 16:56
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save sensq/589de2764297e22d9b5a99acebca4684 to your computer and use it in GitHub Desktop.
Save sensq/589de2764297e22d9b5a99acebca4684 to your computer and use it in GitHub Desktop.
// Meryのマクロ用スクリプト
// コードのインデントを一括で整形する
// Ruby専用のつもりだったが、{}でインデントが増減する系の言語(C, Java, Javascript, Powershellなど)にも基本的に使用可能
// 波括弧省略したif文やfor文があると正しく整形されない不具合あり(判定が難しそう)
var lines = document.GetLines()
var pm_words = []
var p_words = []
var m_words = []
var counter = 0
var indent = 2 // 任意の数にする
function main() {
create_reserved_word()
// 読み込み
var line_texts = []
for(var i = 0; i < lines; i++) {
line_texts.push(document.GetLine(i+1))
}
// 整形して上書き
ret = format(line_texts)
var text = ""
for(var l = 0; l < ret.length; l++){
text += ret[l]
text += "\n"
}
var sy = ScrollY // ウィンドウのスクロール位置取得
document.selection.SelectAll()
document.selection.Text = text.substring(0, text.length-1)
ScrollY = sy // ウィンドウのスクロール位置を戻す
}
// インデント判断用の辞書作成
function create_reserved_word() {
indent_pm_word()
indent_plus_word()
indent_minus_word()
// 上下でインデントが増減する文字列
function indent_pm_word() {
pm_words.push(/^\s*when(\(|\s|$)/)
pm_words.push(/^\s*else(\s|$)/)
pm_words.push(/^\s*elsif(\(|\s|$)/)
pm_words.push(/^\s*rescue(\s|$)/)
pm_words.push(/^\s*ensure(\s|$)/)
}
// インデントが増える文字列
function indent_plus_word() {
p_words = p_words.concat(pm_words)
p_words.push(/^\s*module(\s|$)/)
p_words.push(/^\s*class(\s|$)/)
p_words.push(/^\s*def(\s|$)/)
p_words.push(/^\s*unless(\(|\s|$)/)
p_words.push(/^\s*if(\(|\s|$)/)
p_words.push(/^\s*case(\s|$)/)
p_words.push(/^\s*begin(\s|$)/)
p_words.push(/^\s*while(\s|$)/)
p_words.push(/^\s*until(\(|\s|$)/)
p_words.push(/\sdo(\s|$)/)
p_words.push(/.*\{(\s|$)/)
}
// インデントが減る文字列
function indent_minus_word() {
m_words = m_words.concat(pm_words)
m_words.push(/^\s*end(\s|$)/)
m_words.push(/.*\}(\s|$|;|\)\(\);)/)
}
}
// コメント行の判断
function chk_comment_word(line) {
if(/^\s*#/.test(line)){
return true
}
if(/^\s*\/\//.test(line)){
return true
}
return false
}
// 1行で{}が完結している行の判断
function chk_inline_line(line) {
if(/.*\{.*\}.*/.test(line)){
if(/.*\{(\s|$)/.test(line)){
return false
} else {
return true
}
}
return false
}
// インデントを下げる行の判断
function chk_plus_word(line) {
if(chk_comment_word(line)){
return
}
if(chk_inline_line(line)){
return
}
for(var item = 0; item < p_words.length; item++){
if(p_words[item].test(line)){
counter += 1
break
}
}
}
// インデントを上げる行の判断
function chk_minus_word(line) {
if(chk_comment_word(line)){
return
}
if(chk_inline_line(line)){
return
}
for(var item = 0; item < m_words.length; item++){
if(m_words[item].test(line)){
counter -= 1
if(counter < 0){
counter = 0
}
break
}
}
}
// インデントを行う
function add_indent(line) {
var spaces = ""
for(var c = 0; c < counter; c++){
for(var i = 0; i < indent; i++){
spaces += " "
}
}
return line.replace(/^/, spaces)
}
// フォーマットを実行するメソッド
function format(ary) {
var ret_ary = ary.concat()
// 最初に全部のインデントを消去
for(var line = 0; line < ret_ary.length; line++){
ret_ary[line] = ret_ary[line].replace(/^\s*/, "")
}
// フォーマット実行
for(var line = 0; line < ret_ary.length; line++){
chk_minus_word(ret_ary[line])
ret_ary[line] = add_indent(ret_ary[line])
chk_plus_word(ret_ary[line])
}
return ret_ary
}
main()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment