Linux」カテゴリーアーカイブ

Get MIME Type

ファイル情報取得で MIME Type を取得したい。
mimetypes モジュールでは拡張子判別しかできないみたいですけど。
Nautilus は拡張子が優先だけど無くても取得できているじゃないか。
ということで地味に方法を探してみる。

ファイルの MIME タイプの検出 (GNOME 2.2 システム管理 (Linux 版)) – Sun Microsystems

/etc/gnome-vfs-mime-magic
/etc/mime.types

のファイルが元ということになっているみたいなんだが Ubuntu では

ubuntuで対応しているMIME Typeを調べるには:Linux つれづれ日記:So-net blog

/usr/share/mime 以下なのか。
xdg-mime は MIME Types のインストール関連に使うものだがどっちに登録するのかな?

つーか Nautilus が取得できているんだから絶対にシェルから取得できるはずだ。
色々調べていたらこんなのを見つけた。

Nautilus File Manager Scripts: File Information Querying Scripts

file コマンドだけでこんなことができるのか。

$ file --help

で調べると –mime-type オプションがあるらしい、それならこうしてみよう。

#!/usr/bin/env python
#-*- coding:utf-8 -*-

import gtk
import urllib
import os.path
import commands

class MimeWin(gtk.Window):
    """
        Showing MIME Type of Dropped file
    """
    def __init__(self):
        gtk.Window.__init__(self)
        dnd_list = [("text/uri-list", 0, 0)]
        self.drag_dest_set( gtk.DEST_DEFAULT_MOTION |
                            gtk.DEST_DEFAULT_HIGHLIGHT |
                            gtk.DEST_DEFAULT_DROP,
                            dnd_list, gtk.gdk.ACTION_MOVE )
        self.connect("drag_data_received", self.on_drop)
        self.label = gtk.Label("Drop")
        self.add(self.label)
        self.connect("delete-event", gtk.main_quit)
        self.resize(320, 150)
        self.show_all()

    def on_drop(self, widget, context, x, y, selection_data, info, time):
        drops = selection_data.data.split("\n")
        for drop in drops:
            name = urllib.unquote(drop)[7:-1]
            if os.path.isfile(name):
                # Get MIME Type
                mime = commands.getoutput("file --mime-type %s" % name)
                self.label.set_text(mime)

if __name__ == "__main__":
    w = MimeWin()
    gtk.main()

ext_non

おお、しっかり取得してくれているじゃないか。
しかし Python Script では

ext_py

text/x-java …
text/x-python のはずなのに、ダメだこりゃ。

mime = mimetypes.guess_type(name)[0]
if mime:
    self.label.set_text(mime)
else:
    self.label.set_text("Non Extension")

ならキチンと text/x-python になる、しかし拡張子が無いなら None になる。
んーどっちも使えない、もうちょっと調べます。

Enjoy!

create_small_image Nautilus-Script

次の覚書は GtkUIManager を利用してツールバーに独自画像を。
とやりたかったけどストック以外を指定する方法が無いみたい。
一旦個別に抜きだしして割り当てるならできそうだけどどうしよう。

ところで

gtk.gdk.Pixbuf

GDK-PixBuf には save というメソッドがあるんだね。
これは…上手く使えそう。

たとえば blog に使う大きな画像へのリンク用の小さな画像作りなんかに。
これを Nautilus スクリプトにしてしまえばそのためだけに Gimp を利用する手間が省ける。
ということで試しに書いてみる。
生成する画像の名前は WordPress が付ける名前に合わせサイズを付加する例。

#!/usr/bin/env python
#-*- coding:utf-8 -*-

"""
    create_small_image Nautilus-Script
    written in Python.
"""

import gtk
import os

path_array = os.environ["NAUTILUS_SCRIPT_SELECTED_FILE_PATHS"].split("\n")
for picfile in path_array:
    try:
        pixbuf = gtk.gdk.pixbuf_new_from_file(picfile)
    except:
        continue
    # Under 300*300 image
    d_width = 300
    d_height = 300
    # GdkPixbuf size
    p_width = pixbuf.get_width()
    p_height = pixbuf.get_height()
    # Calculated to fit the smaller
    width = 0
    height = 0
    if (d_width * p_height) > (d_height * p_width):
        width = p_width * d_height / p_height
        height = d_height
    else:
        width = d_width
        height = p_height * d_width / p_width
    # Create Resizeing GtkPixbuf
    small_image = pixbuf.scale_simple(width, height, gtk.gdk.INTERP_BILINEAR)
    # Create small_image Name
    pos = picfile.rindex(".")
    image_name = "%s-%dx%d.png" % (picfile[:pos], width, height)
    small_image.save(image_name, "png")

で、Nautilus script に登録する。
Nautilus で画像を選択状態にして右クリックメニューからスクリプトを選択。

sclipt_menu

で、画像があるディレクトリに縮小された画像が生成されているはず。
てかおいおい、こんな簡単にスモール画像が作れちゃったよ。
今まで書いたスクリプトを組み合わせただけなので製作時間 15 分。

さてコレを覚書ページに…どこに入れればいいのだ?
よく解らないから blog に書いてみた。

追記

また script を sclipt と書いていた…ので書き換えておます。

Enjoy!

Python is doing in Linux

ぱぇぽぃ2 ? Blog Archive ? ラジオメニューとトグルボタンの同期

をもう少しまともに解説、やはり実際に使えるコードでないと動作を実感しないだろうから。

GtkRadioAction でラヂオメニューとツールバーを同期させる

しかし GtkRadioActionEntry の value 引数に直接値を入れたのは我ながらナイス。
ついでにココも大幅に追記、これも以前 Blog のほうで書いたコードだったりする。

テキストや図形を描写する

思いつきを Blog でやって覚書ページにまとめると決めていたがサボってばかりだ。
しかし自分で書いたコードを探すのに自分の Blog を検索するのって何か変な気分。

しばらく IronPython ばかりやっていたのですがやはり Linux で PyGtk のほうが面白いです。
なんたってすぐに起動できる、簡単に書けるようにバインディングされている、端末操作も楽。
なにより、メソッドの先頭が大文字という違和感が PyGtk には無いのが一番嬉しい。
.NET Framework はクラス名なのかメソッドなのかプロパティなのか解りにくい。

というか… .NET Framework は単純なものを作る場合は短いコードで住ませられるんだけど。
少し凝ったことをしようとすると嫌がらせとしか思えないほど面倒になってタマラン。
.NET Framework とは仮想マシンであり Windows では無いのが少し解ってきた今日この頃。
要求する新たな知識がハンパないので新参プログラマーはカワイソウ。

Devhelp を見て
「ならば PyGtk ではこう書けばイケるだろう」
が通用する PyGtk って楽だなぁと感じた今日この頃。
SDK Help はこう作って欲しいです、MSDN 様。

Enjoy!

グラフィックコンテキストの色はもっと簡単に変更できた

グラフィックコンテキストの色はもっと簡単に変更できた

set_rgb_fg_color(gtk.gdk.color_parse("red"))

で expose-event の中でも CPU 負荷もなくアッサリ変更できる。
GTK+ はデフォルトがダブルバッファリングなのでチラツキも全然無い。
チビッと試しに書いてみた。

#!/usr/bin/env python
#-*- coding:utf-8 -*-

import gtk
import pango

ui_str = """<ui>
    <menubar name="MenuBar">
        <menu action="File">
            <menuitem action="quit"/>
        </menu>
    </menubar>
</ui>"""

class GC_Test(gtk.Window):
    """
        GC で色々な表示を試してみる
        Font を変更するには pango を使う必要があるのね
    """
    def __init__(self):
        # お約束
        gtk.Window.__init__(self)
        # GtkUIManager 作成
        uimanager = gtk.UIManager()
        # GtkAccelGroup を取り出し self にて突っ込む
        accelgroup = uimanager.get_accel_group()
        self.add_accel_group(accelgroup)
        # GtkActionGroup 作成
        actiongroup = gtk.ActionGroup("nandemoii")
        # GtkActionEntry の list を作成して GtkUIManager に突っ込む
        e = [("quit", gtk.STOCK_QUIT, "終了(_Q)", "<Control>Q", "さいなら", self.on_quit),
            ("File", None, "ファイル(_F)") ]
        actiongroup.add_actions(e)
        # GtkUIManager の更新
        uimanager.insert_action_group(actiongroup, 0)
        uimanager.add_ui_from_string(ui_str)
        # メニューを取り出す
        menubar = uimanager.get_widget("/MenuBar")
        # パッキング
        statusbar = gtk.Statusbar()
        drawingarea = gtk.DrawingArea()
        #
        # ダブルバッファリング無効状態にしたいならココを有効にしてね
        #drawingarea.unset_flags(gtk.DOUBLE_BUFFERED)
        #
        # WM_PAINT のようなものを発生させる
        drawingarea.connect("expose-event", self.on_drawingarea_expose)
        # パッキング
        vbox = gtk.VBox()
        vbox.pack_start(menubar, False)
        vbox.pack_start(drawingarea)
        vbox.pack_end(statusbar, False)
        self.add(vbox)
        # いつもの処理
        self.set_title("gc_test")
        self.connect("delete-event", self.on_quit)
        self.resize(320,240)
        self.show_all()

    def on_quit(self, widget, event=None):
        gtk.main_quit()

    def on_drawingarea_expose(self, widget, event=None):
        # グラフィック・コンテキストを得る
        gc = widget.style.fg_gc[gtk.STATE_NORMAL]
        # 赤くする
        gc.set_rgb_fg_color(gtk.gdk.color_parse("red"))
        # 自分のサイズ取得
        d_width = widget.allocation.width
        d_height = widget.allocation.height
        # 塗りつぶす
        widget.window.draw_rectangle(gc, True, 0, 0, d_width, d_height)
        # 緑色にする
        gc.set_rgb_fg_color(gtk.gdk.color_parse("green"))
        # Font を大きくして文字列描写
        font_desc = pango.FontDescription('Monospace 32')
        layout = widget.create_pango_layout ("まっかっか")
        layout.set_font_description(font_desc)
        widget.window.draw_layout(gc, 10, 20, layout)
        # 青色にする
        gc.set_rgb_fg_color(gtk.gdk.color_parse("blue"))
        # 線
        widget.window.draw_line(gc, 0, 0, d_width, d_height)

if __name__ == "__main__":
    w = GC_Test()
    gtk.main()

makkakka

これでどこをどう書けばどういう表示になるか簡単に解る…と思う。
2D にしてグリグリウインドウサイズを変更するとチラツキが無いのも理解できる。
ダブルバッファリングを無効にする方法もついでに。

PyGtk って何でもやれて面白いですよ。

keywords

今月も mono が多い…そんなに Linux で C# なんかやりたいの?
キッカケだけならそれでいいけど、私がそうだったし。

テンプレートとスクリプト

nanikore

Nautilus にあるこのテンプレートって何だろうと気になった。
多分よく使うテンプレートをコピーして新規作成してくれる機能だと思う。
私だったら当然

#!/usr/bin/env python
#-*- coding:utf-8 -*-

とかかな、「 py 」って打って Tab キーを押すだけでスニペットが挿入してくれるけど。
それでもあったほうが便利かなと思うので使い方を探す、が見つからないんですけど。
せっかく堂々とメニューに乗っているのに誰も使っていないのかな?

でも調べているうちにスクリプトで Nautilus が拡張できると知った(今頃…
面白そうと思って早速作ってみた、これで端末のお世話になる時間が減りそうだ。

Nautilus をスクリプトで拡張

しかし gedit といい Nautilus といい gimp といい Eye of GNOME といい…
Opera と自作以外は標準アプリしか使っていないのを思い知る。

しかし他のモンをあんまりインストールしていないので私の 9.04 は超安定しています。