C#でmp3ファイルを再生する


 

C#でmp3再生がようやく出来ました。

P/InvokeでmciSendCommandを使用します。

大筋は,Creating a Sound Recorder in C and C# でOKです。

自分がハマった点は,

mciSendCommandの第4パラメータ(下記のparam)は,

public static extern uint mciSendCommandW(uint deviceId, uint command, UIntPtr flags, IntPtr param);

と,IntPtr型で定義し,Marshal.StructureToPtrで設定している点と,

    [STAThread]
    public static void Main()

と Single Thread Apartment にしなければならない点でした。STAにしないと,MCIERR_CANNOT_LOAD_DRIVER(266)というエラーが返ります。

フォームを使うとSTAになるらしいのですが,まだ試作でコマンドラインレベルのため,STAになっていないようでした。

検索すると,外国の方がたいへん悩んだ様子があり,未解決のままになっているのですが,STAにするといいですよ。

STAの件は,以前にC++/CLIでMP3再生した時にも同じハマリになったのですが,すっかり忘れていました。

カテゴリー: 技術メモ | コメントをどうぞ

Lhazのリリース方法


Lhazのリリース方法です。v2系を例にしています。

lhaz\Releaseフォルダ配下の,上図で選択状態になっているファイルを,「送る」で「デバッグ版のLhaz.exe」に送ります。あるいは,デバッグ版のLhaz.exeにドラッグ&ドロップしてください。32ビット版は,32ビットデバッグ版,64ビット版は,64ビットデバッグ版で圧縮します。圧縮形式は,「SFX(CAB)圧縮」を選びます。自己解凍書庫の設定は,以下のようにします。

「ショートカット名」を空欄にする点に注意してください。

v3系は以下のファイルになります。

 

カテゴリー: Lhaz | コメントをどうぞ

Google Documents List API コレクション編


Googleドキュメントの任意のコレクション配下にファイルをアップロードすべく,少々苦闘してしまいました。

まず,コレクションやサブコレクションの作成は,Google Documents List API のサンプル通りでうまくいきました。

次に,任意のコレクションへのファイルのアップロードなのですが,なかなかうまくいきませんでした。

ResumableUploader の完了イベントに渡ってくる引数の AsyncOperationCompletedEventArgs e には,下記のようにメンバーとして DocumentEntry があります。

    static void OnDone(object sender, AsyncOperationCompletedEventArgs e) {
        DocumentEntry entry = e.Entry as DocumentEntry;
    }

Adding a resource to a collection に従って,アップロード完了したファイルの  entry->Id を使用して,DocumentService->Insert でコレクションに移動しようとしましたが,全然うまくいきません。

「デリゲートのコンテキストではAPI呼べないのかな?」とか,「DocumentsRequest->Insertで出来ないかな?」とか,「そもそも ResumableUploader でアップロード先コレクションを指定できないのかな?」とあれこれ試しても,うまくいきません。

そのうち,デバッガで entry の中身を見てみると,ほぼ空っぽなことに気づきました。ごく一部のメンバーしか値が入っていないようなのです。なぜ?

そこで,一覧を取得しなおして,アップロードしたファイル名と比較して,一致した場合はコレクションに移動する,という処理を作成しました。

一応動作していますが,美しくないです。

4/22 追記

ファイル名で比較では,同一ファイル名が存在しうるので,その既存のファイルもコレクションに移動してしまうことに気がつきました。全然だめです。

よくよく検索したところ, Googleグループに回答そのものがありました。

手元のコードでは,以下のようにUploadUrlを指定することで,任意のコレクション配下にファイルをアップロードできるようになりました。

            String^ s = gcnew String("https://docs.google.com/feeds/upload/create-session/default/private/full/" + parent->DocumentEntry->ResourceId + "/contents?conver=false");

 

カテゴリー: 技術メモ | コメントをどうぞ

ListView_EditLabelでキーが効かない


Win32API ListView_EditLabelマクロでリストビューのアイテムの編集を始められるのですが,ENTERキーやBSキーが効きません。ENTERキーが効かないので,マウスで他のエリアをクリックして編集を確定させなければなりませんでした。これでは使いづらいので,原因を調べました。

ダイアログの上にリストビューコントロールを作成していると,キーがダイアログの方で処理される,という現象があり,サブクラス化で回避できる,という情報がありました。しかし,Lhazではダイアログアプリではないので,これには該当しません。

引き続き調べていくと,TranslateAccelerator() がアクセラレータに登録されているキーをWM_COMMANDに変換している,ということを思い出しました。確かに,ENTERキーは個別ファイルを開きますし,BSキーは上位フォルダに移動します。

どうも簡単に回避する仕組みはないようなので,フラグ変数を設けて,ListView_EditLabel~LVN_ENDLABELEDITの間は,TranslateAccelerator()を呼び出さない,というダサイ解決法に落ち着きました。

カテゴリー: Lhaz, 技術メモ | コメントをどうぞ

OpenGrok index が cron で動かない


OpenGrokのindex更新を午前2時に行うよう,crontabに設定にしたのですが,全く動かないので悩んでいました。数分後に実行されるよう変更して, /var/log/syslog を見ると, grandchild #6356 failed with exit status 2 とエラーが出ていました。エラー出力をファイルに出させると, ”Unable to determine Exuberant CTags command name for…” とのことで, ctags が見つからないようです。ここまで来て, PATH の問題だと分かりました。 crontab -e で PATH を通して,無事に自動更新されるようになりました。

 

カテゴリー: 技術メモ | コメントをどうぞ

ベクターの個人情報が消せない件


ベクターで個人情報流出の危険が発生したとのことで,フォームから下記のように依頼しました。

>作者登録(個人情報)を抹消して頂きたくお願いいたします。

返答は以下の通りで,完全な削除はできないとのことでした。

(株)ベクターです。
弊社サービスをご利用いただき、ありがとうございます。

ご登録いただいておりました作品は全て公開を終了させていただきます。
(サイト上に反映されますのは、次回のサイト更新時となります)

おそれいりますが、弊社システムの仕様上、作者登録の完全な削除
につきましては行うことができません。

作品が公開されていない状態では、サイト上に情報が掲載されることは
ございません。また、弊社から連絡を差し上げることもございませんの
で、あしからずご了承いただければと存じます。

では住所や名前をダミーデータに更新するかとログインを試みましたが,既にログインできなくなっていました。何が消えて何が消えてないのか分かりませんので,アカウントの復活を依頼しました所です。

4/4追記

ようやくベクターより返信があり,住所電話番号その他を空欄にしてもらえました。残念ながら氏名は削除できないとのことですが,納得することにしました。

カテゴリー: 未分類 | 2件のコメント

Google Documents List Data API 共有編


Googleドキュメント上のファイルの共有は,以下のように行います。

本当は「リンクを知っている全員」への共有を行いたかったのですが,あれこれ設定を変えて試しても,「ウェブ上で一般公開」の共有にしかできませんでした。

    GDataCredentials^ c = gcnew GDataCredentials(email, password);
    RequestSettings^ r = gcnew RequestSettings(appname, c);
    DocumentsRequest^ dr = gcnew DocumentsRequest(r);
    Document^ doc = SortTable[sel]->GetDoc();
    DocumentEntry^ entry = doc->DocumentEntry;
    AclQuery^ query = gcnew AclQuery(entry->AccessControlList);
    AclFeed^ aclFeed = dr->Service->Query(query);
    AclEntry^ aclentry = gcnew AclEntry();
    aclentry->Role = gcnew AclRole("reader");
    AclScope^ scope = gcnew AclScope();
    scope->Type = AclScope::SCOPE_DEFAULT;
    scope->Value = "";
    aclentry->Scope = scope;
    aclFeed->Insert(aclentry);
    dr->Service->Query(query);
カテゴリー: 技術メモ | コメントをどうぞ

Gerritを約1年運用してみて


Gerritを利用して拙作のLhazをオープンソース化してから,1年が過ぎようとしています。ここで,Gerritの良い点,悪い点をまとめます。GitHubやSourceForgeを使用した経験はないので,他の開発プラットフォームと比較した結果ではありません。運用中のレビューサイトはこちらになります。

良い点

gitが身についた

Gerritはgitベースですので,gitの使い方が身につきました。add, commitなどの基本的なコマンドはgitのみの運用でも身につくかと思いますが,Gerritではpushやコンフリクトの解決にrebaseが必要だったりして,やや進んだ使い方が身につきます。また,Lhazの開発では,zlib等の外部ライブラリを使用しており,mergeも使ったりしました。

ブランチがGerrit上で可視化されるのも良いと思います。具体的には,zlib等をmasterブランチ,lhazブランチと分けて,開発元の更新はmaster,自分で手を加えた部分はlhaz,でトラッキングしていますが,このような感じで流れが分かります。

コラボレーション

Gerritでは複数人で開発を進めていきますが,コードレビューしたりされたりで,人の書いたコードをじっくり見ることができ,たいへん参考になります。2ペインで左に更新前,右に更新後,と差分が見やすいのも気に入っています。自分のレビュースタイルは,動いてるならいいんじゃない?,といったあっさりしたものですが,1ライン単位でレビューコメントを記載できるので,ネチネチ派?の方も使い出があるのではと思います。

Lhaz開発メンバーから文字列クラスのリノベーションをご提案頂き,1プロジェクトとしてインテグレートさせて頂いたのですが,自分には馴染みの少ないテンプレートが駆使されているC++らしいコードで,とても勉強になりました。

仕事(Androidスマートフォン開発)でもGerritを使用していますが,コミットのアップロードやマージがあった際にメールで通知を受けることができるので,相当広い範囲に目を配ることができます。

モチベーション

Gerritにpushして,レビューして,+1 Verified,+2 Looks good to me, approved,のスコアがついた後,「Submit Patch Set」というボタンを押して,変更がブランチにマージされます。この瞬間,小さな達成感があり,気持ちよいです。早く次の変更を入れたくなるので,開発が継続していきます。

そして,過去のコミットを振り返ると,開発の歴史そのものですので,「よくがんばったな」「続けていこう」という気になれます。この辺りは特にGerrit固有ということはないですが。

悪い点

とっつきにくい?

こちらのWikiにてLhazの開発参加方法を説明していますが,自分で見ても始めるのが面倒くさそうです(実際はそうでもないと思いますが…)。Lhazでこれまでコミット頂けたのもまだ4名の方で,あまり気軽にトライできないのかな,と思われます。

また,GitHubのように自分で試せる公開Gerritサーバといったものはないので,自分でサーバを用意してGerritをインストールしていくのも,ひと手間いります。 review.chitora.com でホスティングすることも可能ですので,使ってみたい方はご連絡ください。

 コードレビュー専用

Gerritは純粋なコードレビューツールですので,設計に使用することは難しいです(全てテキストファイルで設計すれば可能かもしれませんが)。また,タスク管理やプロジェクト管理,バグ管理もできません。この辺りは,SourceForge等の方が強いと思います。Lhaz開発では,別途Redmineを使用して,それらの管理を行っています。逆に,コードレビュー専用だけに,セットアップさえ済めば,運用上はボタンを押すだけのシンプルさ,とも言えるかもしれません。

カテゴリー: 技術メモ | コメントをどうぞ

歌集・句集


吟醸の 香に添い調ぶ 蟋蟀の 歌に酔うらん 長き月夜に
多摩川の 小川に見えし エジプトの ナイルを眺め 帰り来たれば
満開の 桜のもとに 笑う君 心配するな 尽くせ全力
命とる 物のほどかは 靖国の 桜となりし 学徒思へば

閏日の朝楽しげに雪雀

カテゴリー: 文系 | コメントをどうぞ

開発をつぶやく


Gerritのmergeフックを利用して,ソースの変化をTwitterにつぶやく方法です。

Gerritにソースをpushして,レビューアにapproveされて,Submitボタンを押して変更がマージされると,下記スクリプトが実行されます(「review_site」はGerritのインストール先です)。

review_site/hooks/change-merged

実行される際のパラメータは,以下のようになります。

change-merged --change <change id> --change-url <change url> --project <project name> --branch <branch> --submitter <submitter> --commit <sha1>
  • change id: Gerrit上のURLの連番
  • change url: GerritのURL
  • project name: gitのリポジトリ名
  • branch: マージされたリモートブランチ名
  • submitter: 変更をpushした人
  • sha1: コミットのhash

ツイート内容として,

[プロジェクト] コミットコメントのサブジェクト GerritレビューURL

例) [lhaz] Clean up of sort kind/reverse http://review.chitora.com/#change,497

とつぶやきたい場合,change-mergedスクリプトの内容を以下のようにします。

#!/bin/sh
URL=$4
PROJECT=$6
SHA1=$12
cd ../git/$6.git
TITLE=`git show -s --format="%s" $SHA1`
twt "[$PROJECT] $TITLE $URL"

それぞれ引数を変数に引き取り,

cd ../git/$6.git

にてgitリポジトリのディレクトリに移動します。hooksから見た相対位置になります。

TITLE=`git show -s --format="%s" $SHA1`

はコミットのサブジェクトを取り出すgitコマンドになります。
twtは自作のコマンドラインでツイートするツールですが,類似のものが使用できると思います。

カテゴリー: 技術メモ | コメントをどうぞ