初歩のシェルスクリプトで遊ぶ[端末の256色カラーセレクタ(4)]

バージョン3.1でいったん置いとく

入れようと思ってた機能は入れたんで、ここらでいったんスクリプトを置いときます。
こっちはメインの256色版。
2000行あるけれど、いちおうファイル一つにまとまってます。丸ごとコピーして実行権限つければいけるはず。
Ubuntu20.04,xfce-terminalあたりで、無料・無保証で構わない人のみどうぞ。
端末が違うと動かない機能があったりしますが、それも含めて端末のテストも兼ねてます。こっちの端末は太字が出ないんだな、とか。

#!/bin/sh
#!/bin/bash
#!/usr/bin/ksh
#!/usr/bin/posh
#!/bin/busybox sh
#!/usr/bin/zsh
#!/usr/bin/yash
#!/bin/dash

# ========================================================================================
# ■ 端末カラーセレクター256色 v3.1
# https://twitter.com/beta_reverse_2
# ========================================================================================

# **************************************************************************************
# ユーザ設定_任意
# **************************************************************************************

# サンプルテキスト
# 横幅推奨値='                                                  '
  STD_SAMPLE='                             standard sample text '
 MAIN_SAMPLE='                                 main sample text '
  SUB_SAMPLE='                                  sub sample text '
 FREE_SAMPLE='                                 free sample text '

# カラーパレットの横幅初期値
paletteWidth='96'

# カラーパレットの並び順データ
# # ====[shMerge]====	colorTableListSh	20201101_085854
colorTableListSh(){ (	# ====[shMerge<ins>]====
#!/bin/sh
# 引数に数字を与えると、その番号のカラーパレットデータを出力する
# パレットデータの数字は「0-255」
# 行のデータはタブ区切りにする
# 1行に入れる数値データの数は、360の約数にする
# 行数に制限は無いが、端末表示に収まる行数に。
# 「0-255」を、すべて必ず1回ずつ使わなければならない。
# 同じ数字を複数回使ってはいけない。
# カスタマイズするなら、既存のカラーパレットをベースにして、行単位で入れ替えると簡単。

# HSL S -> L -> H
Palette0='0	1	2	3	4	5	6	7
8	9	10	11	12	13	14	15
232	233	234	235	236	237	238	239	240	241	242	243
244	245	246	247	248	249	250	251	252	253	254	255
16	59	102	145	188	231
95	101	65	66	60	96
138	144	108	109	103	139
131	137	143	107	71	72	73	67	61	97	133	132
181	187	151	152	146	182
174	180	186	150	114	115	116	110	104	140	176	175
167	173	179	185	149	113	77	78	79	80	74	68	62	98	134	170	169	168
52	58	22	23	17	53
88	94	100	64	28	29	30	24	18	54	90	89
124	130	136	142	106	70	34	35	36	37	31	25	19	55	91	127	126	125
160	166	172	178	184	148	112	76	40	41	42	43	44	38	32	26	20	56	92	128	164	163	162	161
196	202	208	214	220	226	190	154	118	82	46	47	48	49	50	51	45	39	33	27	21	57	93	129	165	201	200	199	198	197
203	209	215	221	227	191	155	119	83	84	85	86	87	81	75	69	63	99	135	171	207	206	205	204
210	216	222	228	192	156	120	121	122	123	117	111	105	141	177	213	212	211
217	223	229	193	157	158	159	153	147	183	219	218
224	230	194	195	189	225'


# HSL L -> S -> H
Palette1='0	1	2	3	4	5	6	7
8	9	10	11	12	13	14	15
232	233	234	235	236	237	238	239	240	241	242	243
244	245	246	247	248	249	250	251	252	253	254	255
16	59	102	145	188	231
52	58	22	23	17	53
88	94	100	64	28	29	30	24	18	54	90	89
124	130	136	142	106	70	34	35	36	37	31	25	19	55	91	127	126	125
160	166	172	178	184	148	112	76	40	41	42	43	44	38	32	26	20	56	92	128	164	163	162	161
95	101	65	66	60	96
196	202	208	214	220	226	190	154	118	82	46	47	48	49	50	51	45	39	33	27	21	57	93	129	165	201	200	199	198	197
131	137	143	107	71	72	73	67	61	97	133	132
138	144	108	109	103	139
167	173	179	185	149	113	77	78	79	80	74	68	62	98	134	170	169	168
174	180	186	150	114	115	116	110	104	140	176	175
203	209	215	221	227	191	155	119	83	84	85	86	87	81	75	69	63	99	135	171	207	206	205	204
181	187	151	152	146	182
210	216	222	228	192	156	120	121	122	123	117	111	105	141	177	213	212	211
217	223	229	193	157	158	159	153	147	183	219	218
224	230	194	195	189	225'

# カラーパレット_色番号順
Palette2='0	1	2	3	4	5	6	7
8	9	10	11	12	13	14	15
232	233	234	235	236	237	238	239	240	241	242	243
244	245	246	247	248	249	250	251	252	253	254	255
16	17	18	19	20	21	22	23	24	25	26	27	28	29	30	31	32	33
34	35	36	37	38	39	40	41	42	43	44	45	46	47	48	49	50	51
52	53	54	55	56	57	58	59	60	61	62	63	64	65	66	67	68	69
70	71	72	73	74	75	76	77	78	79	80	81	82	83	84	85	86	87
88	89	90	91	92	93	94	95	96	97	98	99	100	101	102	103	104	105
106	107	108	109	110	111	112	113	114	115	116	117	118	119	120	121	122	123
124	125	126	127	128	129	130	131	132	133	134	135	136	137	138	139	140	141
142	143	144	145	146	147	148	149	150	151	152	153	154	155	156	157	158	159
160	161	162	163	164	165	166	167	168	169	170	171	172	173	174	175	176	177
178	179	180	181	182	183	184	185	186	187	188	189	190	191	192	193	194	195
196	197	198	199	200	201	202	203	204	205	206	207	208	209	210	211	212	213
214	215	216	217	218	219	220	221	222	223	224	225	226	227	228	229	230	231'

# HSV S -> V -> H
Palette3='0	1	2	3	4	5	6	7
8	9	10	11	12	13	14	15
232	233	234	235	236	237	238	239	240	241	242	243
244	245	246	247	248	249	250	251	252	253	254	255
16	59	102	145	188	231
224	230	194	195	189	225
181	187	151	152	146	182
138	144	108	109	103	139
95	101	65	66	60	96
217	223	229	193	157	158	159	153	147	183	219	218
174	180	186	150	114	115	116	110	104	140	176	175
131	137	143	107	71	72	73	67	61	97	133	132
210	216	222	228	192	156	120	121	122	123	117	111	105	141	177	213	212	211
167	173	179	185	149	113	77	78	79	80	74	68	62	98	134	170	169	168
203	209	215	221	227	191	155	119	83	84	85	86	87	81	75	69	63	99	135	171	207	206	205	204
52	58	22	23	17	53
88	94	100	64	28	29	30	24	18	54	90	89
124	130	136	142	106	70	34	35	36	37	31	25	19	55	91	127	126	125
160	166	172	178	184	148	112	76	40	41	42	43	44	38	32	26	20	56	92	128	164	163	162	161
196	202	208	214	220	226	190	154	118	82	46	47	48	49	50	51	45	39	33	27	21	57	93	129	165	201	200	199	198	197'

# HSV V -> S -> H
Palette4='0	1	2	3	4	5	6	7
8	9	10	11	12	13	14	15
232	233	234	235	236	237	238	239	240	241	242	243
244	245	246	247	248	249	250	251	252	253	254	255
16	59	102	145	188	231
52	58	22	23	17	53
95	101	65	66	60	96
88	94	100	64	28	29	30	24	18	54	90	89
138	144	108	109	103	139
131	137	143	107	71	72	73	67	61	97	133	132
124	130	136	142	106	70	34	35	36	37	31	25	19	55	91	127	126	125
181	187	151	152	146	182
174	180	186	150	114	115	116	110	104	140	176	175
167	173	179	185	149	113	77	78	79	80	74	68	62	98	134	170	169	168
160	166	172	178	184	148	112	76	40	41	42	43	44	38	32	26	20	56	92	128	164	163	162	161
224	230	194	195	189	225
217	223	229	193	157	158	159	153	147	183	219	218
210	216	222	228	192	156	120	121	122	123	117	111	105	141	177	213	212	211
203	209	215	221	227	191	155	119	83	84	85	86	87	81	75	69	63	99	135	171	207	206	205	204
196	202	208	214	220	226	190	154	118	82	46	47	48	49	50	51	45	39	33	27	21	57	93	129	165	201	200	199	198	197'


# 存在するデータの番号を入力されたとき、そのデータを出力して、exit 0
# 存在しないデータの番号を入力されたとき、exit 1

eval 'XX=`echo "${Palette'${1:-0}'}"`'
if test -n "${XX}" ; then
	eval 'echo "${Palette'${1:-0}'}"'
	exit 0
else
	exit 1
fi
# [EOF]
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	effectCodeList256Sh	20201101_085854
effectCodeList256Sh(){ (	# ====[shMerge<ins>]====
#!/bin/sh
# 1行に6個ずつ
# 空なら0を埋めておく
LF='
'
codeList="0${LF}1${LF}2${LF}3${LF}4${LF}5
6${LF}7${LF}8${LF}9${LF}10${LF}11
12${LF}13${LF}14${LF}15${LF}16${LF}17
18${LF}19${LF}20${LF}21${LF}22${LF}23
24${LF}25${LF}26${LF}27${LF}28${LF}29
51${LF}52${LF}53${LF}54${LF}55${LF}56
60${LF}61${LF}62${LF}63${LF}64${LF}65"

echo "${codeList}"
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	helpMessageC256sh	20201101_085854
helpMessageC256sh(){ (	# ====[shMerge<ins>]====
#!/bin/sh
# 操作説明
printf \
'\033[7m%s\033[27m %s  '\
'\033[7m%s\033[27m %s  '\
'\033[7m%s\033[27m %s\n'\
'\033[7m%s\033[27m %s  '\
'\033[7m%s\033[27m %s  '\
'\033[7m%s\033[27m %s  '\
'\033[7m%s\033[27m %s  '\
'\033[7m%s\033[27m %s\n' \
 ' up down left right '    '選択決定' \
 ' PgUp PgDn ' 'フォーカス切替' \
 ' space 0 '    'チェック' \
 ' + a '        '色情報詳細' \
 ' - s '        'mainとsubを入替' \
 ' . '          '色配置' \
 ' * '          '拡張操作' \
 ' / q '        '終了'
true
) }	# ====[shMerge</ins>]====

# ======================================================================================
# グローバル定数 シェル関数内での再定義と検索タグは必須
# ======================================================================================
ESC=`printf '\033'` # 【gloval const ESC】
ctrl_plus_C=`printf '\003'` # 【gloval const ctrl_plus_C】
ENTER_KEY=`printf '\015'` # 【gloval const ENTER_KEY】

# ======================================================================================
# シェル関数_外部へ分離可能
# ======================================================================================
# cd $(dirname `readlink -f "${0}"`) # ====[shMerge<disable>]==== #_shMergeDisabled

# PATH="./lib:${PATH}" # ====[shMerge<disable>]==== #_shMergeDisabled

# # ====[shMerge]====	ansi256matrixToViewCodeSh	20201101_085854
ansi256matrixToViewCodeSh(){ (	# ====[shMerge<ins>]====
#!/bin/sh
# カラーパレット表を読み込んで、パレットを端末表示するためのデータを作成する。
# 表示幅(文字数)は指定できる。
# 一行に指定されるパレットの数が増減しても、表示幅を同じ幅に揃える。
roundSh(){ (
Width=${1:?'横幅指定が必要'}
Part=${2:?'分割数指定が必要'}

# 余った文字数
Remaind=$(( ${Width} % ${Part} ))
# 余った文字を振り分ける行番号リスト
addLines=''

NN=1
while test ${NN} -le ${Remaind} ; do
addLines="${addLines}$(( ( ${Part} * ${NN} ) / ( ${Remaind} + 1 ) + 1 ))
"
NN=$(( ${NN} + 1 ))
done

#echo "${addLines}" # 【debug】

partNo='1'
while test "${partNo}" -le "${Part}" ; do
addLineFlag='false'

# ${partNo}が 指定値と同じなら フラグtrue
while read addLine ; do
  if test -z "${addLine}" ; then
	continue
elif test "${partNo}" -eq "${addLine}" ; then
	addLineFlag='true'
fi
done << ____ADD_LINES
${addLines}
____ADD_LINES

#printf '%d:' "${partNo}" # 【debug】

# trueのとき1加算
if ${addLineFlag} ; then
	echo $(( ${Width} / ${Part} + 1 ))
else
	echo $(( ${Width} / ${Part} ))
fi

partNo=$(( ${partNo} + 1 ))
done

exit 0
) }

# 全体の横幅は何文字にするのか
Cols=${1:-78}

while read LINE ; do

eval set -- ${LINE}

addChars=`roundSh ${Cols} ${#}`

NUM=0
while read NN ; do
	NUM=$(( ${NUM} + 1 ))
	eval 'wordLength_'${NUM}'=${NN}'
done << ____add
${addChars}
____add


NUM=0
for Index in ${@} ; do
NUM=$(( ${NUM} + 1 ))

# wordLength インデックスカラーを表示する幅を文字数で
eval 'wordLength=${wordLength_'${NUM}'}'

# Index        インデックス番号
# wordLength   表示幅を文字数で
echo "${Index}	${wordLength}"

done

echo '0	-1'
done
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	ansi256matrixToMagSh	20201101_085854
ansi256matrixToMagSh(){ (	# ====[shMerge<ins>]====
#!/bin/sh
# ansi256matrixデータの、
# 各行のカーソル移動によるX座標の移動値
# 開始値を0、最大値を359として、360を各行の要素数で割る
# カーソル移動して数値を増減させるときは、この数値を倍して増減する。
# この数値を倍率で割って、マトリックスから行を抜き出し、
# 商に1加算してcut -fすると、インデックス番号が得られる。

while read TR ; do
# ansi256matrixデータの、各行のデータ数を数える
	eval set -- ${TR}
# データを1つズラす度に増減させる値
	echo $(( 360 / ${#} ))
done

# テーブル数が6のとき
# 0   60   120   180   240   300   360
#   1     2     3     4     5    6
# 
# 1:0-59
# 2:60-119
# 3:120-179
# 4:180-239
# 5:240-299
# 6:300-359
# 
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	ansi256matrixToGridSh	20201101_085854
ansi256matrixToGridSh(){ (	# ====[shMerge<ins>]====
#!/bin/sh
# 色番号からカーソルXY座標を得るデータを作成
# インデックス番号表データを、
# 「カラーインデックス番号+1」行:カーソルX座標(0-359):Y座標(0-)
# へ変換する。
# インデックス番号+1行目のデータを取り出すと、カーソルXY座標が得られる。
# インデックス番号は「0-255」で、重複と欠番があってはならない


matrixTR='-1'
indexCheck='-1'

while read LINE ; do

matrixTR=$(( ${matrixTR} + 1 ))
eval 'set -- '${LINE}
# X座標値の倍率を計算する
Mag=$(( 360 / ${#} ))

# カラーインデックス番号	X座標	Y座標
matrixTD='-1'
for Index in ${@} ; do
	matrixTD=$(( ${matrixTD} + 1 ))
	echo "${matrixTR}	$(( ${matrixTD} * Mag ))	${Index}"
done

# カラーインデックスでソート
done | sort -k3n 
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	ansi256viewToSepCode2sh	20201101_085854
ansi256viewToSepCode2sh(){ (	# ====[shMerge<ins>]====
#!/bin/sh
#!/usr/bin/ksh
#!/bin/bash

# viewCodeを受け取って、見えない数字が埋め込まれた端末表示画像データを作成する
# このスクリプトで作成するデータは、呼び出し元プロセスの
# シェル変数に保存して、繰り返し利用する

# セパレータを4つ作成,ESC作成
ESC=`printf "\033"`
FS=`printf "\034"` # 3
GS=`printf "\035"` # 2
RS=`printf "\036"` # 1
US=`printf "\037"` # 0
numToQuotCodeFunc(){
XX="${1}"
shift 1
quotCode=''

for NN in ${@} ; do
case "${NN}" in
( 0 ) quotCode="${quotCode}${US}" ;;
( 1 ) quotCode="${quotCode}${RS}" ;;
( 2 ) quotCode="${quotCode}${GS}" ;;
( 3 ) quotCode="${quotCode}${FS}" ;;
esac
done
eval ${XX}'="${quotCode}"'
}

while read Palette Nums ; do
# パレット表示幅Numsと同じ数連続した半角空白を作る
NN=0
paletteSp=''
while test ${NN} -lt ${Nums} ; do
	paletteSp="${paletteSp} "
	NN=$(( ${NN} + 1 ))
done


case "${Nums}" in
# ----------------------------------------------------------------------
( -* ) # 改行_負の数はすべて改行を意味する
# ----------------------------------------------------------------------
echo "${ESC}[0mN"
continue
;;
# ----------------------------------------------------------------------
( 0 ) # 文字幅が0文字のとき
# ----------------------------------------------------------------------
continue
;;
# ----------------------------------------------------------------------
( * ) # 文字幅がすべて1文字以上のとき
# ----------------------------------------------------------------------

Quot64=$(( ${Palette} / 64 ))
Quot16=$(( ${Palette} % 64 / 16 ))
 Quot4=$(( ${Palette} % 64 % 16 / 4 ))
 Quot1=$(( ${Palette} % 64 % 16 % 4 ))

# 見えない数字を読み込む
numToQuotCodeFunc quotSepNo  ${Quot64} ${Quot16} ${Quot4} ${Quot1}

echo "${ESC}[48;5;${Palette}m${paletteSp}${quotSepNo}"
#printf "${ESC}[48;5;${Palette}m${paletteSp}${quotSepNo}"

;;
esac
done | tr -d '\n' | tr 'N' '\n' | sed -e '{ s/^/colorSep\o037\o036\o035\o034/1 }'
#done  | sed -e '{ s/^/colorSep\o037\o036\o035\o034/1 }'
#done | sed -n -e '
#/N$/!{H;d}
#/N$/{H;g;s/\n//g;s/N$//;s/^/colorSep\o037\o036\o035\o034/1;p;s/.*//;h;d}'
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	sepDrawFocusOvewWrite1sh	20201101_085854
sepDrawFocusOvewWrite1sh(){ (	# ====[shMerge<ins>]====
#!/bin/sh
#!/usr/bin/ksh
#!/bin/dash
#!/usr/bin/yash
#!/usr/bin/zsh
#!/bin/busybox sh
#!/bin/bash

# ----------------------------------------------------------------------
# セパレータコード可視化
# ----------------------------------------------------------------------
# 見えない数字が埋め込まれたセパレータ埋め込みコードを受け取り、
# 指定された見えない数字の場所にカーソルを表示する

fgNo=${1:-245}
bgNo=${2:-250}

fgNoQ64=$(( ${fgNo} / 64 ))
fgNoQ16=$(( ${fgNo} % 64 / 16 ))
 fgNoQ4=$(( ${fgNo} % 64 % 16 / 4 ))
 fgNoQ1=$(( ${fgNo} % 64 % 16 % 4 ))
bgNoQ64=$(( ${bgNo} / 64 ))
bgNoQ16=$(( ${bgNo} % 64 / 16 ))
 bgNoQ4=$(( ${bgNo} % 64 % 16 / 4 ))
 bgNoQ1=$(( ${bgNo} % 64 % 16 % 4 ))

arabicToSepNumFunc(){
# ${1}:代入変数名
# ${2}:Q64位_[0-3]
# ${3}:Q16位_[0-3]
# ${4}:Q4位_[0-3]
# ${5}:Q1位_[0-3]

for NN in ${2} ${3} ${4} ${5} ; do

if test ${NN} -eq 0 ; then
	eval ${1}'="${'${1}'}${US}"'
elif test ${NN} -eq 1 ; then
	eval ${1}'="${'${1}'}${RS}"'
elif test ${NN} -eq 2 ; then
	eval ${1}'="${'${1}'}${GS}"'
elif test ${NN} -eq 3 ; then
	eval ${1}'="${'${1}'}${FS}"'
fi

done
}

QfgNo=''
QbgNo=''

# 疑似4進数の値(FS,GS,RS,US)を番号名に設定
eval `printf "FS=\034  GS=\035  RS=\036  US=\037 "`
arabicToSepNumFunc QfgNo ${fgNoQ64} ${fgNoQ16} ${fgNoQ4} ${fgNoQ1}
arabicToSepNumFunc QbgNo ${bgNoQ64} ${bgNoQ16} ${bgNoQ4} ${bgNoQ1}


# ----------------------------------------------------------------------
# フォーカスマーク付加
# ----------------------------------------------------------------------
focusNo="${3}"


sed -n -e '#n

# overWrite 1行目行頭にエスケープシーケンス埋め込み
1{
s/^/\o033[1;1H\o033[?25l/
}
# overWrite  行末改行前にエスケープシーケンス埋め込み
${
s/$/\o033[?0J\o033[?25h/
}



# sepCodeDraw 不可視セパレータコードを可視化 ---------------------------
/^colorSep\o037\o036\o035\o034/{

# 色用セパレータ行開始マークを削除
s/^colorSep\o037\o036\o035\o034//1

# /231/231色S/    数字を残したまま「色S」を挿入
{
s/'${QfgNo}'/'${QfgNo}'\o033[0;30;103mS/
# / 231/色|       数字と直前の半角空白を削って「色|」を挿入
s/ '${QbgNo}'/\o033[0;30;106m|/
}

# もし「色|色S」があるならば
/\o033\[0;30;106m|\o033\[0;30;103mS/{
# 「色$」に入れ替え
s/\o033\[0;30;106m|\o033\[0;30;103mS/\o033[0;30;107m$/
}

# / 231色S/色S    S前の半角空白を削除
{
s/ '${QfgNo}'\o033\[0;30;103mS/\o033[0;30;103mS/
}

}

# focusMark フォーカスしているならば
/^FOCUS_ID_'${focusNo}'$/{
# 上書きして次の行を読み込む
n
# 矢印を右端に付加
s/$/  \o033[7m <= \o033[0m/

# ↓のフォーカスID削除には該当せず通常出力へ
}

/^FOCUS_ID_/ {
# フォーカスID行を出力せずにcontinue
d
}

# overWrite フォーカスIDではない他の全行ならば
{
s/$/\o033[0K/         # 行末尾に行右側消去を埋め込み
p                     # 出力

}'
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	subMenuSh	20201101_085854
subMenuSh(){ (	# ====[shMerge<ins>]====
#!/bin/sh
#!/usr/bin/posh
#!/bin/busybox sh
#!/bin/bash
#!/usr/bin/yash
#!/usr/bin/ksh
#!/usr/bin/zsh
#!/bin/dash
# 簡単なサブメニューを表示
# リストから一つ選択を求め、リスト番号を出力する
# 標準出力するのはリスト番号の数字のみ
# それ以外のメニュー表示等は、全てエラー出力する

selectList="${1}"      # 選択リストの内容 改行区切りのテキストデータで
windowWidth="${2:-36}" # 表示メニューの幅 文字数
orientY="${3:-4}"      # 表示位置の原点左上の位置 Y
orientX="${4:-10}"     # 表示位置の原点左上の位置 X

# CSIシーケンス開始後、末尾mの前まで
# '\033[97;45m' なら '97;45' と書く
menuColor="${5:-97;45}"


#printf "\033#8" 1>&2 # 【debug】

listCount=`echo "${selectList}" | wc -l`
focusLine='0'

pressKeySh(){ (
stty_BAK=`stty -g`
stty -echo raw
dd count=1 2>/dev/null
stty "${stty_BAK}"
) }


UP____KEY=`printf '\033[A'`
DOWN__KEY=`printf '\033[B'`
ENTER_KEY=`printf '\015'`

#tput sc
printf '\0337'  1>&2 # tput sc
# カーソル消去
printf '\033[?25l' 1>&2

# 表示領域の枠を描画
{
printf "\033[${orientY};${orientX}H"
for NN in `seq 1 ${listCount}` ; do

printf "\033[${orientX}G\033[${menuColor}m%${windowWidth}s\033[0m\n" ' '

done
} 1>&2

while true ; do
{
printf "\033[${orientY};${orientX}H"
echo "${selectList}" |
	sed -e 's/^/ /1' \
	-e "$(( ${focusLine} + 1 ))s/^ />/1" \
	-e "s/.*/\o033[${orientX}G\o033[${menuColor}m&\o033[0m/"
} 1>&2



case "`pressKeySh`" in
( 8 | ${UP____KEY} )
focusLine=$(( ( ${focusLine} - 1 + ${listCount} ) % ${listCount} ))

;;
( 2 | ${DOWN__KEY} )
focusLine=$(( ( ${focusLine} + 1 + ${listCount} ) % ${listCount} ))

;;
( ${ENTER_KEY} | 0 | ' ' )
#tput rc
printf '\0338'  1>&2 # tput rc
printf '\033[?25h'  1>&2
echo $(( ${focusLine} + 1 ))
exit 0

;;
( '*' )
echo ''
exit 1

;;
esac
done
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	effectCodeCheckSh	20201101_085854
effectCodeCheckSh(){ (	# ====[shMerge<ins>]====
#!/bin/sh
#!/usr/bin/zsh
# 文字装飾コードのチェックシートを表示する

# ESC=`printf '\033'` # 【gloval const ESC】# ====[shMerge<disable>]==== #_shMergeDisabled

# ${1}:フォーカスのID値(${2}のデータの行番号-1)
focusIdNo=${1}
# コードリストの行番号(${1}で指定される数値)
codeIdCount='-1' # forループ1回ごとに+1

# 出力は1行ずつechoで
echoLine=''

# ${2}:コードの番号*1000 のリスト 有効/無効(正/負)
# コマンド置換で「-1000 LF -1001 LF 1002 LF 1-1003 ....」の改行を空白に変換(zsh)
set -- `echo ${2}`

for flagNo in ${@} ; do
codeIdCount=$(( ${codeIdCount} + 1 ))

codeNo=$(( ${flagNo#-} - 1000 ))

# 表示文字と色も変数に格納しておく
# コードが有効化されているならば
case "${flagNo}" in
( -* ) Ast=' ' ;;
(  * ) Ast="${ESC}[7m*${ESC}[27m" ;;
esac

# 表示文字と色も変数に格納しておく
# フォーカスが当たっているならば
case ${focusIdNo} in
( ${codeIdCount} )
brL="${ESC}[7m[${ESC}[27m"
brR="${ESC}[7m]${ESC}[27m"
;;
( * )
brL=' '
brR=' '
;;
esac

case "${codeNo}" in # 桁数に合わせて横幅調整
( ? ) # 1文字ならば
echoLine="${echoLine}${brL}${Ast}${brR} ${codeNo}:${ESC}[${codeNo}mCode ${codeNo}${ESC}[0m"
;;
( * ) # 2文字以上ならば
echoLine="${echoLine}${brL}${Ast}${brR}${codeNo}:${ESC}[${codeNo}mCode${codeNo}${ESC}[0m"
;;
esac

if test $(( ( ${codeIdCount} + 1 ) % 6 )) -eq 0 ; then
echo "${echoLine}"
echoLine=''
fi

done

# 16色版は6の倍数以外もサポートする
if test -n "${echoLine}"
then echo "${echoLine}"
fi
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	effectCodeBuildSh	20201101_085854
effectCodeBuildSh(){ (	# ====[shMerge<ins>]====
#!/bin/sh
# 実用できる文字装飾コードを組み立て
eval 'set -- '${1}
IFS=';'
echo "${*}"
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	effectCodeRemoveSh	20201101_085854
effectCodeRemoveSh(){ (	# ====[shMerge<ins>]====
#!/bin/sh
#!/usr/bin/zsh
# 文字装飾コードを有効リストから削除する
# ${1}:'1'
# ${2}以降:' 2 15 1 3 6'
# output:'2 15 3 6'

MM=${1} ; shift 1
LL=''
for NN in ${@} ; do
	if  	test ${NN} -eq ${MM}
	then	true
	else	LL="${LL} ${NN}"
	fi
done
echo ${LL}
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	effectCodeInversionSh	20201101_085854
effectCodeInversionSh(){ (	# ====[shMerge<ins>]====
#!/bin/sh
# 指定行の数値を、正負反転させる
NN=$(( ${1} + 1 ))
sed -n -e "#n
${NN}{
  s/^-/m/
  s/^[^m]/-&/
  s/^m//
}
{
  p
}
"
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	ansi256_216colorSetSh	20201101_085854
ansi256_216colorSetSh(){ (	# ====[shMerge<ins>]====
#!/usr/bin/zsh
#!/bin/sh
# 256カラーパレットの彩色216に、任意のbitカラーを上書きセットする

numTo256colFunc(){
# ${1}:代入する変数名 RR,GG,BBのいずれか
# ${2}:「0-5」の数値 RGBのレベル指定
# ${3}-${8} 0-5レベルで設定する整数値
case "${2}" in
( 0 ) eval ${1}'=${3:-0}' ;;
( 1 ) eval ${1}'=${4:-95}' ;;
( 2 ) eval ${1}'=${5:-135}' ;;
( 3 ) eval ${1}'=${6:-175}' ;;
( 4 ) eval ${1}'=${7:-215}' ;;
( 5 ) eval ${1}'=${8:-255}' ;;
esac
}

for RRR in 0 1 2 3 4 5 ; do # 36の位
numTo256colFunc 'RR' "${RRR}"  ${1} ${2} ${3} ${4} ${5} ${6}
for GGG in 0 1 2 3 4 5 ; do # 6の位
numTo256colFunc 'GG' "${GGG}"  ${1} ${2} ${3} ${4} ${5} ${6}
for BBB in 0 1 2 3 4 5 ; do # 1の位
numTo256colFunc 'BB' "${BBB}"  ${1} ${2} ${3} ${4} ${5} ${6}

Index=$(( 36 * ${RRR} + 6 * ${GGG} + ${BBB} + 16 ))
printf "\033]4;${Index};rgb:%02x/%02x/%02x\007" "${RR}" "${GG}" "${BB}"

#printf "%02x %02x %02x\n" "${RR}" "${GG}" "${BB}"
done
done
done
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	ansi256_24rampSetSh	20201101_085854
ansi256_24rampSetSh(){ (	# ====[shMerge<ins>]====
#!/bin/sh
# 256カラーパレットのグレーランプ24に、任意の明るさを上書きセットする
# インデックス:232-255
# (明るさの段階)=Index-231
# (明るさ0-255で)=10l+8

# ${1} 掛け算の係数
# ${2} 加減算値

for Index in `seq 232 255` ; do

Step=$(( ${Index} - 231 ))
Luminous=$(( ${1:-10} * ${Step} + ${2:-8} ))

  if test ${Luminous} -gt 255 ; then
Luminous='255'
elif test ${Luminous} -lt 0 ; then
Luminous='0'
fi

printf "\033]4;${Index};rgb:%02x/%02x/%02x\007" "${Luminous}" "${Luminous}" "${Luminous}"
#printf "%d %02x/%02x/%02x\n" "${Index}" "${Luminous}" "${Luminous}" "${Luminous}"

done
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	ansi256_numToRGBsh	20201101_085854
ansi256_numToRGBsh(){ (	# ====[shMerge<ins>]====
#!/bin/sh


# 標準入力から「0-255」の数字を入力すると、
# RGB256階調の数値を出力する。
# 「0-16」のときは「__」を出力する。(「--」「-」は不適切 「set --」関係)


while read Index ; do
RR='__'
GG='__'
BB='__'


if test "${Index}" -ge 0 && test "${Index}" -le 15 ; then

echo "${RR}	${GG}	${BB}	${Index}"

elif test "${Index}" -ge 16 && test "${Index}" -le 231 ; then

numTo256Func(){
# ${1}:代入する変数名 RR,GG,BBのいずれか
# ${2}:「0-5」の数値 RGBのレベル指定
case "${2}" in
( 0 ) eval ${1}'=0' ;;
( 1 ) eval ${1}'=95' ;;
( 2 ) eval ${1}'=135' ;;
( 3 ) eval ${1}'=175' ;;
( 4 ) eval ${1}'=215' ;;
( 5 ) eval ${1}'=255' ;;
esac
}

numTo256Func RR $(( ( ${Index} - 16 ) / 36 ))
numTo256Func GG $(( ( ( ${Index} - 16 ) % 36 ) / 6 ))
numTo256Func BB $(( ( ( ${Index} - 16 ) % 36 ) % 6 ))

echo "${RR}	${GG}	${BB}	${Index}"

elif test "${Index}" -ge 232 && test "${Index}" -le 255 ; then


RR=$(( ( ( ${Index} - 232 ) * 10 ) + 8 ))
GG="${RR}"
BB="${RR}"

echo "${RR}	${GG}	${BB}	${Index}"

fi
done
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	rgbToHSLawk1sh	20201101_085854
rgbToHSLawk1sh(){ (	# ====[shMerge<ins>]====
#!/bin/sh
# RGB to HSL
# RGB in:0-255
# H 0-359 S 0-255 L 0-255

ofmt_parm="%.${1:-0}f"
awk -v range_select="${2:-0}" -v OFMT="${ofmt_parm}" -- '

BEGIN{
#OFMT="%.2f"
#OFMT="%.0f"
#OFMT="%d"
#range_select=1

FS = "\t"
OFS = "\t"
}

/__/ {
print ( $0 )
next
}

{
rr = $1
gg = $2
bb = $3
index_no = $4

# 計算方法の振り分け
if ( rr == gg && rr == bb ) {
hsl_calc = 0
} else if ( rr >= gg && rr > bb ) {
hsl_calc = 1
} else if ( gg >= bb && gg > rr ) {
hsl_calc = 2
} else if ( bb >= rr && bb > gg ) {
hsl_calc = 3
}


if ( hsl_calc == 1 ) { # red -------------------------------------------
g_m_b = gg - bb

if ( g_m_b >= 0 ){
	max_p_min = rr + bb
	max_m_min = rr - bb
} else {
	max_p_min = rr + gg
	max_m_min = rr - gg
}

hhsl = ( 60 * g_m_b ) / max_m_min

if ( hhsl < 0 ){
hhsl = hhsl + 360
}

} else if ( hsl_calc == 2 ) { # green ----------------------------------
b_m_r = bb - rr


if ( b_m_r >= 0 ){
	max_p_min = gg + rr
	max_m_min = gg - rr
} else {
	max_p_min = gg + bb
	max_m_min = gg - bb
}

hhsl = ( 60 * b_m_r ) / max_m_min + 120
if ( hhsl < 0 ){
hhsl = hhsl + 360
}

} else if ( hsl_calc == 3 ) { # blue -----------------------------------
r_m_g = rr - gg


if ( r_m_g >= 0 ){
	max_p_min = bb + gg
	max_m_min = bb - gg
} else {
	max_p_min = bb + rr
	max_m_min = bb - rr
}

hhsl = ( 60 * r_m_g ) / max_m_min + 240
if ( hhsl < 0 ){
hhsl = hhsl + 360
}


} else if ( hsl_calc == 0 ) { # white ----------------------------------
hhsl = 0

}

if ( hsl_calc == 1 || hsl_calc == 2 || hsl_calc == 3 ) {
cnt = max_p_min / 2

if ( cnt <= 127.5 ){
	hssl = ( max_m_min * 255 ) / max_p_min
}else { #  if ( cnt > 127.5 )
	hssl = ( max_m_min * 255 ) / ( 510 - max_p_min )
}

hsll = max_p_min / 2

} else {
hssl = 0
hsll = rr
}

if ( range_select == 0 ){

print ( hhsl ,  hssl ,  hsll ,  index_no  )

} else {
hhsl = hhsl * 100 / 360
hssl = hssl * 100 / 255
hsll = hsll * 100 / 255
print ( hhsl  , hssl  , hsll , index_no )
}
}'
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	rgbToHSVawk1sh	20201101_085854
rgbToHSVawk1sh(){ (	# ====[shMerge<ins>]====
#!/bin/sh
# RGB to HSV
# RGB in:0-255
# H 0-359 S 0-255 V 0-255

ofmt_parm="%.${1:-0}f"
awk -v range_select="${2:-0}" -v OFMT="${ofmt_parm}" -- '

BEGIN{
#OFMT="%.2f"
#OFMT="%.0f"
#OFMT="%d"
#range_select=1

FS = "\t"
OFS = "\t"
}

/__/ {
print ( $0 )
next
}

{
rr = $1
gg = $2
bb = $3
index_no = $4

# 計算方法の振り分け
if ( rr == gg && rr == bb ) {
hsv_calc = 0
} else if ( rr >= gg && rr > bb ) {
hsv_calc = 1
} else if ( gg >= bb && gg > rr ) {
hsv_calc = 2
} else if ( bb >= rr && bb > gg ) {
hsv_calc = 3
}


if ( hsv_calc == 1 ) { # red -------------------------------------------
max = rr
g_m_b = gg - bb

if ( g_m_b >= 0 ){
	max_m_min = rr - bb
} else {
	max_m_min = rr - gg
}

hhsv = ( 60 * g_m_b ) / max_m_min

if ( hhsv < 0 ){
hhsv = hhsv + 360
}

} else if ( hsv_calc == 2 ) { # green ----------------------------------
max = gg
b_m_r = bb - rr

if ( b_m_r >= 0 ){
	max_m_min = gg - rr
} else {
	max_m_min = gg - bb
}

hhsv = ( 60 * b_m_r ) / max_m_min + 120
if ( hhsv < 0 ){
hhsv = hhsv + 360
}

} else if ( hsv_calc == 3 ) { # blue -----------------------------------
max = bb
r_m_g = rr - gg

if ( r_m_g >= 0 ){
	max_m_min = bb - gg
} else {
	max_m_min = bb - rr
}

hhsv = ( 60 * r_m_g ) / max_m_min + 240
if ( hhsv < 0 ){
hhsv = hhsv + 360
}

} else if ( hsv_calc == 0 ) { # white ----------------------------------
max = rr
hhsv = 0

}

if ( hsv_calc == 1 || hsv_calc == 2 || hsv_calc == 3 ) {
hssv = ( max_m_min * 255 ) / max
hsvv = max

} else {
hssv = 0
hsvv = max
}

if ( range_select == 0 ){

print ( hhsv ,  hssv ,  hsvv ,  index_no  )

} else {
hhsv = hhsv * 100 / 360
hssv = hssv * 100 / 255
hsvv = hsvv * 100 / 255
print ( hhsv  , hssv  , hsvv , index_no )
}
}'
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	term256ColorLevelGet1sh	20201101_085854
term256ColorLevelGet1sh(){ (	# ====[shMerge<ins>]====
#!/bin/sh
#!/bin/busybox sh
#!/usr/bin/yash
#!/usr/bin/posh
#!/usr/bin/zsh
#!/bin/bash
#!/usr/bin/ksh

# 端末に現在設定されている色レベルを取得する
# 位置パラメータに数値「0-255」を指定すること

getColorLevelSh(){ (
stty_BAK="`stty -g`"

# rawは複合設定で、その一部は「-icanon min 1 time 0」である。
# min,timeは-icanonと共に使用する。
# min は制限時間中の読み込み成功と見なす文字数の最少数
# time は読み込みのタイムアウト時間を0.1秒単位で指定する
# min 0 time 10 は「入力データが無くとも1秒で戻る」
stty -echo raw min 0 time 10
printf '\033]4;'${1}';?\007' 1>&2
dd count=1 2>/dev/null
stty "${stty_BAK}"
) }

#223	]4;223;rgb:ffff/d7d7/afaf
IFS_BAK="${IFS}"
BEL=`printf '\007'`
ESC=`printf '\033'`

for NN in ${@} ; do

termReturn=`getColorLevelSh ${NN}`

case "${termReturn}" in
( "${ESC}]4;${NN};rgb:"*"${BEL}" ) true   ;;
(               *                ) exit 1 ;;
esac

# ${ESC}]4;223;rgb:ffff/d7d7/afaf${BEL} -> 223;rgb:ffff/d7d7/afaf${BEL}
termReturnTrim="${termReturn#*;}"
# 223;rgb:ffff/d7d7/afaf${BEL} -> 223;rgb:ffff/d7d7/afaf
termReturnTrim="${termReturnTrim%${BEL}}"
# 223;rgb:ffff/d7d7/afaf -> 223
indexNo="${termReturnTrim%;*}"
# 223;rgb:ffff/d7d7/afaf -> ffff/d7d7/afaf
termReturnTrim="${termReturnTrim#*:}"

RR=${termReturnTrim%%/*}
termReturnTrim=${termReturnTrim#*/}

GG=${termReturnTrim%/*}
BB=${termReturnTrim#*/}

# 下2桁を削って数字が残るなら4桁とみなす
if test -n "${RR%??}" ; then
RR="${RR%??}"
GG="${GG%??}"
BB="${BB%??}"
fi

# 16進数出力
#echo "${RR}	${GG}	${BB}	${indexNo}"
# 10進数出力
printf '%d	%d	%d	%d\n' "0x${RR}" "0x${GG}" "0x${BB}" "${indexNo}" 

done
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	pressKeySh	20201101_085854
pressKeySh(){ (	# ====[shMerge<ins>]====
#!/bin/sh
# キー入力を1回のみ受け取る
stty_BAK=`stty -g`
stty -echo raw
dd count=1 2>/dev/null
stty "${stty_BAK}"
) }	# ====[shMerge</ins>]====

# # ====[shMerge]====	pressKeyScan256sh	20201101_085854
pressKeyScan256sh(){ (	# ====[shMerge<ins>]====
#!/bin/sh

focusID=${1:-0}

# 操作キー取得
# eval `printf 'ESC=\033 ctrl_plus_C=\003 ENTER_KEY=\015 '` # 【gloval const ESC ctrl_plus_C ENTER_KEY】# ====[shMerge<disable>]==== #_shMergeDisabled

UP____KEY="${ESC}[A"
DOWN__KEY="${ESC}[B"
RIGHT_KEY="${ESC}[C"
LEFT__KEY="${ESC}[D"
SPACE_KEY=' '
TAB______KEY='	'
PAGE_UP___KEY="${ESC}[5~"
PAGE_DOWN_KEY="${ESC}[6~"

stty_BAK=`stty -g`
stty -echo raw


while true ; do


case "`dd count=1 2>/dev/null`" in
# ----------------------------------------------------------------------
( 8 | "${UP____KEY}" ) 
# ----------------------------------------------------------------------
case "${focusID}" in
( 0 )
echo '0__UP'
break 1
;;
( 1 )
echo '1__UP'
break 1
;;
( 2 )
echo '2__UP'
break 1
;;
esac

;;
# ----------------------------------------------------------------------
( 2 | "${DOWN__KEY}" ) 
# ----------------------------------------------------------------------
case "${focusID}" in
( 0 )
echo '0__DOWN'
break 1
;;
( 1 )
echo '1__DOWN'
break 1
;;
( 2 )
echo '2__DOWN'
break 1
;;
esac

;;
# ----------------------------------------------------------------------
( 6 | "${RIGHT_KEY}" ) 
# ----------------------------------------------------------------------
case "${focusID}" in
( 0 )
echo '0__RIGHT'
break 1
;;
( 1 )
echo '1__RIGHT'
break 1
;;
( 2 )
echo '2__RIGHT'
break 1
;;
esac

;;
# ----------------------------------------------------------------------
( 4 | "${LEFT__KEY}" ) 
# ----------------------------------------------------------------------
case "${focusID}" in
( 0 )
echo '0__LEFT'
break 1
;;
( 1 )
echo '1__LEFT'
break 1
;;
( 2 )
echo '2__LEFT'
break 1
;;
esac

;;
# ----------------------------------------------------------------------
( s | '-' ) 
# ----------------------------------------------------------------------
echo '_MINUS'
break 1

;;
# ----------------------------------------------------------------------
( 0 | "${SPACE_KEY}" ) 
# ----------------------------------------------------------------------
case "${focusID}" in
( 0 )
	true
;;
( 1 )
	true
;;
( 2 )
echo '2__SPACE'
break 1
;;
esac

;;
# ----------------------------------------------------------------------
( "${PAGE_UP___KEY}" | 9 )
# ----------------------------------------------------------------------
echo '_PAGE_UP'
break 1

;;
# ----------------------------------------------------------------------
( "${PAGE_DOWN_KEY}" | 3 )
# ----------------------------------------------------------------------
echo '_PAGE_DOWN'
break 1

;;
# ----------------------------------------------------------------------
( '*' )
# ----------------------------------------------------------------------
echo '_ASTER'
break 1

;;
# ----------------------------------------------------------------------
( '.' )
# ----------------------------------------------------------------------
echo '_PERIOD'
break 1

;;
# ----------------------------------------------------------------------
( '+' | a )
# ----------------------------------------------------------------------
echo '_PLUS'
break 1

;;
# ----------------------------------------------------------------------
( "${ENTER_KEY}" )
# ----------------------------------------------------------------------
echo '_ENTER'
break 1

;;
# ----------------------------------------------------------------------
( '/' | 'q' | "${ctrl_plus_C}" ) 
# ----------------------------------------------------------------------
echo '_QUIT'
break 1

;;

esac
done


stty "${stty_BAK}"
exit 0
) }	# ====[shMerge</ins>]====

# ======================================================================================
# シェル関数_外部へ分離できない
# ======================================================================================


matrixToArrFunc(){ # 表形式データを疑似配列に変換する
# matrixName_NN行目_MM列目
# ${2}を変数名として、行を_NN,列を_MMとしたシェル変数を作成する
# NN,MMは[0]開始
matrixData="${1}"
matrixName="${2}"

NN='-1'
while read LINE ; do
NN=$(( ${NN} + 1 ))

MM='-1'
eval set -- ${LINE}
for TD in ${@} ; do
MM=$(( ${MM} + 1 ))
eval ${matrixName}_${NN}_${MM}'="${TD}"'
done

done << ____MATRIX
${matrixData}
____MATRIX
}

resetFunc(){ # 初期起動時とリセット時

# これから処理するカラーパレット表を読み込む
currentPalette=`colorTableListSh ${colorTableNo}`
# 列データ(X座標値)は、それぞれの行で何倍するのか
currentMags=`echo "${currentPalette}" | ansi256matrixToMagSh`
# 表データは何行あるのか
paletteLineCount=`echo "${currentPalette}" | wc -l`
# 表データに横幅データを組み込んだデータを作成し、
colorTableViewCode=`echo "${currentPalette}" | ansi256matrixToViewCodeSh ${paletteWidth} `
# 横幅指定込みのデータから、不可視数値埋め込み画像データを作成
colorTableSepImg=`echo "${colorTableViewCode}" | ansi256viewToSepCode2sh`

# 現在選択中のカラーパレットのデータを、シェル変数の疑似配列に変換する(高速化目的)
matrixToArrFunc "${currentPalette}" colorTableArr
# 列データの倍率をシェル変数の疑似配列化する(高速化目的)
matrixToArrFunc "${currentMags}" colorTableMagsArr

# 初期色番号設定
# 初期値を設定しつつ、継承もする
mainFgNo="${mainFgNo:-15}"
mainBgNo="${mainBgNo:-0}"
subFgNo="${subFgNo:-8}"
subBgNo="${subBgNo:-11}"

# ---- リセット処理しても色番号を維持するため ---------------------------
# 1.色番号指定で起動
# 2.起動時カラーテーブルの${colorTableGrid}を新規作成
# 3.XY座標を${colorTableGrid}から割り出す
# 4.${colorTableGrid}を破棄
# 5.XY座標で通常処理ループを処理
# 6.カラーテーブル切替(リセット)時は、色番号を保持してXY座標を破棄
# 7.${colorTableGrid}を作成...以後は起動時と同様に

# 色インデックス番号からXY座標を得る表
colorTableGrid=`echo "${currentPalette}" | ansi256matrixToGridSh`

# カーソル位置 Y座標,X座標 設定
# ${colorTableGrid}を読み 色番号データを  X変数に代入  Y変数に代入
set -- `echo "${colorTableGrid}" | sed -n -e $(( ${mainFgNo} + 1 ))'{ p;q }'`
MAIN_FG_Y="${1}"
MAIN_FG_X="${2}"
set -- `echo "${colorTableGrid}" | sed -n -e $(( ${mainBgNo} + 1 ))'{ p;q }'`
MAIN_BG_Y="${1}"
MAIN_BG_X="${2}"
set -- `echo "${colorTableGrid}" | sed -n -e $(( ${subFgNo} + 1 ))'{ p;q }'`
SUB_FG_Y="${1}"
SUB_FG_X="${2}"
set -- `echo "${colorTableGrid}" | sed -n -e $(( ${subBgNo} + 1 ))'{ p;q }'`
SUB_BG_Y="${1}"
SUB_BG_X="${2}"

# 使用完了シェル変数を消去
colorTableGrid=''
colorTableViewCode=''
currentPalette=''

# リセット処理完了
resetFlag='false'
}
# ======================================================================================
# シェル関数_ メインループ キーアクション
# ======================================================================================
keyActionFunc__QUIT(){
	exit 0
}
keyActionFunc_0__UP(){
MAIN_FG_Y=$(( ( ${MAIN_FG_Y} - 1 + ${paletteLineCount} ) % ${paletteLineCount} ))
}
keyActionFunc_1__UP(){
MAIN_BG_Y=$(( ( ${MAIN_BG_Y} - 1 + ${paletteLineCount} ) % ${paletteLineCount} ))
}
keyActionFunc_2__UP(){
effectCodeFocusY=$(( ( ${effectCodeFocusY} - 1 + ${effectCodeLineCount} ) % ${effectCodeLineCount} ))
}
keyActionFunc_0__DOWN(){
MAIN_FG_Y=$(( ( ${MAIN_FG_Y} + 1 + ${paletteLineCount} ) % ${paletteLineCount} ))
}
keyActionFunc_1__DOWN(){
MAIN_BG_Y=$(( ( ${MAIN_BG_Y} + 1 + ${paletteLineCount} ) % ${paletteLineCount} ))
}
keyActionFunc_2__DOWN(){
effectCodeFocusY=$(( ( ${effectCodeFocusY} + 1 + ${effectCodeLineCount} ) % ${effectCodeLineCount} ))
}
keyActionFunc_0__RIGHT(){
MAIN_FG_X=$(( ( ${MAIN_FG_X} + 1 * ${mainFgMag} + 360 ) % 360 ))
}
keyActionFunc_1__RIGHT(){
MAIN_BG_X=$(( ( ${MAIN_BG_X} + 1 * ${mainBgMag} + 360 ) % 360 ))
}
keyActionFunc_2__RIGHT(){
effectCodeFocusX=$(( ( ${effectCodeFocusX} + 1 + 6 ) % 6 ))
}
keyActionFunc_0__LEFT(){
MAIN_FG_X=$(( ( ${MAIN_FG_X} - 1 * ${mainFgMag} + 360 ) % 360 ))
}
keyActionFunc_1__LEFT(){
MAIN_BG_X=$(( ( ${MAIN_BG_X} - 1 * ${mainBgMag} + 360 ) % 360 ))
}
keyActionFunc_2__LEFT(){
effectCodeFocusX=$(( ( ${effectCodeFocusX} - 1 + 6 ) % 6 ))
}
keyActionFunc__MINUS(){
FFXX="${MAIN_FG_X}"
FFYY="${MAIN_FG_Y}"
BBXX="${MAIN_BG_X}"
BBYY="${MAIN_BG_Y}"
MAIN_FG_X="${SUB_FG_X}"
MAIN_FG_Y="${SUB_FG_Y}"
MAIN_BG_X="${SUB_BG_X}"
MAIN_BG_Y="${SUB_BG_Y}"
SUB_FG_X="${FFXX}"
SUB_FG_Y="${FFYY}"
SUB_BG_X="${BBXX}"
SUB_BG_Y="${BBYY}"
}
keyActionFunc__PLUS(){ (
clear

codeSampSub(){ (
fgNo="${1}"
bgNo="${2}"
effectCode="${3}"

printf "\033[7m%"`tput cols`"s\015" ' ' # 背景マーカーラインを引いてからCR
if test -z "${effectCode}" ; then
printf '  %s\033[0m\n' "\033[38;5;${fgNo}m\033[48;5;${bgNo}m"
else
printf '  %s\033[0m\n' "\033[38;5;${fgNo}m\033[48;5;${bgNo}m\033[${effectCode}m"
fi
) }

colorDetailSub(){ (
colorNo="${1}"

eval 'RR=${colorLevelRGBarr_'${colorNo}'_0}'
eval 'GG=${colorLevelRGBarr_'${colorNo}'_1}'
eval 'BB=${colorLevelRGBarr_'${colorNo}'_2}'

printf "\033[48;5;${colorNo}m%26s\033[0m %s\n" ' ' "256color \\033[48;5;${colorNo}m"
printf "\033[48;2;${RR};${GG};${BB}m%26s\033[0m %s\n" ' ' "24bit \\033[48;2;${RR};${GG};${BB}m"

printf '%s%2s%6s%4s %2s%6s%4s %2s%6s%5s\n' \
'RGB(' "R:" "${RR}" "/255" "G:" "${GG}" "/255" "B:" "${BB}" "/255)"
if expr "${RR}" + 1 2>/dev/null 1>&2 ; then
printf '%s%2s   x%02X%4s %2s   x%02X%4s %2s   x%02X%5s\n' \
'RGB(' "R:" "${RR}" "/xFF" "G:" "${GG}" "/xFF" "B:" "${BB}" "/xFF)"
fi

echo "${RR}	${GG}	${BB}	${colorNo}" | rgbToHSLawk1sh 2 0 | { read HH SS LL INDEX
printf '%s%2s%6s%4s %2s%6s%4s %2s%6s%5s\n' \
'HSL(' "H:" "${HH}" "/360" "S:" "${SS}" "/255" "L:" "${LL}" "/255)"
}
echo "${RR}	${GG}	${BB}	${colorNo}" | rgbToHSLawk1sh 2 1 | { read HH SS LL INDEX
printf '%s%2s%6s%4s %2s%6s%4s %2s%6s%5s\n' \
'HSL(' "H:" "${HH}" "/100" "S:" "${SS}" "/100" "L:" "${LL}" "/100)"
}
echo "${RR}	${GG}	${BB}	${colorNo}" | rgbToHSVawk1sh 2 0 | { read HH SS VV INDEX
printf '%s%2s%6s%4s %2s%6s%4s %2s%6s%5s\n' \
'HSV(' "H:" "${HH}" "/360" "S:" "${SS}" "/255" "V:" "${VV}" "/255)"
}
echo "${RR}	${GG}	${BB}	${colorNo}" | rgbToHSVawk1sh 2 1 | { read HH SS VV INDEX
printf '%s%2s%6s%4s %2s%6s%4s %2s%6s%5s\n' \
'HSV(' "H:" "${HH}" "/100" "S:" "${SS}" "/100" "V:" "${VV}" "/100)"
}
) }

codeSampSub "${mainFgNo}" "${mainBgNo}" "${EFFECT_CODE}"
printf \
"\033[${EFFECT_CODE}m\033[38;5;${mainFgNo};48;5;${mainBgNo}m%s\033[0m %6s %s\n"\
"\033[${EFFECT_CODE}m\033[38;5;${mainFgNo};48;5;${mainBgNo}m%s\033[0m\n"\
	"${MAIN_SAMPLE}" "${mainFgNo};${mainBgNo}" "${EFFECT_CODE}" \
	"${FREE_SAMPLE:-        }"
colorDetailSub ${mainFgNo}
colorDetailSub ${mainBgNo}

codeSampSub "${subFgNo}" "${subBgNo}" "${EFFECT_CODE}"
printf \
"\033[${EFFECT_CODE}m\033[38;5;${subFgNo};48;5;${subBgNo}m%s\033[0m %6s %s\n"\
"\033[${EFFECT_CODE}m\033[38;5;${subFgNo};48;5;${subBgNo}m%s\033[0m\n"\
	"${SUB_SAMPLE}" "${subFgNo};${subBgNo}"  "${EFFECT_CODE}" \
	"${FREE_SAMPLE:-        }"
colorDetailSub ${subFgNo}
colorDetailSub ${subBgNo}

pressKeySh
) }

keyActionFunc__ASTER(){
if NN=`subMenuSh "${subMenuAst}" ${subMenuAstParm2}  ${subMenuAstParm3} \
	${subMenuAstParm4} ${subMenuAstParm5}` ; then
subMenuAst${NN}
else
	true
fi
}
keyActionFunc_2__SPACE(){
XY=$(( ${effectCodeFocusY} * 6 + ${effectCodeFocusX} ))

# idフラグ番号_$((id + 1000 * -1))
MM=`echo "${effectCodeFlags}" | sed -n -e "$(( ${XY} + 1 )){ p;q }"`
# id番号
NN=$(( ${MM#-} - 1000 ))

if test ${MM} -le -1 ; then # 現在無効
effectCodeList="${effectCodeList} ${NN}"

else
eval 'set -- '${effectCodeList}
effectCodeList=`effectCodeRemoveSh ${NN} ${@}`

fi

# 有効無効を反転
effectCodeFlags="`echo "${effectCodeFlags}" | effectCodeInversionSh ${XY}`"

# テキスト装飾コードを構築
EFFECT_CODE=`effectCodeBuildSh "${effectCodeList}"`
}
keyActionFunc__PERIOD(){ # 色配置切替
if colorTableListSh $(( ${colorTableNo} + 1 )) 1>/dev/null ; then
	colorTableNo=$(( ${colorTableNo} + 1 ))
else
	colorTableNo='0'
fi

resetFlag='true'
}

keyActionFunc__ENTER(){ # 再描画
clear
}
keyActionFunc__PAGE_UP(){
focusID=$(( ( ${focusID} - 1 + 3 ) % 3 ))
}
keyActionFunc__PAGE_DOWN(){
focusID=$(( ( ${focusID} + 1 + 3 ) % 3 ))
}

# ======================================================================================
# シェル関数_アスタリスクで起動するサブメニュー
# ======================================================================================

subMenuAst='文字色をインデックス番号で指定する
背景色をインデックス番号で指定する
サンプルテキストを書き換える
カラーパレットの幅を画面に合わせる
カラーパレットを標準色にセットする
カラーレベル情報を端末から読み出す
シェルもどき【debug】
疑似配列,シェル変数 閲覧【debug】'
subMenuAstParm2='40'    # ウィンドウ幅文字数
subMenuAstParm3='8'     # 原点行数
subMenuAstParm4='4'     # 原点文字数
subMenuAstParm5='97;45' # 色指定_16色指定で

subMenuAst1(){
echo '------ 文字色をインデックス番号で指定する ------------------------'
echo '(0-255) 数値を指定'
read NN
if test "${NN}" -ge 0 && test "${NN}" -le 255 ; then
	mainFgNo=${NN}
	resetFlag='true'
else
	return 0
fi
}
subMenuAst2(){
echo '------ 背景色をインデックス番号で指定する ------------------------'
echo '(0-255) 数値を指定'
read NN
if test "${NN}" -ge 0 && test "${NN}" -le 255 ; then
	mainBgNo=${NN}
	resetFlag='true'
else
	return 0
fi
}

subMenuAst3(){
echo '------ サンプルテキストを入力 ------------------------------------'
FREE_SAMPLE=`read XX ; echo "${XX}"`
}

subMenuAst4(){ # カラーパレットを画面幅に合わせる
paletteWidth=`tput cols`
resetFlag='true'
}
subMenuAst5(){ (
echo '------ 彩色領域216色の設定を上書き パラメータを指定 --------------
default 0 95 135 175 215 255 (0-5の階調レベル)'
read XX
eval 'set -- '${XX}
ansi256_216colorSetSh ${@}
echo '------ 白黒階調領域24色の設定を上書き パラメータを指定 -----------
default 10 8 (直線の傾き オフセット)'
read XX
eval 'set -- '${XX}
ansi256_24rampSetSh ${@}
) }
subMenuAst6(){
echo '------ カラーレベル情報を端末から取得して再構築 ------------------'
XX="`term256ColorLevelGet1sh $(seq 0 255) | tee /dev/stderr`"
if test -z "${XX}" ; then
echo '端末から色レベル情報を読み出せませんでした。' 1>&2
read WAIT
return
fi
matrixToArrFunc "${XX}" colorLevelRGBarr
matrixToArrFunc "`echo "${XX}" | rgbToHSLawk1sh 0 0 2>/dev/null`" colorLevelHSLarr
matrixToArrFunc "`echo "${XX}" | rgbToHSVawk1sh 0 0 2>/dev/null`" colorLevelHSVarr
}
subMenuAst7(){
echo '------ shell -----------------------------------------------------
主処理と同一プロセスでコマンドを入力実行します。
何も入力せずにEnterすると戻ります。'
while read XX ; do
if test -z "${XX}" ; then
	return 0
else
eval "${XX}"
fi
done
}
subMenuAst8(){ ( # 擬似配列の全て,シェル変数の一部を一覧表示
matrixScanSub(){ (
echo "----疑似配列読み出しテスト ${1} ----------------------------------"
NN='-1'
while true ; do
NN=$(( ${NN} + 1 ))
eval 'if test -z "${'${1}'_'${NN}'_0}"
then break
fi'
printf '%d:	' ${NN}
MM='-1'
while true ; do
MM=$(( ${MM} + 1 ))
eval 'if test -z "${'${1}'_'${NN}'_'${MM}}'"
then break
fi'
eval 'printf "%s	" "${'${1}'_'${NN}'_'${MM}}'"'
done
echo
done
) }
for XX in colorLevelRGBarr colorLevelHSLarr colorLevelHSVarr colorTableMagsArr colorTableArr ; do
matrixScanSub ${XX} | less
done
{ echo '---- ${colorTableViewCode} -------------------------------------------'
colorTableListSh ${colorTableNo} | ansi256matrixToViewCodeSh ${paletteWidth} |
 nl -v1 -s':' ; } | less
{ echo '---- ${colorTableGrid} -----------------------------------------------'
colorTableListSh ${colorTableNo} | ansi256matrixToGridSh | nl -v0 -s':' ; } | less
clear
echo '---- ${colorTableSepImg} 不可視数字の可視化 ----------------------------'
echo "${colorTableSepImg}" | awk --posix '{ gsub( "\034" , "3" , $0 ) ; gsub( "\035" , "2" , $0 ) 
gsub( "\036" , "1" , $0 ) gsub( "\037" , "0" , $0 ) ; print $0 }'
echo 'read WAIT'
read WAIT
) }

# ======================================================================================
#  デバッグ
# ======================================================================================
debug1Sub(){ (
printf '\033[?0J'
printf '%s' "${PRESS_KEY}" | od -An -tc -v
printf '%s' "${PRESS_KEY}" | od -An -to1 -v
) }
debug2Sub(){ (
printf '\033[?0J'
echo '\
	mainFgNo	mainBgNo	subFgNo	subBgNo
	MAIN_FG_X	MAIN_BG_X	SUB_FG_X	SUB_BG_X
	MAIN_FG_Y	MAIN_BG_Y	SUB_FG_Y	SUB_BG_Y
	mainFgMag	mainBgMag	subFgMag	subBgMag' | while read TD0 TD1 TD2 TD3 ; do
eval 'echo "${TD0}:${'${TD0}'}:${TD1}:${'${TD1}'}:${TD2}:${'${TD2}'}:${TD3}:${'${TD3}'}"'
done | column -t -s':' | column
eval 'echo mainFgNo="\${colorTableArr_'${MAIN_FG_Y}'_\$(( '${MAIN_FG_X}' / '${mainFgMag}' ))}"'
eval 'echo mainBgNo="\${colorTableArr_'${MAIN_BG_Y}'_\$(( '${MAIN_BG_X}' / '${mainBgMag}' ))}"'
eval 'echo subFgNo="\${colorTableArr_'${SUB_FG_Y}'_\$(( '${SUB_FG_X}' / '${subFgMag}' ))}"'
eval 'echo subBgNo="\${colorTableArr_'${SUB_BG_Y}'_\$(( '${SUB_BG_X}' / '${subBgMag}' ))}"'
) }
debug3Sub(){ (
printf '\033[?0J'
for XX in \
 focusID colorTableNo \
 effectCodeFocusX effectCodeFocusY effectCodeLineCount
do
eval 'echo "${XX}:${'${XX}'}"'
done | column -t -s':' | column
) }
debug4Sub(){ ( # RGB,HSV,HSL
for XX in \
 mainFgRR mainFgGG mainFgBB mainFgHHSL mainFgHSSL mainFgHSLL mainFgHHSV mainFgHSSV mainFgHSVV \
 mainBgRR mainBgGG mainBgBB mainBgHHSL mainBgHSSL mainBgHSLL mainBgHHSV mainBgHSSV mainBgHSVV 
do
eval 'echo "${XX}:${'${XX}'}"'
done | column -t -s':' | column
) }
debug5Sub(){ ( # 文字装飾コード
echo "${effectCodeList}"
echo "${EFFECT_CODE}"
echo ${effectCodeFlags}
) }


# ======================================================================================
# スタートアップ処理_定数、リセットしても維持する変数
# ======================================================================================

# 色番号 メインサンプルとサブサンプルの前景色(文字色)と背景色
# 空白のときはデフォルト値が代入される
# 処理途中でリセットされると、処理中の値が継承される
# ここで数値を入れておくと、継承と同じ処理で起動する
mainFgNo=''
mainBgNo=''
subFgNo=''
subBgNo=''

# 色インデックス表の何番を初期起動するのか
colorTableNo='0'

# カーソルで選択する対象を選ぶ
# 0:MAIN_FG_X,Y
# 1:MAIN_BG_X,Y
# 2:テキスト装飾コード
focusID='0'

# 文字装飾コードチェックシート カーソル初期位置
effectCodeFocusX='0'
effectCodeFocusY='0'

# テキスト装飾コードの表示行数
effectCodeLineCount=$(( `effectCodeList256Sh | wc -l` / 6 ))

# テキスト装飾コードからフラグ用定数を作成
# 1000を足して負にしたもの(「0」に正負をつけるため)
effectCodeFlags=`effectCodeList256Sh | while read NN ; do
echo '-'$(( ${NN} + 1000 ))
done`

# テキスト装飾コード有効リスト
# 有効にした「順番に」改行区切りでコード番号が入る
# 「1,2,3」と「2,3,1」は異なる
effectCodeList=''

# テキスト装飾コードチェック表を端末表示する、作成済みデータを一時保存
# 色の選択中には再作成せず、この変数内のデータを再出力する。
effectCodeViewData=''

# カラーレベルデータを擬似配列化
# colorLevelRGBarr_[色番号]_[0:RR,1:GG,2:BB]
matrixToArrFunc "`seq 0 255 | ansi256_numToRGBsh`" colorLevelRGBarr
# colorLevelHSLarr_[色番号]_[0:HHSL,1:HSSL,1:HSLL]
matrixToArrFunc "`seq 0 255 | ansi256_numToRGBsh | rgbToHSLawk1sh 0 0 2>/dev/null`" colorLevelHSLarr
# colorLevelHSVarr_[色番号]_[0:HHSV,1:HSSV,2:HSVV]
matrixToArrFunc "`seq 0 255 | ansi256_numToRGBsh | rgbToHSVawk1sh 0 0 2>/dev/null`" colorLevelHSVarr

# 初回リセット処理を実行
resetFlag='true'

# ======================================================================================
# メインループ
# ======================================================================================

while true ; do


if "${resetFlag}"
then resetFunc
fi

# X座標の倍率データを元データで作成した擬似配列から読み込む
eval 'mainFgMag="${colorTableMagsArr_'${MAIN_FG_Y:?}'_0}"'
eval 'mainBgMag="${colorTableMagsArr_'${MAIN_BG_Y}'_0}"'
eval 'subFgMag="${colorTableMagsArr_'${SUB_FG_Y}'_0}"'
eval 'subBgMag="${colorTableMagsArr_'${SUB_BG_Y}'_0}"'
# 選択中の色番号を元データから作成した疑似配列から読み込む
eval 'mainFgNo="${colorTableArr_'${MAIN_FG_Y}'_'$(( ${MAIN_FG_X} / ${mainFgMag:?} ))'}"'
eval 'mainBgNo="${colorTableArr_'${MAIN_BG_Y}'_'$(( ${MAIN_BG_X} / ${mainBgMag} ))'}"'
eval 'subFgNo="${colorTableArr_'${SUB_FG_Y}'_'$(( ${SUB_FG_X} / ${subFgMag} ))'}"'
eval 'subBgNo="${colorTableArr_'${SUB_BG_Y}'_'$(( ${SUB_BG_X} / ${subBgMag} ))'}"'

# カラーレベルを疑似配列から読み込む
eval 'mainFgRR=${colorLevelRGBarr_'${mainFgNo}'_0}'
eval 'mainFgGG=${colorLevelRGBarr_'${mainFgNo}'_1}'
eval 'mainFgBB=${colorLevelRGBarr_'${mainFgNo}'_2}'
eval 'mainFgHHSL=${colorLevelHSLarr_'${mainFgNo}'_0}'
eval 'mainFgHSSL=${colorLevelHSLarr_'${mainFgNo}'_1}'
eval 'mainFgHSLL=${colorLevelHSLarr_'${mainFgNo}'_2}'
eval 'mainFgHHSV=${colorLevelHSVarr_'${mainFgNo}'_0}'
eval 'mainFgHSSV=${colorLevelHSVarr_'${mainFgNo}'_1}'
eval 'mainFgHSVV=${colorLevelHSVarr_'${mainFgNo}'_2}'

eval 'mainBgRR=${colorLevelRGBarr_'${mainBgNo}'_0}'
eval 'mainBgGG=${colorLevelRGBarr_'${mainBgNo}'_1}'
eval 'mainBgBB=${colorLevelRGBarr_'${mainBgNo}'_2}'
eval 'mainBgHHSL=${colorLevelHSLarr_'${mainBgNo}'_0}'
eval 'mainBgHSSL=${colorLevelHSLarr_'${mainBgNo}'_1}'
eval 'mainBgHSLL=${colorLevelHSLarr_'${mainBgNo}'_2}'
eval 'mainBgHHSV=${colorLevelHSVarr_'${mainBgNo}'_0}'
eval 'mainBgHSSV=${colorLevelHSVarr_'${mainBgNo}'_1}'
eval 'mainBgHSVV=${colorLevelHSVarr_'${mainBgNo}'_2}'


# 文字装飾チェックにフォーカスが当たっているとき再作成(高速化目的)
if test ${focusID} -eq 2 || test -z "${effectCodeViewData}" ; then
effectCodeViewData=`effectCodeCheckSh $(( ${effectCodeFocusY} * 6 + ${effectCodeFocusX} )) \
 "${effectCodeFlags}" `
else
	true
fi


{ # overWriteSh
printf "\033[${EFFECT_CODE}m"'\033[39;49m%s\033[0m %6s %s\n'\
"\033[${EFFECT_CODE}m""\033[38;5;${mainFgNo};48;5;${mainBgNo}m%s\033[0m %6s %s\n"\
"\033[${EFFECT_CODE}m""\033[38;5;${subFgNo};48;5;${subBgNo}m%s\033[0m %6s %s\n"\
"\033[${EFFECT_CODE}m"'\033[38;5;'"${mainFgNo};48;5;${mainBgNo}m%s\033[0m\n"\
"\033[${EFFECT_CODE}m"'\033[38;5;'"${subFgNo};48;5;${subBgNo}m%s\033[0m\n"\
	"${STD_SAMPLE}" '39;49' "${EFFECT_CODE}" \
	"${MAIN_SAMPLE}" "${mainFgNo};${mainBgNo}" "${EFFECT_CODE}" \
	"${SUB_SAMPLE}" "${subFgNo};${subBgNo}"  "${EFFECT_CODE}" \
	"${FREE_SAMPLE:-        }" \
	"${FREE_SAMPLE:-        }"

echo 'FOCUS_ID_0'
printf "\033[48;5;${mainFgNo}m%30s\033[0m"" %3s,%3s,%3s L(%3s,%3s,%3s) V(%3s,%3s,%3s)\n" ' ' \
 ${mainFgRR} ${mainFgGG} ${mainFgBB}  ${mainFgHHSL} ${mainFgHSSL} ${mainFgHSLL} \
 ${mainFgHHSV} ${mainFgHSSV} ${mainFgHSVV}

echo 'FOCUS_ID_1'
printf "\033[48;5;${mainBgNo}m%30s\033[0m"" %3s,%3s,%3s L(%3s,%3s,%3s) V(%3s,%3s,%3s)\n" ' ' \
 ${mainBgRR} ${mainBgGG} ${mainBgBB}  ${mainBgHHSL} ${mainBgHSSL} ${mainBgHSLL} \
 ${mainBgHHSV} ${mainBgHSSV} ${mainBgHSVV}

# 作成済みのカラーパレット画像データにカーソルを乗せて表示
echo "${colorTableSepImg}" 

echo 'FOCUS_ID_2'
echo "${effectCodeViewData}"

helpMessageC256sh

} | sepDrawFocusOvewWrite1sh ${mainFgNo} ${mainBgNo} ${focusID} 1>&2

#debug1Sub # 【debug】
#debug2Sub # 【debug】
#debug3Sub # 【debug】
#debug4Sub # 【debug】
#debug5Sub # 【debug】



PRESS_KEY=`pressKeyScan256sh ${focusID}`
keyActionFunc_${PRESS_KEY}


done


exit 255

#