« チェックボックスの作り方多階層でアソシエーションデータを取得する方法 »

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

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

パーマリンク 2008/12/13 13:06:55 著者: cakephp メール
カテゴリ: ヘルパー, ビュー

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(右クリックでURLのコピーをしてください)

モデレーション待ちのフィードバック

この投稿にはモデレーション待ちのフィードバックが 18 件あります....

コメントを残す


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

頂いたURLは表示されます。
(改行が自動で <br /> になります)
(Name, email & website)
(ユーザに、メッセージ・フォームを通じた連絡を許可します (あなたのメール・アドレスは表示されません))
2017年12月
 << <   > >>
          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
31            

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 最初の入門書

検索

XMLフィード

16ブログ     powered by b2evolution