yamicha.com's Blog - Presented by yamicha.com
Blog yamicha.com's Blog - 2018/09 の記事
[1] [2] [3] [4] [5] [6] [7] [8] [9] [10] [11] [12] [13] [14] [15] [16] [17] [18] [19] [20] [21] [22] [23] [24] [25] [26] [27] [28] [29] [30]

yamicha.com's Blog
 諸事情により、現在更新休止中。ご了承ください。もし今後ブログを再開することがあるとすれば、その際にはこのブログスクリプトではなく、新しく開発したものによるかもしれません。
 当ブログ管理者についてはこちらをご参照。
開発魔法(737)
社会問題(733)
お知らせ(11)
質問・バトン回答(15)
ゲスト出演(8)
経済・知的財産(150)
ゲーム開発(182)
[Ada] 勝手に補足
- Note
- 金配りの次の一手


- Endless Ultimate Diary
- 銃世界

漢字バトン
- うるる雑記帳
- 漢字接力棒

ツキアイゲノムバトン
- ブログ@うにうに画像倉庫
- あぶ内閣

縺イ縺セ縺、縺カ縺励ヰ繝医Φ
- 月夜のボヤキ
- 騎士サーラバトン
パスワードを使う
名無し (2012/02/27)


開発者解放裁判
yamicha.com (2010/03/14)
Winnyに関しては、私も「純白」とまでは考えておりませんし、使用し..

開発者解放裁判
通りすがり (2010/03/08)
winnyに関しては「ダウンロードソフト板」なんてところを拠点に開発..

新型インフルエンザの恐怖
いげ太 (2009/11/03)
> C#などの「int Some(int , int)」は、F#では「(int * int) ->..

時効に関する思考
yamicha.com (2009/08/31)
>いげ太さんコメントありがとうございます。手元にドキュメントが少..
Homepage
Blog Top
Normal View
List View
Search
Calendar
Comment List
Trackback List
Blog RSS
Send Trackback
Phone Mode
Administrator
yamicha.com
Blog
るううるる。
Source
法令データ提供システム
FindLaw
Development
Java2 Platform SE 6
Java EE 6 API
MySQL Developer Zone
PHP Reference
MSDN Library
Ada Reference Manual
Objective Caml
Python Documentation
Erlang
Prolog Documents
ねつ造の重量
2007/08/14(Tue)19:38:03
 ねつ造や隠蔽が横行する日本。これもある意味「お国柄」なのでしょうか。
 ところで、中国の「段ボール肉まん」ねつ造報道はまだ記憶に新しい事件ですが、このほど地裁で懲役1年の判決が下されました。日本では考えられないスピード判決かつ量刑です。中国政府が情報統制や言論封殺を行っていることは有名ですが、それでもねつ造は厳しく処断されるべき犯罪ということでしょうか。
 無論、いくら中国でも「ねつ造罪」などは存在しないと考えられますので、今回の判決も「ニセ報道で損害を与えた」ことが直接の罪状のようです。ちなみに、以前に米国で「有名ファーストフードチェーンの食べ物に人間の指が混入していた」事件があり、後に主張者の自作自演であると分かりましたが、この際の罪状は「窃盗罪」でした。「この狂言で同チェーンは大きな販売不振を引き起こしたため、本来得られるはずであった利益を窃盗した」と解釈した上での適用のようです(日本では状況によって「業務妨害」「詐欺」「恐喝」などの罪が適用されるものと考えられます)。ところ変われば法変わる、とでもいいましょうか。
 しかし、中国はある意味日本より進んでいるのではないでしょうか。仮に日本で同様のねつ造が行われ、大変な騒ぎになったとしても、記者に下る罰はせいぜい「新聞社からの懲戒免職」が関の山でしょう。仮に刑事事件になっても執行猶予は見えています。新聞社の責任にしても、ねつ造した記者を「尻尾切り」するか、せいぜいトップが交代する程度でおしまいです。その他、記者や新聞社に対して被害者が民事訴訟を起こすこともできますが、取り返せるのはせいぜい「ニセ情報で被害を受けた分の実費」と「すずめの涙程度の慰謝料」だけですから、裁判に費やすリソースや根強く残るであろう偏見を考えれば、やられ損であることは確実です。
 中国ではこれで(「ねつ造」が直接の罪状ではないとはいえ)懲役1年なのです。ねつ造という行為の重大性を考えれば、日本の対応が甘すぎるのは明らかです。もし日本がねつ造に対して厳しい姿勢で臨むことを検討した場合、マスコミ連中はおそらく「報道を萎縮させる」などと理屈をコネてくるでしょうが、全く当たりません。報道において勇み足は問題ですが、ある程度の推測を交えた報道がなされるのは時としてやむを得ません。しかし、それとねつ造は全く異質なものであり、マスコミがねつ造を前提としていない限り報道を萎縮させることはありません。ねつ造は確信犯なのですから、「知らず知らずのうちにねつ造していました」ということはまず起きないのです。
 極めて重大なねつ造をしておきながら、全く何事もなかったかのように批判をやり過ごし、しばらくしてまたねつ造をやらかすようなマスコミ連中の態度を見るにつけ、例えばテレビ局なら放送免許の停止や剥奪も含む厳しい処分を導入すべき時期ではないかと考えるばかりです。ねつ造は確信犯なのですから、やましいことがなければ反対する必要はないはずです。

 昨今の政府の笑い話としか考えられない所業。「再チャレンジ」と称して役人152人を既卒採用(年齢制限あり。20代後半〜30代前半がターゲットとされる)しようとしたところ、何と25000人の応募があったといいます。政府サイドは「良い人材が手に入る」とウハウハですが、これのどこが「再チャレンジ」なのか、私には理解不能なのですが。
 要するに、これまでの政府は政治家や大企業に「盛り土」するために土を削ってきて(派遣の規制解禁など)、元は平地にいた人々を削った後の大穴にバンバン投げ込んだわけです。そうして何十万、何百万人を落としておいて、今になってようやく150本ロープを垂らして「再チャレンジ」とは。このロープに25000人が殺到し、確率にして0.6%、あきれて物も言えません。既卒採用自体は悪いとは言いませんが、これでは再チャレンジもへったくれもありませんから、「再チャレンジ」ではなく「人材発掘のための既卒採用」と呼ぶべきです。
 そして今度は「最低賃金を6〜19円上げる」そうです。それに一体何の意味があるのでしょうか。単なるパフォーマンスなのでしょうが、パフォーマンスにしては貧弱です。これについては利権者から「中小企業の息の根を止める」などという反対意見が出ているようですが、そのリスクを取らないのであれば、代わりに国民の息の根が止まるだけです。足腰の強い景気回復を望むのであれば、大幅引き上げ以外に道はありません。人件費の懸念から雇用が鈍る恐れについては、残業代の大幅上昇などによって「既存の人間に無理させるよりも人を増やした方が得」という状況を作ることで回避できます。
 とはいっても、これは安倍氏をトップから引きずりおろした後の話でしょう。無賃残業合法化制度などを見ても、安倍内閣がどちらを向いているかは明らかです。しかも、自身の内閣初の選挙であれだけ負けても「続投」なのですから手がつけられません。では国民がどのような意思表示をしていれば退陣していたのでしょうか。しかも、安倍内閣が取得した議席は参院の37議席だけなのですから、衆院の与党2/3を使った強引な法案成立は「国民の信任を受けていない」のです。もし衆院解散を行い、できれば低IQ戦略によらない選挙で、与党が議席の2/3を獲得したのであれば、それで初めて国民の信任を受けたことになります。国民の意思に反したことを次々に行う安倍内閣、ある意味戦後まれに見る内閣でしょう。
 ここで重要になるのが民主党です。同党は「全国平均賃金1000円」を掲げていますが、ここまでの改革は少々難しいにしても、自民党にこれを突きつけてより高い妥協を引き出すことは可能です。政治資金規正法などにしても同様です。与党が民主党案を強引に叩き潰したり、あるいは自分の案を強引に成立させるなどし、かつ民主党案が明らかに優れているのであれば、次の衆院選で民主党に投票すれば良いのです。より高い譲歩を引き出せれば民主党の成果ですし、国民のためになる民主党案を与党が叩き潰せば与党の失点です。逆に、民主党が(無賃残業合法化制度のような)バカげた案を出してきた場合、これは民主党の失点となります。こうしたことを判断材料とした上で行われるのが本来の選挙というものです。
 ともかく、まずは企業の利権を省みずに改革を断行できる人間がトップに立つことです。これなくして「企業を生かす代わりに国民の息の根を止める」政策の歯止めはありません。この点、安倍内閣は誰でも良いので取り替えてしまうべきでしょう。誰に取り替えたとしても、改善または据え置きということはあっても、これ以上悪くなることは考えられません。

 その安倍氏ですが、大敗を受けて記念日参拝を行わないなど後退しています。氏ばかりか取り巻きの閣僚も同様です。私は以前から「靖国参拝には何の利益もないため、行うのは単なるムダ」と主張していますが、それにしても選挙で大敗したら閣僚ともどもコロッとおとなしくなるとは。外交関係悪化のリスクを背負ってまでの信念とはどれほどのものかと考えていたら、その程度ですか。そのようなふぬけ参拝など最初から行わなければ良いのです。
 そして今度は慰安婦に関する包囲網が狭まってきています。安倍氏としては「自分の主張を通した」つもりなのでしょうが、はたから見ればほとんど自爆です。ちなみに、慰安婦決議に関しては読売などの一部新聞社がおかしな社説を書いていたりと、安倍氏サイド以外でも一部に奇妙な意見が存在します。河野談話をどうするか、慰安婦問題の存在を事実とするかは個々の考えですから良いのですが、例えば「他国も同様のことを行っていたのに日本に対する決議は不当」であったり「他国人も慰安所を利用していたが、それは問題ないのか」といった主張に関しては失笑を禁じえません。これが事実とするなら、他国も悪いことは論を待ちませんが、だからといって日本の罪が軽くなるわけではありません。「そのような事実はなかった」と主張するならともかく、「他国もやっていた」という主張を展開するなら、「日本に対する決議は不当」ではなく「他国に対しても同様の決議を行うべき」と主張するのが妥当です。
 余談ですが、このような方法による「言葉のトリック」は慰安婦問題以外にも結構使われているようです。しかし、冷静に見ればこれが非常にこっけいなものであることが分かります。例えば車2台が信号無視をしたとして、後ろの車だけが捕まったとします。しかし、そのドライバーが「前の車は捕まらなかった」と主張したところで、同ドライバーが無罪放免にされるべきでないのは言うまでもありません。このドライバーにできることは、せいぜい「これでは公平でないので、前の車のドライバーも捕まえてくれ」と言うだけです。これは非常にだまされやすいトリックですので、冷静に分析した上で一笑に付すようにしましょう
 そして今度は、どうやら支持率を取り戻すためのパフォーマンスのようですが、原爆症患者に対する支援に言及しました。いくら人気取りであっても、これ自体は良いことです。ところが、やはりこれは人気取りのリップサービスに過ぎないらしく、裁判では早速控訴。ここまで来ると伝説の内閣ではないでしょうか。

 EJBもPerl 6も現段階で使えるところまで使ってしまい、PHP 6もServlet 3.0もJava EE 6もずっと先。今さらVC++ 6.0でできることも知れており、SQLは目新しいでもない。さて、どうしたものでしょう。そんなこんなでSwingでも。
 そういえばSE 6でタブがかなり改善されたようですが、使ったことがありませんでした。SE 6のSwing絡みでは、Look and Feelの自作が簡単になったことがある程度注目されたようですが、タブとなるとどうにも。やはり地味な変更であるためでしょうか。しかし、Look and Feelも「簡単になった」とはいいますが、やはり死にそうなほどコードを書く必要がありました。どうも敷居が高くていけません。
 ではタブはどうかといいますと、こちらは実に簡単です。主な変更点は「タブ上にボタンを配置できる」といったことですが、つまりはタブ上にAWTやSwingのコンポーネントを置けるというだけですから、(単にコンポーネントをタブ上に配置するだけなら)これといって苦戦する要素もありません。
 それでは閉じるボタンを持つ単純なタブのサンプルを。コードの再利用を簡単にするため、今回はJTabbedPaneをオーバーライドしていますが、別にオーバーライドしなくても実装するのは簡単です。
// Main.java
public class Main{
	public static void main(String args[]) throws Exception{
		Frame f = new Frame();
	}
}

// Frame.java
import javax.swing.*;
import java.awt.*;
import java.awt.event.*;

public class Frame extends JFrame implements WindowListener{
	private UserTabbedPane tab;

	public Frame() throws Exception{
		addWindowListener(this);
		setSize(300 , 300);

		getContentPane().setLayout(new BorderLayout());

		// タブを構築
		tab = new UserTabbedPane();

		// 最初からあるタブを登録
		for(int i = 0; i < 5; i++){
			tab.addAutoTab(new JLabel("タブ(" + 
				tab.getCount() + ")") , 
				new JLabel("Tab Content " + tab.getCount()));
		}

		getContentPane().add(tab , BorderLayout.CENTER);

		// タブの変更用ボタン
		JPanel menu = new JPanel(new FlowLayout());

		JButton create = new JButton("タブの作成");
		create.addActionListener(new ActionListener(){
			public void actionPerformed(ActionEvent e){
				tab.addAutoTab(new JLabel("新タブ(" + 
					tab.getCount() + ")") , 
					new JLabel("New Tab Content " + 
					tab.getCount()));
			}
		});

		JButton close = new JButton("すべて閉じる");
		close.addActionListener(new ActionListener(){
			public void actionPerformed(ActionEvent e){
				tab.removeAll();
			}
		});

		menu.add(create);
		menu.add(close);

		getContentPane().add(menu , BorderLayout.NORTH);

		setVisible(true);
	}
	public void windowActivated(WindowEvent e){
	}
	public void windowClosed(WindowEvent e){
	}
	public void windowClosing(WindowEvent e){
		dispose();
	}
	public void windowDeactivated(WindowEvent e){
	}
	public void windowDeiconified(WindowEvent e){
	}
	public void windowIconified(WindowEvent e){
	}
	public void windowOpened(WindowEvent e){
	}
}

// UserTabbedPane.java
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;

public class UserTabbedPane extends JTabbedPane{
	private int count;

	public UserTabbedPane(){
		count = 0;
	}
	public void addAutoTab(Component tab , Component content){
		// 現在のタブ数を取得
		// これがそのまま「今回登録するタブのインデックス」になる
		int number = getTabCount();

		// タブを登録
		// タブ名を count の値とする
		add(String.valueOf(count) , content);

		// タブ用のパネルを構築
		JPanel p = new JPanel(new BorderLayout());
		p.setOpaque(false);

		// 閉じるボタン
		JButton button = new JButton("x");
		button.setPreferredSize(new Dimension(42 , 18));

		final String value = String.valueOf(count);
		button.addActionListener(new ActionListener(){
			public void actionPerformed(ActionEvent e){
				// タブ名から現在のインデックスを取得し...
				int index = indexOfTab(
					String.valueOf(value));
				// タブが見つかったなら削除
				if(index != -1)
					remove(index);
			}
		});

		// 閉じるボタンをタブの右端に登録
		p.add(tab , BorderLayout.CENTER);
		p.add(button , BorderLayout.EAST);

		// タブに項目を設定
		setTabComponentAt(number , p);

		// カウントを増やす
		count ++;
	}
	public int getCount(){
		return count;
	}
}
 注意点をいくつか。
 まず、タブの「閉じる」ボタンを定義する際、匿名クラスに自身のインデックスのタブを閉じるよう登録してはいけません。なぜなら、タブ1、タブ2、タブ3を順番に登録した場合、それぞれインデックスは「0,1,2」となりますが、タブ1を閉じるとインデックスが1つずつずれて「-,0,1」となります。この状態でタブ3を閉じようとすると、匿名クラスに登録されている閉じるべきタブのインデックスは2、しかしインデックス2は存在しないため、例外を投げられてしまいます。
 今回はこれを回避するため、タブ名を識別に使用しています。なお、タブ名は普通ならタブ上に表示されるのですが、タブ上に表示するコンポーネントをセットした場合にはタブ名が無視されるため、タブ名として純粋に識別用のユニーク名をつけてしまうことができます。
 上記コードでは閉じるボタンなどによって実装が少々長くなっていますが、単にタブに何らかのコンポーネントを使うだけなら以下のコードのみで可能です。
JTabbedPane tab = new JTabbedPane();
tab.add("タブ名" , new JLabel("タブクリック時に表示されるコンポーネント"));
setTabComponentAt(0 , new JLabel("タブ上に表示されるコンポーネント"));
 上記でJLabelを渡している部分には、JButton、JTextField、JPanelなどあらゆるものを渡すことができます(引数はComponent型ですので、一応AWTコンポーネントも渡せます)。JPanelを渡せるということは、複数のコンポーネントを登録したパネルをも渡せることを意味します。
 今回はタブに閉じるボタンを使用してみましたが、あらゆるものを渡せるということで、コンボボックスなどを登録してもしっかり動作します。しかし、タブ上のコンポーネントをクリックした場合、そのコンポーネントがクリックされたのと同じ扱い(ボタンなら押される、テキストフィールドならフォーカスが合う、コンボボックスなら展開する)になるのではありますが、タブ自身がクリックされたことにはなりません。つまり、とあるタブ上にボタンがあるとして、このボタンを押したとしても、タブはアクティブになりません。


 閉じるボタンは画像にすれば見栄えが良いのですが、テストにつきこのような仕様です。タブを作っては閉じ、閉じては作り。

 タブ自体の実装はここまでですが、実際には他にも色々試していますので、他に分かったことを明記しておきます。
 まず、タブを使わずにタブに近い動作をさせるためのレイアウトとして「CardLayout」があります。これはその名の通り、コンポーネントがカード状に重なっているレイアウトで、最も上にあるコンポーネントしか表示されないようになっています。ですから、まずボタンなりコンボボックスなりを登録し、それらがクリックされた際にCardLayout中の何らかのコンポーネントが最上位に現れるようにしておけば、タブと同じ操作を実行することができます。
 さて、ボタン付きタブなどはここまでの実装で実現できるのですが、どうせならタブフォーム内に「新規作成」などのボタンを置いてみたいものです。本来タブが表示される部分の空欄に文字列やボタン、その他のコンポーネントが置ければなかなか便利でしょう。
 しかし、果たしてそのようなことが可能なのでしょうか。

1.文字列を表示する
 これは簡単です。JTabbedPaneを継承し、update(Graphics g)をオーバーライド、まずsuper.update(g)としてタブを描画した上で、GraphicsのdrawString()なり好きな描画メソッドを使って好きなように描くだけです。

2.ボタンなどのコンポーネントを登録する
 実はこれが非常に厄介でした。
 通常のコンポーネントはパネルなりにadd()しておけば自動的に表示され、しかもクリックなどのメッセージも自動的に受け取ってくれます。ところが、JTabbedPaneではすべてのadd()メソッドがオーバーライドされ、ここに登録されたコンポーネントはすべてタブとして扱われるようになっているらしく、add()するとタブになってしまいます。よってこの手は使えません。
 どうにかならないかということで、もしかするとJTabbedPaneはBorderLayoutを使っているかもしれず、これに上手く割り込めればコンポーネントを簡単に登録できるのではと考えました。ところが、使われているレイアウトはBasicTabbedPaneUI.TabbedPaneLayoutなのです。これに割り込むことも検討しましたが、やはりどうにもなりませんでした。
 JTabbedPaneのupdate()をオーバーライドさえすれば、そこで任意のコンポーネントを描画することは可能なのですが、そのコンポーネントは登録されていないのですから、何ら入力を受け取ることができません。一体どうすれば良いのでしょうか。
 少々強引な手段として、JTabbedPaneに対してMouseListenerなどのリスナをセットし、そのリスナ中からボタンなどの発火メソッド(fire〜)をコールして「押したことにする」ことは一応可能です。ただし、発火メソッドはprotected宣言されていますので、この方法を使う場合はボタンなど必要なコンポーネントのクラスをオーバーライドし、外部からでも発火できるようにしなければなりません。ボタン領域などの計算も自前で行う必要があります。また、無理やり「押したことにする」ため、コンポーネントのアニメーションはかなり捨てることになるでしょう。それ以外にもいくつか伝達方法はありますが、いずれも強引な手法によります。
 JTabbedPaneのオーバーライドに限らず、JTabbedPaneのUIであるBasicTabbedPaneUIを継承して色々書くことも可能ですが(JTabbedPaneのgetUI()では継承クラスのインスタンスを返すこと)、UIを直接いじってしまうため、タブでLook and Feelが使えなくなるものと考えられます。こちらにも慎重な検討が求められます。
 そして何より、苦労してまでそのようなことをするのであれば、タブにリスナを設定した上でCardLayoutを使った方が楽に決まっています。BorderLayoutなどを使い、タブを上、CardLayoutを適用するJPanelを下に設定するなどすれば、見栄えも普通のタブとあまり変わりません。無論、タブの横にボタンなどという機能を必要としないのであれば、素直にJTabbedPaneを使った方が楽なのですが、どうしても自由度が欲しいならこれも手段ということで。
 この場合、タブをクリックすると表示されるComponentとしてnullを渡しておきます。add("Tab Name" , null)など。

3.タブを全く関係ない動作と結びつける
 上記ができるからには、これもできるはずです。タブをほとんどラジオボタンやコンボボックスと同等のものとして扱えます。
 実際、JTabbedPaneにはSingleSelectionModel型のフィールド及びそれを返すメソッドが存在します。

 このように、地味に便利なJava SE 6のSwing機能。しかし、できればタブ周りはJPanelとBorderLayoutか何かでレイアウトし、プログラマがタブのレイアウトに介入できる余地を与えて欲しいところです。そうなれば、例えばタブをCENTERに配置し、タブ横ボタンをEASTやWESTに配置するなどして、ごく簡単にボタンを配置できるのですが。
 しかし、たまにはJavaでデスクトップアプリケーションを書くのも良いものです。Cと違って標準で色々なAPIが提供されていますし、VMさえ入っていればOSに関係なく動きますし。SE 6での細かな追加点を見ても分かるように、Sunはこちらにも結構力を入れているようです。ただ、個人的にはゲームバッド処理用APIが欲しかったのですが。Java SE 7は関数やらクロージャやらプロパティやらと新機能が目白押し(の予定)ですが、この辺りの進化も望みたいものです。
カテゴリ [開発魔法][社会問題] [トラックバック 0][コメント 0]
<- 前の記事を参照 次の記事を参照 ->

- Blog by yamicha.com -