- 1. Openbox
- 2. ソース
1. Openbox
これは、「Openbox」の処理を行うモジュールです。
「Openbox」のメニューの構造は
<menu id="2" label="カテゴリ名" icon="アイコンファイル名">
<item label="アイテム名" icon="アイコンファイル名"> <action name="Execute">
<execute>ロードモジュール</execute>
</action> </item>
<item label="アイテム名" icon="アイコンファイル名"> <action name="Execute">
<execute>ロードモジュール</execute>
</action> </item>
</menu>
という形式になっています。
サブカテゴリを分ける場合は、「menu」タグをネストさせます。
「アイコンファイル名」は、オリジナルの「MenuMaker」では、「menu」「item」どちらの行も「icon=""」自体が存在しません。
「.png」も「.svg」も表示できるので、変換がないため、短いソースになります。
2. ソース
ソースは、以下になります。
##
# @file Openbox.py
# @version 0.1
# @author 作成:show.kit
# @date 作成:2020年6月9日
# @brief Openbox の環境変数設定ファイル
import os
import re
from test.test_decimal import directory
##
# @class Openbox
# @brief Openbox の環境変数設定
class Openbox:
## Openbox::__init__
# @brief 初期化関数
# @return 戻り値なし
def __init__(self):
## デスクトップ名
self.frontend = 'Openbox'
## メニューファイル名
self.filename = os.environ.get('HOME') + '/.config/openbox/menu.xml'
## 項目名の先頭括弧
self.prefix = "label=\""
## 項目名の括弧閉じ
self.suffix = "\""
## メニューのプログラム行検出キーワード(Openbox は特別)
self.exec_keyword = 'name="Execute"'
##
# メニューのカテゴリ行を日本語に変える
# @param env 環境クラス(Openbox では未使用)
# @param line 対象行
# @param label_en カテゴリ名英語
# @param label_jp カテゴリ名日本語
# @param directory_icon カテゴリアイコンのディレクトリ
# @param icon アイコンファイル(拡張子なし)
def update_category(self, env, line, label_en, label_jp, directory_icon, icon):
## カテゴリ名を英語から日本語へ
line = line.replace(self.prefix + label_en + self.suffix, self.prefix + label_jp + self.suffix)
## icon 追加
line = line.replace('">', '" icon="'+ directory_icon + '/' + icon +'.svg">')
return line
#####
# 終了メニュー設定
# @param env 環境変数クラス
# @param lines メニューファイル全行
def set_end_menu(self, env, lines):
## 終了メニュー用アイコン
## 再起動 [1]ログアウト(終了) [2]シャットダウン
icon_exit = env.directory_icon_category + '/computer-log-out.svg' ## 終了(ログアウト)
icon_restart = env.directory_icon_category + '/system-restart.svg' ## 再起動
icon_stop = env.directory_icon_category + '/system-shutdown.svg' ## 停止(シャットダウン)
lines.insert(-2, ' <separator/>'+"\n")
lines.insert(-2, ' <menu id="50" label="終了" icon="'+icon_exit+'">'+"\n")
lines.insert(-2, ' <item label="ログアウト" icon="'+icon_exit+'"> <action name="Exit"/> </item>'+"\n")
lines.insert(-2, ' <item label="再起動" icon="'+icon_restart+'"> <action name="Execute">'+"\n")
lines.insert(-2, ' <execute>sudo /sbin/reboot</execute>'+"\n")
lines.insert(-2, ' </action> </item>'+"\n")
lines.insert(-2, ' <item label="シャットダウン" icon="'+icon_stop+'"> <action name="Execute">'+"\n")
lines.insert(-2, ' <execute>sudo /sbin/poweroff</execute>'+"\n")
lines.insert(-2, ' </action> </item>'+"\n")
lines.insert(-2, ' </menu>'+"\n")
#####
# @brief applications/*.desktop を検索して
# プログラム名 → アイコンファイル名の辞書を返す
# Fluxbox と違って png で良い
# @param env 環境変数クラス
# @param dic_exec_icon .desktop より取得した編集前の exec → icon 辞書
# @return exec → icon ファイル名フルパス の辞書
def get_dic_exec_icon(self, env, dic_exec_icon):
## 有効な拡張子、ディレクトリ(どちらも優先順位順)
effect_extend = [ '.xpm', '.png', '.svg' ]
effect_directory = [ env.directory_xpm, env.directory_png, env.directory_icon_apps ]
## exe → icon 辞書の妥当性をチェック
## 妥当でなければ変更
for key, value in dic_exec_icon.items(): ## exec → icon 辞書作成
if (os.path.exists(value)): ## icon が存在する
continue ## 終了
elif(not '.' in value): ## icon が存在しない . を含まない
for extend in effect_extend: ## 拡張子として有効なものを検索
for directory in effect_directory:
icon = directory + '/' + value + extend ## icon ファイル名組み立て
if (os.path.exists(icon)): ## 存在する
dic_exec_icon[key] = icon ## icon として設定する
break ## break
else:
continue
break
else: ## . を含む
for directory in effect_directory: ## 有効なディレクトリ順に検索
icon = directory + "/" + value
if (os.path.exists(icon)): ## フルパス/ファイル名 が存在する
dirname, name, extend = env.mysplit(icon) ## フルパスを分解
for ef_extend in effect_extend: ## 拡張子として有効なものを検索
if (ef_extend == extend): ## 有効なものであれば
dic_exec_icon[key] = icon ## icon として設定する
break ##
else:
continue
break
return dic_exec_icon;
##
# @brief icon をメニューに設定する
# @param line メニューの対象行
# @param nextline 対象行の次の行(Openbox でのみ使用
# @param dic_exec_icon exec → icon 辞書
# @return line 更新した行
def set_menu_icon(self, line, nextline, dic_exec_icon):
## 次の行の > と < に挟まれた部分を取り出す(ロードモジュールの記述)
match = re.search(r"\>.*\<", nextline)
if (' ' in match.group()): ## スペースがあれば
exename = match.group().split(' ')[0] ## 先頭の文字列のみ抽出し
exename = exename[1:] ## プログラム名のみとする
else:
exename = match.group()[1:-1]
if (exename in dic_exec_icon): ## exec → icon 辞書に exe が存在するならば
## icon 設定
line = line.replace('"> <', '" icon="'+dic_exec_icon[exename]+'"> <')
return line ## 更新がない場合そのまま返す
|