Bài viết này giới thiệu cấu trúc của một Theme WordPress căn bản. Chúng ta sẽ chuyển Clean Blog có được ở các bài viết trước của series này thành một Theme Wordpress.

Cấu trúc một Theme WordPress căn bản

Giới thiệu

Ở bài viết trước, chúng ta đã có được HTML Template Clean Blog và cài thành công WordPress vào localhost. Bây giờ, vào đường dẫn C:\XAMPP\htdocs\cleanblog\wp-content\themes, tạo một thư mục có tên init_cleanblog, với cấu trúc như sau.

init_cleanblog/
├── img/
│   ├── default-bg.jpg
│   ├── favicon.ico
│   ├── home-bg.jpg
├── includes/
│   ├── loop.php
│   ├── remove-dashboard-items.php
│   ├── theme-options.php
├── 404.php
├── archive.php
├── author.php
├── category.php
├── footer.php
├── functions.php
├── header.php
├── index.php
├── page.php
├── screenshot.jpg
├── search.php
├── single.php
├── style.css
├── template-contact.php

Các bài viết cần tham khảo và thư mục img:

Các tập tin mặc định

Nội dung của remove-dashboard-items.php:

<?php
/**
 * Remove Menu Page
 */
function init_remove_menu_pages() {
    remove_menu_page('tools.php');
    #remove_menu_page('plugins.php');
    #remove_menu_page('edit-comments.php');
    remove_submenu_page('index.php', 'update-core.php');
    #remove_submenu_page('themes.php', 'customize.php');
    #remove_submenu_page('themes.php', 'widgets.php');
}
add_action('admin_menu', 'init_remove_menu_pages');

/**
 * Disable Auto-Saving
 */
function init_disable_autosave(){
    wp_deregister_script('autosave');
}
add_action('wp_print_scripts', 'init_disable_autosave');

/**
 * Remove Editor From Admin Appearance Menu
 */
function init_remove_the_editor() {
    remove_action('admin_menu', '_add_themes_utility_last', 101);
}
add_action('_admin_menu', 'init_remove_the_editor', 1);

/**
 * Hide Help Tabs
 */
function init_remove_help_tabs() {
    $screen = get_current_screen();
    $screen->remove_help_tabs();
}
add_action('admin_head', 'init_remove_help_tabs');

/**
 * Remove menu tabs from the top toolbar
 */
function init_config_admin_bar() {
    //call the global adminbar var
    global $wp_admin_bar;
    // hide the WP logo
    $wp_admin_bar->remove_menu('wp-logo');
    // hide link to the dashboard
    //$wp_admin_bar->remove_menu('dashboard');
    //hide links to WP
    //$wp_admin_bar->remove_menu('about');
    $wp_admin_bar->remove_menu('wporg');
    $wp_admin_bar->remove_menu('documentation');
    $wp_admin_bar->remove_menu('support-forums');
    $wp_admin_bar->remove_menu('feedback');
}
add_action('wp_before_admin_bar_render', 'init_config_admin_bar');

/**
 * Hook for wp-admin logo
 */
function init_login_logo_url() {
    return get_bloginfo('url');
}
add_filter('login_headerurl', 'init_login_logo_url');

function init_login_logo_url_title() {
    return get_bloginfo('name');
}
add_filter('login_headertitle', 'init_login_logo_url_title');

Nội dung của functions.php:

<?php
/**
 * Functions
 * @package INITHTML
 * @author A Hòe <[email protected]>
 */
include_once('includes/remove-dashboard-items.php');
include_once('includes/theme-options.php');

/**
 * Automatically move JavaScript code to page footer, speeding up page loading time.
 */
function remove_head_scripts() {
   remove_action('wp_head', 'wp_print_scripts');
   remove_action('wp_head', 'wp_print_head_scripts', 9);
   remove_action('wp_head', 'wp_enqueue_scripts', 1);
 
   add_action('wp_footer', 'wp_print_scripts', 5);
   add_action('wp_footer', 'wp_enqueue_scripts', 5);
   add_action('wp_footer', 'wp_print_head_scripts', 5);
}
add_action('wp_enqueue_scripts', 'remove_head_scripts');

function disable_emojicons_tinymce($plugins) {
  if (is_array($plugins)) {
    return array_diff($plugins, array('wpemoji'));
  } else {
    return array();
  }
}

function disable_wp_emojicons() {
  remove_action('admin_print_styles', 'print_emoji_styles');
  remove_action('wp_head', 'print_emoji_detection_script', 7);
  remove_action('admin_print_scripts', 'print_emoji_detection_script');
  remove_action('wp_print_styles', 'print_emoji_styles');
  remove_filter('wp_mail', 'wp_staticize_emoji_for_email');
  remove_filter('the_content_feed', 'wp_staticize_emoji');
  remove_filter('comment_text_rss', 'wp_staticize_emoji');
  add_filter('tiny_mce_plugins', 'disable_emojicons_tinymce');
}
add_action('init', 'disable_wp_emojicons');

function modify_jquery() {
    if (!is_admin()) {
        wp_deregister_script('jquery');
        wp_register_script('jquery', 'https://ajax.googleapis.com/ajax/libs/jquery/1.12.4/jquery.min.js', false, '1.12.4');
        wp_enqueue_script('jquery');
    }
}
add_action('init', 'modify_jquery');

/**
 * Setup Images Size
 */
function init_imagesize() {
    add_theme_support('post-thumbnails');
    add_theme_support('automatic-feed-links');
    add_theme_support('title-tag');
}
add_action('after_setup_theme', 'init_imagesize');

/**
 * Menu Locations
 */
if (function_exists('wp_nav_menu')) {
    function init_wp_my_menus() {
        register_nav_menus(array(
            'main-menu' => __('Main menu')
        ));
    }
    add_action('init', 'init_wp_my_menus');
}

/*
 * Search only by title
 */
function search_by_title_only($search, &$wp_query)
{
    global $wpdb;
    if(empty($search)) {
        return $search; // skip processing - no search term in query
    }
    $q = $wp_query->query_vars;
    $n = !empty($q['exact']) ? '' : '%';
    $search =
    $searchand = '';
    foreach ((array)$q['search_terms'] as $term) {
        $term = esc_sql($wpdb->esc_like($term));
        $search .= "{$searchand}($wpdb->posts.post_title LIKE '{$n}{$term}{$n}')";
        $searchand = ' AND ';
    }
    if (!empty($search)) {
        $search = " AND ({$search}) ";
        if (!is_user_logged_in())
            $search .= " AND ($wpdb->posts.post_password = '') ";
    }
    return $search;
}
add_filter('posts_search', 'search_by_title_only', 500, 2);

/**
 * Pagination
 */
function pagination($pages = '') {
    global $paged;
    if(empty($paged)) $paged = 1;
    if($pages == '') {
        global $wp_query;
        $pages = $wp_query->max_num_pages;
        if(!$pages) {
             $pages = 1;
        }
    }
    if(1 != $pages) {
        echo '<ul class="pager">';
        if ($paged > 1) {
            echo '<li class="previous"><a href="' . get_pagenum_link($paged - 1) . '"><span aria-hidden="true">←</span> Trước</a></li>';
        }
        if ($paged < $pages) {
            echo '<li class="next"><a href="' . get_pagenum_link($paged + 1) . '">Sau <span aria-hidden="true">→</span></a></li>';
        }
        echo '</ul>';
    }
}

Nội dung của style.css:

/*
Theme Name: Init HTML Clean Blog
Author: A Hòe <[email protected]>
Author URI: https://www.itithtml.com/
Description: The Init HTML Clean Blog Blog theme.
Version: 1.0
License: GNU General Public License
Tags: blog, sidebar
*/

/* Cơ bản */
    
body {
    font-family: "Roboto", "Helvetica Neue", Helvetica, Arial, sans-serif;
    font-size: 20px;
    line-height: 1.5;
}

h1, h2, h3, h4, h5, h6 {
    margin-top: 0;
}

a {
    color: #333;
}

p a {
    text-decoration: underline;
}

a:focus, a:hover {
    color: #0085a1;
}

img {
    max-width: 100%;
    height: auto;
}

/* Nav */

.navbar-custom {
    background: none;
    border: none;
}

.navbar-custom .nav li a {
    color: #fff;
    font-size: 12px;
    font-weight: 800;
    text-transform: uppercase;
    padding: 20px;
}

.navbar-default .navbar-brand {
    color: #fff;
    font-size: 18px;
    font-weight: 800;
}

.navbar-custom .nav li.active a,
.navbar-custom .nav li.current-menu-item a{
    background: none;
    color: rgba(255, 255, 255, 0.8);
}

.navbar-custom .nav li a:hover, .navbar-custom .nav li a:focus,
.navbar-custom .nav li.active a:hover, .navbar-custom .nav li.active a:focus,
.navbar-default .navbar-brand:hover, .navbar-default .navbar-brand:focus {
    color: rgba(255, 255, 255, 0.8);
    background: none;
}

/* Header trang chủ */

.intro-header {
    background: center center no-repeat;
    background-attachment: scroll;
    background-size: cover;
    margin-bottom: 50px;
}

.index-header {
    background-image: url(img/home-bg.jpg);
}

.site-heading {
    padding: 80px 0 150px;
    color: #fff;
}

.intro-header .site-heading h1 {
    font-size: 80px;
    font-weight: 800;
}

@media (max-width: 991px) {
    .intro-header .site-heading h1 {
        font-size: 50px;
    }
}

hr.small {
    max-width: 100px;
    margin: 15px auto;
    border-width: 4px;
    border-color: #fff;
}

.intro-header .site-heading .sub-heading {
    font-size: 24px;
    line-height: 1.1;
    display: block;
    font-weight: 300;
    margin: 10px 0 0;
}

/* Danh sách bài viết */

.post-preview a .post-title {
    font-size: 36px;
    margin-top: 30px;
    margin-bottom: 10px;
    font-weight: 800;
}

@media (max-width: 991px) {
    .post-preview a .post-title {
        font-size: 30px;
    }
}

.post-preview a:focus, .post-preview a:hover {
    text-decoration: none;
}

.post-preview a .post-subtitle {
    margin: 0 0 10px;
    font-weight: 300;
}

.post-preview .post-meta {
    color: #777;
    font-size: 18px;
    font-style: italic;
    margin-top: 0;
}

.post-preview .post-meta a {
    text-decoration: none;
}

.container .post-preview:last-child hr {
    display: none;
}

.pager li a {
    text-transform: uppercase;
    font-weight: 800;
    letter-spacing: 1px;
    font-size: 14px;
    padding: 13px 20px;
    border-radius: 0;
}

.pager li a:focus, .pager li a:hover {
    color: #fff;
    background-color: #0085a1;
    border: 1px solid #0085a1;
}

/* Footer */

footer {
    padding: 50px 0 65px;
}

.copyright {
    font-size: 16px;
    margin-bottom: 0;
    margin-top: 30px;
}

/* Trang bài viết */

.intro-header .post-heading h1 {
    font-size: 55px;
}

@media (max-width: 991px) {
    .intro-header .post-heading h1 {
        font-size: 35px;
    }
}

.intro-header .post-heading .sub-heading {
    font-size: 24px;
    margin: 10px 0 30px;
    font-weight: 400;
}

.intro-header .post-heading .meta {
    font-style: italic;
    font-weight: 300;
}

.intro-header .post-heading .meta a {
    color: #fff;
}

p {
    margin: 30px 0;
}

blockquote {
    color: #777;
    font-style: italic;
}

.section-heading {
  font-size: 36px;
  margin-top: 60px;
  font-weight: 700;
}

.caption {
  text-align: center;
  font-size: 14px;
  padding: 10px;
  font-style: italic;
  margin: 0;
  display: block;
  border-bottom-right-radius: 5px;
  border-bottom-left-radius: 5px;
}

.comments-container {}

/* Trang liên hệ */

.floating-label-form-group {
    font-size: 14px;
    position: relative;
    margin-bottom: 0;
    padding-bottom: 0.5em;
    border-bottom: 1px solid #eeeeee;
}

.floating-label-form-group input, .floating-label-form-group textarea {
    z-index: 1;
    position: relative;
    padding-right: 0;
    padding-left: 0;
    border: none;
    border-radius: 0;
    font-size: 1.5em;
    background: none;
    box-shadow: none !important;
    resize: none;
}

.floating-label-form-group label {
    display: block;
    z-index: 0;
    position: relative;
    top: 2em;
    margin: 0;
    font-size: 0.85em;
    line-height: 1.764705882em;
    vertical-align: middle;
    vertical-align: baseline;
    opacity: 0;
    -webkit-transition: top 0.3s ease, opacity 0.3s ease;
    -moz-transition: top 0.3s ease, opacity 0.3s ease;
    -ms-transition: top 0.3s ease, opacity 0.3s ease;
    transition: top 0.3s ease, opacity 0.3s ease;
}

.floating-label-form-group::not(:first-child) {
    padding-left: 14px;
    border-left: 1px solid #eeeeee;
}

.floating-label-form-group-with-value label {
    top: 0;
    opacity: 1;
}

.floating-label-form-group-with-focus label {
    color: #0085a1;
}

form .row:first-child .floating-label-form-group {
    border-top: 1px solid #eeeeee;
}

.btn {
    text-transform: uppercase;
    font-size: 14px;
    font-weight: 800;
    letter-spacing: 1px;
    border-radius: 0;
    padding: 15px 25px;
}

.btn-lg {
    font-size: 16px;
    padding: 25px 35px;
}

.btn-default:hover, .btn-default:focus {
    background-color: #0085a1;
    border: 1px solid #0085a1;
    color: #fff;
}

Đây là tập tin main.css của Clean Blog. Các tập tin chưa được giới thiệu các bạn tạm thời để trống.

Bây giờ, các bạn có thể vào http://localhost/cleanblog/wp-admin/, đến phần Giao diện để kích hoạt giao diện Init HTML Clean Blog vừa tạo. Lưu ý đây chỉ là giao diện rỗng, chúng ta sẽ tiếp tục ở các bài viết sau.

Giao diện Clean Blog