長い文章に「続きを読む」リンクを付ける方法

Permalink2008/12/13 13:06:55
カテゴリ: ヘルパー, ビュー

CakePHP1.2 RC3

ブログの記事など長い文章を一覧で表示するようなページにおいて、「続きを読む」のようなリンクを付けたいことがあると思います。

特定の文字数で文章をカットしてくれるヘルパーがText::truncate()に用意されています。
今回はそれをアレンジして、「続きを読む」リンクを作成してみます。

cake/libs/views/helpers/text.php を app/views/helpers/text.php にコピーします。
そして、truncate メソッドを真似して、truncateJp メソッドを作成します(ほとんど truncate メッソドのままです)。

function truncateJp($text, $length = 100, $ending = '…', $endingOptions = array(), $exact = true, $considerHtml = false) {
	if (is_array($ending)) {
		extract($ending);
	}
	if ($considerHtml) {
		if (mb_strlen(preg_replace('/<.*?>/', '', $text)) <= $length) {
			return $text;
		}
		$totalLength = mb_strlen($ending);
		$openTags = array();
		$truncate = '';
		preg_match_all('/(<\\/?([\\w+]+)[^>]*>)?([^<>]*)/', $text, $tags, PREG_SET_ORDER);
		foreach ($tags as $tag) {
			if (preg_match('/img|br|input|hr|area|base|basefont|col|frame|isindex|link|meta|param/s', $tag[2])) {

			} else if (preg_match('/<[\\w]+[^>]*>/s', $tag[0])) {
				array_unshift($openTags, $tag[2]);
			} else if (preg_match('/<\\/([\\w]+)[^>]*>/s', $tag[0], $closeTag)) {
				$pos = array_search($closeTag[1], $openTags);
				if ($pos !== false) {
					array_splice($openTags, $pos, 1);
				}
			}
			$truncate .= $tag[1];

			$contentLength = mb_strlen(preg_replace('/&[0-9a-z]{2,8};|&#[0-9]{1,7};|&#x[0-9a-f]{1,6};/i', ' ', $tag[3]));
			if ($contentLength + $totalLength > $length) {
				$left = $length - $totalLength;
				$entitiesLength = 0;
				if (preg_match_all('/&[0-9a-z]{2,8};|&#[0-9]{1,7};|&#x[0-9a-f]{1,6};/i', $tag[3], $entities, PREG_OFFSET_CAPTURE)) {
					foreach ($entities[0] as $entity) {
						if ($entity[1] + 1 - $entitiesLength <= $left) {
							$left--;
							$entitiesLength += mb_strlen($entity[0]);
						} else {
							break;
						}
					}
				}

				$truncate .= mb_substr($tag[3], 0 , $left + $entitiesLength);
				break;
			} else {
				$truncate .= $tag[3];
				$totalLength += $contentLength;
			}
			if ($totalLength >= $length) {
				break;
			}
		}

	} else {
		if (mb_strlen($text) <= $length) {
			return $text;
		} else {
			$truncate = mb_substr($text, 0, $length - mb_strlen($ending));
		}
	}
	if (!$exact) {
		$spacepos = strrpos($truncate, ' ');
		if (isset($spacepos)) {
			if ($considerHtml) {
				$bits = mb_substr($truncate, $spacepos);
				preg_match_all('/<\\/([a-z]+)>/', $bits, $droppedTags, PREG_SET_ORDER);
				if (!empty($droppedTags)) {
					foreach ($droppedTags as $closingTag) {
						if (!in_array($closingTag[1], $openTags)) {
							array_unshift($openTags, $closingTag[1]);
						}
					}
				}
			}
			$truncate = mb_substr($truncate, 0, $spacepos);
		}
	}

    if (!empty($endingOptions)) {
        $Html = new HtmlHelper();
        $url = '';
        if (isset($endingOptions['url'])) {
            $url = $endingOptions['url'];
        }
        $option = array();
        if (isset($endingOptions['target'])) {
            $option['target'] = $endingOptions['target'];
        }
		$truncate .= '&nbsp;' . $Html->link($ending, $url, $option);
    } else {
		$truncate .= $ending;
    }

	if ($considerHtml) {
		foreach ($openTags as $tag) {
			$truncate .= '</'.$tag.'>';
		}
	}

	return $truncate;
}


そして、View に下記のように書きます。

<?php e($text->truncateJp($value, 200, '続きを読む', array('url' => $url, 'target' => '_blank'))); ?>

これで「続きを読む」にリンクが張られた状態で表示できます。

truncateJp のオプション説明
第1引数:文章
第2引数:表示させたい全角文字数 - 1
第3引数:「続きを読む」のような文字
第4引数(array):url=>URL、target=>ターゲット先





関連記事


    この記事へのトラックバック アドレス

    コメント, トラックバック:

    この投稿への コメント/トラックバック はまだありません...

    コメントを残す:

    頂いたメールアドレスはこのサイト上には表示されません
    頂いたURLは表示されます。

    許可される XHTML タグ: <p, ul, ol, li, dl, dt, dd, address, blockquote, ins, del, span, bdo, br, em, strong, dfn, code, samp, kdb, var, cite, abbr, acronym, q, sub, sup, tt, i, b, big, small>
    (改行が自動で <br /> になります)
    (名前、メールアドレス、URLを記憶する Cookie を発行します)
    (ユーザがメッセージ・フォームを通してあなたに連絡することを許可します (あなたのメール・アドレスは表示されません))

    プロフィール
    愛知県名古屋市在住のあつ@株式会社一六社(いちろくしゃ)スタッフ

    あつへのメッセージはSkypeを使ってテキストメッセージでどうぞ
    あつ

    CakePHPに関する情報をまとめていきます。

    開発スピードがアップできればうれしいです。

    >>連絡はこちらへどうぞ


    CakePHP関連のブックマーク


    CakePHP最新版
    CakePHP 1.2.3.8166


    CakePHPの書籍

    CakePHPによる実践Webアプリケーション開発

    CakePHP1.2で作成する人にオススメ。
    とても参考になります。

    まるごとPHP!(vol.2)

    安藤さんの解説が載っています。
    AmazonのPagination部分は参考になります。

    CakePHPによるWebアプリケーション開発

    まだ読んだことありません

    CakePHPポケットリファレンス
    CakePHPポケットリファレンス
    CakePHP1.2 でやるなら、これがあると何かと便利♪

    CakePHP徹底入門
    CakePHP徹底入門
    CakePHP1.2 を今から始めるならここから

    Fast CakePHP
    Fast CakePHP
    シンプルでわかりやすい CakePHP の入門書

    CakePHPガイドブック
    CakePHPガイドブック
    CakePHP1.1 ではとても参考にした CakePHP 最初の入門書

    アーカイブ

     RSS2.0

    powered by
    b2evolution
    ブログ一六社

    Geo Visitors Map