大家好,我是 Eric。
昨天介紹了自訂迴圈的作法,並透過 header.php 範本檔製作首頁頁首的投影片輪播。今天,我們再來進一步透過短代碼 (shortcode) 的機制,讓我們可以在區塊編輯器中,更有彈性的加入我們想要想要使用的程式碼片段,甚至直接擴展既有外掛、佈景主題的功能。
短代碼在 WordPress 區塊編輯器中通常會以 [短代碼]
或是 [短代碼 參數1=值1 參數2=值2]
的方式呈現,如果安裝官方的 Jetpack 外掛,便可以透過 [portfolio]
來呈現作品集,或是透過 [testimonial]
來呈現使用者證言。
除了 Jetpack 以外,我們常見的頁面編輯器,如 Elementor,或是 WordPress 的進階搜尋外掛 Ivory Search ,都會在設定完後,產生一組短代碼,讓使用者可以任意貼在頁面,藉此產生相對應的內容。也因為他們是透過短代碼來產生內容,因此我們也可以藉由短代碼,字型擴充這些外掛的功能。
首先,定義短代碼的基本語法如下:
add_shortcode( 'myshortcode', 'eric_the_shortcode' );
function eric_the_shortcode( $atts ) {
$a = shortcode_atts( array(
'引數 1' => '引數預設值',
'引數 2' => '引數預設值',
),
$atts );
/* 定義回傳的初始值 */
$output = '';
/* 接下來可以用 $a 來組合要用的字串 */
$output .= '<a href="' . $a['引數 1'] . '">';
$output .= $a['引數 2'] . '</a>';
/* 最後要將組合後的字串回傳 */
return $output;
}
接著只要透過 [myshortcode]
,就會在頁面回傳一個連結元素 <a href="引數 1">引數 2</a>
。
我們延續昨天的範例,讓我們可以在頁面的任何區塊,或是在小工具中,插入自訂的投影片輪播。關於自訂內容類型與自訂欄位的設定,可以直接延續昨天的設定,但我們就不需要將迴圈放入 header.php 中。
/**
* 定義自訂投影片輪播的短代碼。
*
* @param string $atts 從短代碼回傳的引數。
*/
function custom_slider( $atts ) {
$a = shortcode_atts( array(
'slides' => 3, //顯示投影片的張數
'exclude' => '', //排除投影片 ID,以逗點區隔
'include' => '', //包含投影片 ID,以逗點區隔
'size' => 'full', //投影片使用的圖片大小
),
$atts );
/* 將短代碼的引數轉換為自訂迴圈的引數 */
$args = array(
'post_type' => 'slide',
'posts_per_page' => $a['slides'],
'post__in' => explode( ',', $a['include'] ),
'post__not_in' => explode( ',', $a['exclude'] ),
);
$slides = new WP_Query( $args );
$output = '';
if ( $slides -> have_posts() ) {
$output .= '<div class="slick-slider" id="custom-slider">';
while ( $slides -> have_posts() ) {
$slides -> the_post();
$output .= '<div id="slide-' . get_the_ID() . '">';
$output .= '<a href="' . get_field( 'url' ) . '" target="_self">';
$output .= get_the_post_thumbnail( get_the_ID(), $a['size'] );
$output .= '</a>';
$output .= '</div>';
}
$output .= '</div>';
}
wp_reset_postdata();
return $output;
}
add_shortcode( 'slider', 'custom_slider' );
接著,只要在區塊編輯器加入短代碼區塊,或是直接在文章中插入短代碼 [slider]
,便會在任何你想要的位置插入上述的 HTML 元素。此外,也可以透過 [slider slides=4]
來自訂想要加入的投影片數量。
我們以 Content Blocks 這款外掛為例,原本的外掛是透過短代碼的方式,將頁面的物件模組化,集中在 Content Block 這個自訂類型中進行管理,可以說是區塊編輯器「可重複使用區塊」的前身。
原本 Content Blocks 可接受的引數如下所示:
/* post-widget.php Line 172 */
shortcode_atts( array(
'id' => '',
'slug' => '',
'class' => 'content_block',
'suppress_content_filters' => 'no',
'featured_image' => 'no',
'featured_image_size' => 'medium',
'title' => 'no',
'title_tag' => 'h3',
'markup' => 'div'
), $atts ) );
今天我們想要結合頁面捲動動畫 (animation on scroll) 的功能,必須要加上 data-aos
的屬性,因此必須要擴展這個外掛的引數。我們可以先複製 Content Blocks 這款外掛的原始碼,透過編輯子佈景主題的 functions.php 或 Code Snippets 來做以下的改編。
/**
* 擴展 content_block 短代碼。
* 按照 WordPress 的 PHP 編碼標準,我們把原本的 extract 作法改掉。
*/
add_shortcode( 'content_block_ext', 'custom_post_widget_shortcode' );
function custom_post_widget_shortcode( $atts ) {
$a = shortcode_atts( array(
'id' => '',
'slug' => '',
'class' => 'content_block',
'suppress_content_filters' => 'no',
'featured_image' => 'no',
'featured_image_size' => 'medium',
'title' => 'no',
'title_tag' => 'h3',
'markup' => 'div',
'aos' => '',
), $atts );
if ( $a['slug'] ) {
$block = get_page_by_path( $a['slug'], OBJECT, 'content_block' );
if ( $block ) {
$a['id'] = $block->ID;
}
}
$content = '';
if( $a['id'] != '' ) {
$args = array(
'post__in' => array( $a['id'] ),
'post_type' => 'content_block',
);
$content_post = get_posts( $args );
foreach( $content_post as $post ) {
/* 這邊幫最外圍的元素加上 data-aos 的資料屬性。 */
$aos_attr = ''
if ( $a['aos'] !== '' ) {
$aos_attr = ' data-aos="' . $a['aos'] . '"';
}
$content .= '<' . esc_attr( $a['markup'] ) . ' class="'. esc_attr( $a['class'] ) .'" id="custom_post_widget-' . $a['id'] . '"' . $aos_attr . '>';
/* 以上是主要的修改部分。 */
if ( $a['title'] === 'yes' ) {
$content .= '<' . esc_attr( $a['title_tag'] ) . '>' . $post -> post_title . '</' . esc_attr( $a['title_tag'] ) . '>';
}
if ( $a['featured_image'] === 'yes' ) {
$content .= get_the_post_thumbnail( $post -> ID, $a['featured_image_size'] );
}
if ( $a['suppress_content_filters'] === 'no' ) {
$content .= apply_filters( 'the_content', $post -> post_content );
} else {
$content .= $post -> post_content;
}
$content .= '</' . esc_attr( $a['markup'] ) . '>';
}
}
return $content;
}
接著,我們便可以複製 Content Blocks 在後台顯示的短代碼,並在需要加入動畫的時候,將短代碼從原本的 [content_block ...]
改為 [content_block_ext ...]
就可以了。
透過短代碼,我們可以大幅的提高 WordPress 客製化的彈性。前面舉的兩個例子,其中一個是自行建立想要包裝的短代碼,後者則是奠基於外掛的短代碼,再進一步客製化。透過這種作法,只要你熟悉了特定的外掛或佈景主題後,便能夠自己根據該外掛或佈景主題進行延伸。
下一章,我們一樣將結合前面所提到的各種工具,來針對 Contact Form 7 的功能進行擴展。
【第 09 天】WordPress 的 Shortcode
Shortcodes