月別アーカイブ: 2012年8月

さらっと理解しておきたいjQueryオブジェクト(前編)

CSSコーダにとって、サイトを動的にしたい時の救世主となるjQuery。CSSセレクタで要素を選択し、あとはメソッドの書式に従っていくつかの呪文を唱えるだけで、簡単にアニメーションや文書構造の変更ができます。たとえば、サイト訪問時にclass=”fadein”とした全要素をフェードインする場合、以下のようなソースで事足ります。

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="ja" lang="ja" dir="ltr">
<head>
//meta宣言とtitleは省略
//jQueryのインポート(Google CDN)
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script>
<script>
$(function(){
$(".fadein").fadeIn();
//要素がフェードイン
});
</script>
</head>
//省略

もちろん$(“#main ul li”)のような指定にも対応していますので、解説サイトのサンプルをコピーして、セレクタ部分を変更するだけで好きな要素に処理を適用できます。
また、同じ要素に対して複数の処理を連続して適用する場合には、処理を順番にピリオドで繋いでいけばよいという特性も直感的です。メソッドチェーンと呼ばれるこの書き方を頭に入れておけば、JavaScriptについてほとんど知識が無くても、処理部分に手を加えることができます。

$(".fadeinout").fadeIn().fadeOut();
//フェードイン後フェードアウト

こうした直感的な文法をもつjQueryですが、本当に直感のままの記述を行っていると、ときどき反逆します(笑)。メソッドチェーンが有効にならず、途方に暮れてしまいます。たとえば次のような例です。

$(".fadeinout").attr("class").appendTo("#classname");
//クラス名を取り出し、classnameというidの領域に表示したい
//動きません

あるいは、JavaScriptについて少し知識のある人間が、jQueryもJavaScriptだからとチャンポンな書き方をして反逆されることもあります。

$(".fadeinout").innerHTML = "Hi!";
//動きません

何故こういったことが起こるのか、結論から言いますと、jQueryは独自メソッドをもつjQueryオブジェクトというオブジェクト形式を扱う為で、メソッドチェーンなどもメソッドの返り値がこのjQueryオブジェクトである為に実現しているのです。

jQueryオブジェクトを知る為に、JavaScriptのオブジェクトの種類について整理してみましょう。

組み込みオブジェクト 〜素のJavaScriptが持つオブジェクト

JavaScriptというと、WEBページを動的にする手段としてWEBと切っても切り離せない言語であると思われがちですが、実際のところ素のJavaScriptがそういった機能を有しているわけではありません。ブラウザ以外のJavaScript実行環境で、document.writeIn()などと命令しても、JavaScriptはそれがどういう命令なのか理解する事ができません。
それでは素のJavaScriptはどのような要求に応えるのかというと、数値や文字列の演算であったり、メモリへのアクセスであったりと、プログラミング言語の基本的な処理です。
しかしながら、素のJavaScriptにもオブジェクトやメソッドといった概念があり、既に組み込み済みのオブジェクトもあります。たとえばStringオブジェクトは文字列を操作するメソッドを提供するオブジェクトで、このオブジェクトは特に宣言をしなくても、文字列データに対して自動的に呼び出すことができるようになっています。

var movie = "演歌の花道";
var titlelength = movie.length;
//titlelengthの値は5

この例では変数movieに入った文字列をStringオブジェクトで自動的にラップしているため、Stringオブジェクトのlengthメソッドを使う事ができています。他にも組み込みオブジェクトとして、NumberやArrayなどがあります。

ブラウザオブジェクト 〜ブラウザメーカーによる勝手実装のオブジェクト

JavaScriptがWEBページを処理の対象として認識できるのは、WEBブラウザがJavaScriptのオブジェクトとしてページを定義し、処理の為のメソッドを提供しているからです。具体的にはページはWindowオブジェクトとして定義され、Windowオブジェクトの直下にdocument、location、navigatorなどのプロパティがあり、これらもまたオブジェクトとして定義され、メソッドが提供されているといった構造です。そして基本的にこのWindowオブジェクトは省略して書く事ができるため、おなじみのdocument.writeIn()という表記になっているわけです。
ちなみにWindowオブジェクト自体のメソッドとしては、setTimeOutなどのタイマー系やalertなどのウィンドウ表示系があります。これらは確かにdocument.alert()のようには書きませんね。

documentオブジェクトは下位にforms、images、anchorsといったオブジェクトを持ち、これらのオブジェクトはページ中のフォーム要素、イメージ、アンカー全てを配列に格納してくれているので、name属性やインデックスで個々の要素を取り出す事ができます。

var formvalue = document.フォーム名.要素名.value;
var formvalue = document.forms[インデックス].elements[インデックス].value;
var imagesource = document.イメージ名.src;

このように基本的なオブジェクトモデルをベンダーが定義してくれているおかげで、JavaScriptがWEB制作の言語として特待的なポジションを得ているわけです。ただ、ブラウザオブジェクトはIEとNetscapeのブラウザ戦争の過程で、独自仕様を実装しよう(そして囲い込みを行おう)という目論見のもとにルール無用に拡張されていった背景があります。そこで、そうした勝手実装でなくどのブラウザでも共通した記述が可能になるようなオブジェクトモデルが求められるに至りました。

DOMオブジェクト 〜XMLの汎用的な操作モデルを導入したオブジェクト

DOMとはDocument Object Modelの略で、HTMLの親戚であるXMLを操作するための汎用モデルです。ブラウザオブジェクトの勝手実装による混乱に収拾をつけるため、W3Cはこのモデルをベースにしたオブジェクトやメソッドを定義し、勧告としました。
DOMオブジェクトは文書中のhtmlタグとその属性、テキストなどに対応し、メソッドやプロパティを持ちます。また各タグへのアクセス方法として、タグ名、id、クラス名での検索メソッドを提供しています。これらはブラウザオブジェクトのdocumentオブジェクトをhtml文書の最上位の要素<html>の参照というかたちで実装されているので、これまでのブラウザオブジェクトのスクリプトと併存して使う事ができます。

document.getElementById("target").value = 1;
//idをもとに要素をオブジェクトとして取得するgetElementByIdメソッド
 
var element = document.lastChild;
//要素の親子関係(子要素を内包する親要素)をもとに要素を取得
 
element.setAttribute("id","idname");
//要素に属性を付加

今回はjQueryオブジェクトの説明まで辿り着かなかったので、次回に続きます。


Twenty Elevenテーマで、個別記事にサイドバーを表示したときのレイアウト崩れ対策

以前このブログでは、digitalnatureのMystiqueというWordPressテーマを導入し、デザイン部分についてはほぼデフォルトのまま使用していました。何しろ優秀なテーマで、機能も多く、特に他のテーマに乗り換える動機も無かったのですが、000webhostのテロルによってブログを強制削除された事件の後は、これを機に自作テーマ開発でも行おうかという目論見もありWordPress標準テーマであるTwenty Elevenを暫定的に使い続けていました。

このTwenty Elevenテーマですが、デフォルトの設定だと各記事ページ、固定ページにサイドバーが表示されないため、不便です。自作テーマ移行まで過渡期的な利用だと割り切っていたため対策も行わなかったのですが、容易に設定ができるようなので実験がてら設定してみました。

固定ページへのサイドバー追加

固定ページへのサイドバー追加は非常に簡単です。

固定ページへのサイドバー追加

固定ページへのサイドバー追加

投稿画面のページ属性で、Sidebar Templateを選択するだけです。

各記事ページへのへのサイドバー追加

各記事ページへサイドバーを追加するには、実際にTwenty Elevenのソースに手を加えなければなりません。とは言え、失敗するリスクやヴァージョンアップ時に変更がリセットされてしまう危険性を避ける為に、以前紹介記事を書いた子テーマを利用しましょう。

記事の中での説明にあるように、カスタムスタイルシートについては、子テーマの中で親テーマのstyle.cssを呼び出す処理が書けました。追加の部分についてはCSSの後着優先という性質を利用して上書きをしましたね。一方、××.phpのような処理を書くファイルについては、処理の順序の問題もあり、子テーマのファイル中で親テーマのファイルを呼び出すというのは難儀です。そのため、カスタム処理を書きたいファイルを子テーマのフォルダ内にコピーし、そのファイルに処理を追加するという形になります。子テーマに同名のファイルが見つかると、親テーマのファイルは参照されません。

さて子テーマの作成、有効化までは完了したものとして、サイドバーを呼び出す処理を書きます。各記事ページにアクセスする時に呼び出されるのは、Twenty Elevenのテーマフォルダの中にある、single.phpです。WordPressではテンプレートエンジンのごとく、HTMLを断片的に吐き出してページを完成させています。つまりサイドバー部分の断片を吐き出す命令を、しかるべき位置で呼び出してやれば良いわけです。

//子テーマにコピーしたsingle.php
<?php
/**
 * The Template for displaying all single posts.
 *
 * @package WordPress
 * @subpackage Twenty_Eleven
 * @since Twenty Eleven 1.0
 */
 
get_header(); ?>
<div id="primary">
<div id="content" role="main">
<?php while ( have_posts() ) : the_post(); ?>
 
/* 中略 ちなみにこの部分で記事を取得、表示しています */
 
<?php endwhile; // end of the loop. ?>
</div><!-- #content -->
</div><!-- #primary -->

//ここにこの一文を追加します。
 
<?php get_sidebar(); ?>
 
//追加部分終わり
 
<?php get_footer(); ?>

get_sidebarという命令がそのまま、サイドバーを取ってくる処理です。フッターを呼び出す、get_footerの前で呼びましょう。これをsingle.phpという名前で子テーマフォルダに保存すると、個別ページの表示がこのようになります。

サイド?バー

サイド?バー

ご覧のように、コメント投稿欄の下にサイドバー部分がはみ出てしまいます。新しくサイドバーを表示するようにしたため、個別記事ページで呼び出されるCSSも調整する必要があります。子テーマのstyle.cssに、以下の内容を追加して下さい。

.singular #primary{
float: left;
	margin: 0 -26.4% 0 0;
	width: 100%;
}
 
.singular #content,
.left-sidebar.singular #content {
	position: relative;
margin: 0 34% 0 7.6%;
	width: 58.4%;
}
 
.singular .entry-header,
.singular .entry-content,
.singular footer.entry-meta,
.singular #comments-title {
	margin: 0 auto;
	width: auto;
}

個別記事ページでは、記事が表示されるエリアに.singularというクラスによる限定が付いており、通常の記事エリアのidである#primary、#contentの指定より優先されています。したがって基本的には#primary、#contentの指定をそのまま.singularで限定されたセレクタの宣言にもってきて上書きすれば良いのです。

子テーマでの宣言が有効に

子テーマでの宣言が有効に

ちなみに、追加部分の最後、.singular .entry-header以下略の部分は、コメント投稿欄の幅などを指定しています。親テーマのstyle.cssそのままだと、サイドバー抜きの場合の表示幅を基準にサイズを合わせるので、不格好になってしまいます。そこで、widthをautoに指定し直しています。

面倒だという方に…

以上がサイドバー表示の手順ですが、ここまで手を入れるのは面倒だという人の為に、Twenty Elevenにサイドバーを追加するニッチなプラグインがいくつかあります。Twenty Eleven Theme Extensionsが有名ですね。

Twenty Twelveではもう少し融通が利くようになってほしいものです。