今日のGreasemonkey - Table Filter

投稿者 nanki 2007-03-12 08:38:00 GMT

screenshot

はじめてのGreasemonkeyでもある。

10行以上のtableや、リストの上にインクリメンタルな検索ボックスが追加される。 使ってみると、いたるところに現れる。

vim で言うところの、SmartCaseも使える。

tablefilter.user.js


JavaScript URLMapper

投稿者 nanki 2007-02-13 15:03:00 GMT

ちょっと複雑なパス体系を持つRailsアプリでJSONでAJAXする人には役に立つかもしれない。 GoogleMapsとかね。

要 prototype.js

使い方はこんな風。

URLMapper.connect(
  "/user/:user_id/category/:category_id/entry/:action/:entry_id",
  {controller: 'entry', action: 'index', entry_id: null});
URLMapper.connect(
  "/user/:user_id/category/:action/:category_id",
  {controller: 'category', action: 'index', category_id: null});
URLMapper.connect(
  "/user/:action/:user_id",
  {controller: 'user', action: 'index', user_id: null});
URLMapper.connect(
  "/:controller/:action/:id",
  {action: 'index', id: null});

URLMapper.url_for({controller: 'entry'});
// -> "/entry/index/"
URLMapper.url_for({controller: 'entry', action: 'new'});
// -> "/entry/new/"
URLMapper.url_for({controller: 'category', action: 'new'});
// -> "/category/new/"
URLMapper.url_for({controller: 'category', action: 'new', user_id: 3});
// -> "/user/3/category/new/"
URLMapper.url_for({controller: 'category', action: 'update', user_id: 3, category_id: 2});
// -> "/user/3/category/update/2"
URLMapper.url_for({controller: 'entry', action: 'update', user_id: 3, category_id: 2, entry_id: 1});
// -> "/user/3/category/2/entry/update/1"

url_for は可変長引数をとって、引数をHashとしてマージするので、

//サーバからJSONを取得。
//[{user_id: 3, category_id: 2, entry_id: 1}, ...]
var entries = getJSON();

URLMapper.url_for({controller: 'entry', action: 'update'}, entries[0]);
// -> "/user/3/category/2/entry/update/1"

とか。

ソースはこんなの。

Hash.prototype.subtract = function(op2) {
  var result = $H().merge(this);
  this.remove.apply(result, $H(op2).keys());
  return result;
};


var URLMapper = {
  url_options: $A(),

  UrlOption: function(url, required, defaults, match) {
    this.url      = url.gsub(/\/:([A-z_][A-z0-9_]*)/, function(match) {return '/#{' + match[1] + '}'});
    this.required = required;
    this.defaults = defaults;
    this.match    = match;
  },

  extractParameters: function(url) {
    var params = $H();
    url.scan(/\/:([A-z_][A-z0-9_]*)/, function(match) {params[match[1]] = true});
    return params;
  },

  connect: function(url, defaults) {
    url = url.gsub(/%3A/, ':');
    var params = this.extractParameters(url);
    var required = params.subtract(defaults);
    this.url_options.push(new this.UrlOption(url, required, $H(defaults), $H(defaults).subtract(params)));
  },

  url_for: function() {
    var options = $A(arguments).inject($H(), function(r, v){return r.merge(v)});
    var detected = this.url_options.select(
      function(url_option) {
        return url_option.required.subtract(options).size() == 0 && url_option.match.all(function(pair){return options[pair.key] == pair.value});
      }
    ).sortBy(function(url_option) {
      return $H(options).subtract(url_option.required).subtract(url_option.defaults).size();
    }).first();


    if (!detected) {
      throw "no URL matches.";
    }

    return (new Template(detected.url)).evaluate($H().merge(detected.defaults).merge(options));
  }
}

Operaのバグ?

投稿者 nanki 2007-01-17 14:39:00 GMT

最近、Javascript付いている。

Ajaxのレスポンス中に<script>タグを埋め込んでいたら、Operaで動いてない。
prototype 1.4.0のevalScriptsがOperaでは動かないらしい。

  evalScripts: function() {
    return this.extractScripts().map(eval);
  },

  evalScripts: function() {
    return this.extractScripts().map(function(a){return eval(a)});
  },

と変更することで直るのだとか。

1.5.0を使おう。

参考

Bug in Opera? Problems calling Prototype’s evalScripts()


Lightbox JS : Webとモーダルダイアログ

投稿者 nanki 2006-02-23 09:25:00 GMT

Lightbox JSを使ってみた。

<a href="large.png" rel="lightbox" title="...">
<img src="thumbnail.png">
</a>

というコードを書き、画像をクリックすると、ページ遷移は起こらずに、画面が半透明の膜で覆われ、その上に大きい画像が表示される。(実物を見るのが早い)

すぐに、これはモーダルダイアログの代わりになるなと思い、prototype.jsと組み合わせて、画像以外も表示できるか試してみた。

モーダルダイアログには使いにくいという印象しかないのでどうなることかと思いきや、思いのほか使いやすい。

思うに、WebにおけるUIというのはほとんどモーダルなのだ。設定画面を使ってる間、前の画面を操作することはない。 ページを遷移して、何かしらの操作をして、また戻る、という袋小路のようなページがたくさんある場合、これをLightbox風モーダルダイアログに置き換えても、得るものこそあれ、何も失うものはない。

都合のいいことに、ほとんどのモダンなブラウザに対応している上、Javascriptが動かなくても、ただのリンクにしか見えないので、よほどのことをしない限りはテキストブラウザ上でも今までと同様に動作する。

検索 UI の改善:NULL::something では、検索ボックスの結果がオーバーレイ表示される。(Lightboxは使ってなかったと思う&IEは未対応)

もうちょっと改良してみようかと思ったら、こんなのあった→Lightbox Gone Wild!

参考:

Lightbox JS

モーダルダイアログとは

検索 UI の改善