飴屋ぷろじぇくと

Date : 2014年10月

--.--.--[--] スポンサーサイト

上記の広告は1ヶ月以上更新のないブログに表示されています。
新しい記事を書く事で広告が消せます。

2014.10.30[木] WindowsリソースからFreeBASIC+GTK(その3)


UTAUを作った動機を知れば自ずと判ることなんですが、飴屋はこんな風に手間かけて手間を減らすツールを作るのが好きなんです。

というわけで、今回は画像関係の話題。

gtk-app-dlg.png

こんな画面をサンプルに載せましたが、このイメージ、実は問題がありまして、これって、実行時に画像を読み込んでいるんです。具体的にはGdkPixbufに読み込んでいます。
bitmap1 = gdk_pixbuf_new_from_file("./apple.bmp", NULL)
これを以下のようにしてGtkImageにして表示してます。
image1 = gtk_image_new_from_pixbuf(butmap1)
まあこれはこれで良いんですが、実行時に結合となると後々厄介かもしれないので本来のリソースのように実行ファイルに埋め込めないものかとやってみました。

まずソースにバイナリデータを記述するのですが、FreeBasicではこんな表記が出来るようです。
Dim pixdata As String = !"\212\234\127\128\129\065\066"
そしてデータはやたら長いので行継続記号"_"を使って、
Dim pixdata As String = _
!"\212\234\127\128\129\065\066\128\129\065\066\128\129\065\066" _
!"\234\127\128\129\065\212\173\129\065\128\066\128\129\154\170" _
!"\252\234\227\128\129\065\226\065\128\129\066\066\128\129\165"
こんな風に書きます。
変換プログラム内で画像ファイルをこのようなソースに変換するわけですが、折角なのでこちらでの画像の読み込みもGTKを使用しました。実装はこんな関数。
/*
 * 画像リソースをソースコードに変換する
 */

void pixToText(CodeData *cds, const char *filename, const char *pname) {
    string text;
    char fname[256];
    strcpy(fname, filename);
    fname[0] = ' ';
    char *p = strchr(fname, '"');
    if (p) *p = 0;
    strltrim(fname);
    GdkPixbuf *pixbuf = gdk_pixbuf_new_from_file(fname, NULL);
    int n_channels = gdk_pixbuf_get_n_channels(pixbuf);
    gboolean has_alpha = gdk_pixbuf_get_has_alpha(pixbuf);
    guchar *pix = gdk_pixbuf_get_pixels(pixbuf);
    int rowstride = gdk_pixbuf_get_rowstride(pixbuf);
    int bpsamp = gdk_pixbuf_get_bits_per_sample(pixbuf);
    int w = gdk_pixbuf_get_width(pixbuf);
    int h = gdk_pixbuf_get_height(pixbuf);
    int len = rowstride * h;
    sprintf(buf, "Const %s_n_channels As Integer = %d\n", pname, n_channels);
    text += buf;
    sprintf(buf, "Const %s_has_alpha As Integer = %d\n", pname, has_alpha);
    text += buf;
    sprintf(buf, "Const %s_bits_per_sample As Integer = %d\n", pname, bpsamp);
    text += buf;
    sprintf(buf, "Const %s_width As Integer = %d\n", pname, w);
    text += buf;
    sprintf(buf, "Const %s_height As Integer = %d\n", pname, h);
    text += buf;
    sprintf(buf, "Const %s_rowstride As Integer = %d\n", pname, rowstride);
    text += buf;
    sprintf(buf, "Const %s_pixcels As String = _\n!\"", pname);
    text += buf;
    for (int i = 0; i < len; i++) {
        sprintf(buf, "\\%03u", pix[i]);
        if (i > 0 && i % 25 == 0) {
            text += "\" _\n!\"";
        }
        text += buf;
    }
    text += "\"\n";
    
    sprintf(buf, "%s.bi", pname);
    FILE *fb = fopen(buf, "wt");
    fprintf(fb, "%s", text.c_str());
    fclose(fb);

    sprintf(buf, "#include \"%s.bi\"\n", pname);
    cds->incs += buf;
}

ソースに埋め込むコードは画像のバイナリデータをAscii表現しているので無駄に長くなります。なので出力ファイルを分割して画像のコードはインクルードファイルに格納しています。もちろん #include は自動で挿入されます。
スポンサーサイト

Copyright © 飴屋/菖蒲

上記広告は1ヶ月以上更新のないブログに表示されています。新しい記事を書くことで広告を消せます。