prefwindowの伸縮

内のエレメントの内容が折り返されて複数行になったときトップレベルウィンドウが追従してスペースを拡張せずに下の内容が切れてしまうという現象に悩まされてる。解決策を探索中ここ https://bugzilla.mozilla.org/show_bug.cgi?id=283697 でのfixとして3.0a9で突っ込まれたwindow.sizeToContent()が先のこけてる個所であることを偶然見つけたりして。それはいいとして、内に配置されるコンポーネントの文字列が折り返されてコンポーネントの高さが変わってもトップレベルウィンドウが追随して伸張しないというのは未だ放置されている不具合のようである。( https://bugzilla.mozilla.org/show_bug.cgi?id=394793 )

描画時の動的なレイアウトに頼らず高さを固定で決め打ちしておくにしても、ローカライズするとなれば言語によっては相当に長さが変わることが考えられる。そのため開発中の見た目より倍近い十分な高さを空けておくなどという情けない対策をとらざるを得ない。なんとかならないか試行錯誤した末、以下のようなhackに行き着いた。

<prefpane onpaneload="onpaneload();">
<vbox id="descbox">
<description id="desc" width="300">改行されるくらい長い文字列</description>
</vbox>
</prefpane>

<script>
function onpaneload()
{
  setTimeout(function(){
    var h = document.getElementById("desc").boxObject.height;
    document.getElementById("descbox").setAttribute("height",h);
    window.sizeToContent();
  },1);
}
</script>

なんらかの原因によってsizeToContentが複数行になりうるコンポーネントの高さを一律一行であるとみなして全体の高さを計算してしまっているようなので、文字列のサイズとは無縁なboxで囲んであげた。DOMInspectorで見たところboxObject.heightはコンポーネントが改行した後の高さを保持してくれているようなので、これを後からboxへ伝えてやる。然る後、sizeToContentし直してあげているという仕組みである。

これでbabelzillaで訳を短くするよう努めてくれなんて注意書きをしなくて済むというものだ。