wordpress全站PJAX系列教程 - wordpress開發(fā)

    wordpress全站PJAX系列文章聚合,推薦去原文的評(píng)論區(qū)看看,肯定收獲不少

    很多人喜歡Pjax 的魅力,我收集了一個(gè)博客的教程,將他們整合到一起。

    這里只做備份用,很推薦去原文看看,尤其是評(píng)論區(qū),說不定會(huì)有意想不到的收獲。

    此系列文章更新于2015年2月

    第一部分

    教程寫給自己的,所以日后可能有補(bǔ)充。首先這個(gè)pjax的代碼有好幾部分,來自網(wǎng)絡(luò)不同作者,經(jīng)過本人封裝,教程就是按這幾個(gè)部分來進(jìn)行的。這是第一部分,我把自己理解的大致原理說一下,pjax是 pushstate + ajax,分別百度可以得到相關(guān)資料,在此就不贅述了。

    Ajax

    ajax直白的理解就是請(qǐng)求一個(gè)鏈接所指向的頁面的其中一部分來替換當(dāng)前頁面的一部分,比如我用的wordpress,典型的博客頁面,有頁面頭部、主體部分、側(cè)欄部分、頁面底部四個(gè)主要部分。
    ajax請(qǐng)求的過程是如何的呢?比如我現(xiàn)在打開的是頁面A頁面A中有一個(gè)a標(biāo)簽,正常情況下點(diǎn)擊a標(biāo)簽的鏈接會(huì)打開一個(gè)頁面B,那么整個(gè)頁面A就會(huì)被替換成頁面B。然而,頁面A和頁面B有些結(jié)構(gòu)是完全一樣的,比如頭部,底部,甚至是側(cè)欄,其實(shí)要替換的僅僅是主體部分而已,ajax就提供了這樣一個(gè)功能,它控制你在點(diǎn)擊a標(biāo)簽的鏈接時(shí),只抓取頁面B的主體部分來替換頁面A的主體部分,而頭部、底部、側(cè)欄不用替換(也就不用刷新)。

    PushState

    以上是最直白的理解,而pushstate則是干嘛的?HTML5里引用了新的API,history.pushState和history.replaceState,就是通過這個(gè)接口做到無刷新改變頁面URL的。因?yàn)橛胊jax替換局部頁面時(shí),瀏覽器的地址是不會(huì)改變的,你替換為頁面B的主體,地址欄的url還是頁面A的,而且點(diǎn)擊瀏覽器的后退或前進(jìn)按鈕地址欄url也是不會(huì)改變的,pushstate的作用則用來改變地址欄url的狀態(tài)。

    那么PJAX就是以上兩者的結(jié)合。
    開始我們必須對(duì) 被請(qǐng)求的頁面進(jìn)行請(qǐng)求前的處理,這個(gè)處理非常重要,如果把被請(qǐng)求的頁面想象成一張圖片,那么這個(gè)處理就相當(dāng)于對(duì)圖片進(jìn)行剪裁,沒有處理之前,被請(qǐng)求的頁面B是完整的,請(qǐng)求過來就首先要預(yù)讀取一邊頁面B,而其實(shí)我們不必要將整個(gè)頁面都讀取,我們只需要讀取主體部分,所以我們可以把頭部、側(cè)欄和底部都先剪掉,只剩下主體部分,然后再請(qǐng)求過來替換頁面A中的主體部分。
    這個(gè)剪裁的方法如下:
    在對(duì)應(yīng)的php頁面進(jìn)行

    <?php if( $_GET['ajx'] != 'container' ) { ?>
    
    //被剪裁掉的部分,比如:
    //<?php  get_header(); ?>
    //<?php get_sidebar(); ?>
    //<?php get_footer(); ?>
    
    <?php } ?>

    這個(gè)方法非常重要,包括評(píng)論分頁也需要這樣的處理,對(duì)pjax的速度是一大影響。了解了這個(gè)其實(shí)剩下的只需要把剩下的代碼超過去就可以了。當(dāng)然,你不剪裁也是可以的,那也可以替換,但那就不算是真正的ajax了。目前大多數(shù)pjax的代碼都不會(huì)有這樣的處理。下面一篇是pjax的核心代碼以及一些說明。

    第二部分

    原文來源: http://www.inlojv.com/4967.html

    處理過程

    上篇我們提到了“剪裁”,本篇我們先來實(shí)際體驗(yàn)一下被剪裁掉的頁面是如何的,這方便我們對(duì)接下來的頁面請(qǐng)求過程有一個(gè)感性的認(rèn)識(shí)。
    假設(shè)我的index.php首頁是這個(gè)結(jié)構(gòu):頭部、主題、側(cè)欄、底部 四大結(jié)構(gòu)組成。

    <?php  get_header(); ?>
    
    <div id="container">
    </div>
    
    <?php get_sidebar(); ?>
    
    <?php get_footer(); ?>

    現(xiàn)在我先把頭部剪掉

    <?php if( $_GET['ajx'] != 'container' ) { ?>
    <?php  get_header(); ?>
    <?php } ?>
    
    <div id="container">
    </div>
    
    <?php get_sidebar(); ?>
    
    <?php get_footer(); ?>

    可以看到我用第一篇中所說的代碼將頭部包住了,這意味著我把頭部剪掉了。
    原本首頁是?http://127.0.0.1/?,現(xiàn)在我們以這樣的鏈接形式來訪問首頁?http://127.0.0.1/?ajx=container
    打開這個(gè)鏈接你會(huì)發(fā)現(xiàn),首頁的頭部不見了,由于頭部加載了css,你首頁的樣式也會(huì)消失,這個(gè)狀態(tài)就是我們想要ajax請(qǐng)求的,我們不需要頭部,把它給剪掉了,接著我們可以用同樣的方法剪掉側(cè)欄和底部,最后就會(huì)只剩下主體部分,如下:

    <?php if( $_GET['ajx'] != 'container' ) { ?>
    <?php  get_header(); ?>
    <?php } ?>
    
    <div id="container">
    </div>
    
    <?php if( $_GET['ajx'] != 'container' ) { ?>
    <?php get_sidebar(); ?>
    <?php } ?>
    
    <?php if( $_GET['ajx'] != 'container' ) { ?>
    <?php get_footer(); ?>
    <?php } ?>

    這就是真正需要ajax請(qǐng)求的頁面了。
    我們需要把http://127.0.0.1/?ajx=container?這樣的鏈接傳遞給ajax方法進(jìn)行異步請(qǐng)求,
    比如在頁面A?http://127.0.0.1/page-a?中要請(qǐng)求頁面B,頁面A中的a標(biāo)簽中指向頁面B的鏈接就應(yīng)該是這樣的?http://127.0.0.1/page-b?ajx=container?,
    利用兩個(gè)js函數(shù)來對(duì)點(diǎn)擊的鏈接進(jìn)行處理,加上后面的?=ajx=container參數(shù),在必要的時(shí)候后再去掉它們。

    完整的PJAX代碼

    var ajx_content = "#ajx_content";
    
    function rerun() {}
    
    $(function() {
        rerun();
        a();
    });
    
    function show_loading(e) {
        if ($("#loading_box").length == 0) {
            var div = "<div id='loading_box'></div><div id='loading'></div><div id='loading-text'></div></div>";
        }
        if (e === true) {
            $("body").append(div);
        } else {
            $("#loading_box,#loading,#loading-text").fadeOut(400, function() {
                $(this).remove();
            });
        }
    }
    
    function body_am(id) {
        id = isNaN(id) ? $("#" + id).offset().top : id;
        $("body,html").animate({
            scrollTop: id
        }, 600);
        return false;
    }
    
    function pluginRerun() {
        var plugin_scripts = $('script[src*="plugins"]');
        plugin_scripts.each(function() {
            var url = $(this).attr("src");
            $.getScript(url);
        });
    }
    
    function addUrlPara(url, para) {
        var strArray = new Array();
        strArray = url.split("?");
        if (strArray.length == 1) {
            if (url.indexOf("#") != -1) {
                strArray = url.split("#");
                return strArray[0] + "?" + para + "#" + strArray[1];
            }
            return url + "?" + para;
        } else {
            if (url.indexOf(para) != -1) return url;
            return strArray[0] + "?" + para + "&" + strArray[1];
        }
    }
    
    function removeUrlPara(url, para) {
        var strArray = new Array();
        strArray = url.split(para);
        if (strArray.length == 1) {
            strArray = url.split("?" + para);
            return strArray[0];
        } else {
            if (strArray[1].indexOf("&") != -1) {
                strArray = url.split(para + "&");
                return strArray[0] + strArray[1];
            } else {
                strArray = url.split("?" + para);
                return strArray[0] + strArray[1];
            }
        }
    }
    
    function l() {
        history.replaceState({
            url: window.document.location.href,
            title: window.document.title,
            html: $(document).find(ajx_content).html()
        }, window.document.title, document.location.href);
    }
    
    function a() {
        window.addEventListener("popstate", function(e) {
            if (e.state) {
                document.title = e.state.title;
                $(ajx_content).html(e.state.html);
                rerun();
            }
        });
    }
    
    function ajax(reqUrl, msg, data) {
        if (msg == "pagelink" || msg == "search") {
            show_loading(true);
            $(ajx_content).fadeTo("normal", 0);
            $("body,html").animate({
                scrollTop: $("body").offset().top
            }, 810);
            var paraUrl = addUrlPara(reqUrl, "ajx=container");
        } else if (msg == "comtpagenav") {
            to_anchor("#post-comment-list", 0);
            $("#comment_list").fadeTo(500, .2, function() {
                $("#comment_list").css("position", "relative");
            });
            reqUrl = removeUrlPara(reqUrl, "ajx=container");
            paraUrl = addUrlPara(reqUrl, "ajx=comts");
        }
        $.ajax({
            url: paraUrl,
            data: data,
            beforeSend: function() {
                l();
            },
            success: function(data) {
                if (msg == "pagelink" || msg == "search") {
                    $(ajx_content).replaceWith($(data).filter(ajx_content));
                    $(ajx_content).fadeTo(500, 1, function() {
                        rerun();
                    });
                    show_loading(false);
                } else if (msg == "comtpagenav") {
                    var content = $(data).find("#comment_list").html();
                    $("#comment_list").animate({
                        opacity: 0,
                        top: 35
                    }, 200, function() {
                        $("#comment_list").html(content);
                        $("#comment_list").animate({
                            opacity: 1,
                            top: 0
                        }, 400, function() {
                            $("#comment_list").css("position", "inherit");
                        });
                        rerun();
                    });
                }
                document.title = $(data).filter("title").text();
                reqUrl = removeUrlPara(reqUrl, "ajx=comts");
                var state = {
                    url: reqUrl,
                    title: $(data).filter("title").text(),
                    html: $(data).filter(ajx_content).html()
                };
                window.history.pushState(state, $(data).filter("title").text(), reqUrl);
            },
            complete: function() {},
            timeout: 5e3,
            error: function(request) {
                if (msg == msg == "pagelink" || msg == "search") {
                    show_loading(false);
                    location.href = reqUrl;
                } else if (msg == "comtpagenav") {
                    $("#comment_list").fadeTo("normal", 1);
                    $("#comt_svg").css("display", "none");
                    $("#comments_paginate").css("display", "block");
                } else {
                    location.href = reqUrl;
                }
            }
        });
    }
    
    function check_x(url) {
        var url_string = new String("  , comment-page-, #respond, #comment, javascript:, oauth2, .jpg, .gif, .png");
        var url_x = url_string.split(", ");
        for (var i in url_x) {
            if (url.indexOf(url_x[i]) >= 0) {
                return true;
            }
        }
        return false;
    }
    
    
    $("body").on("click", "a[target!=_blank]:not(.noajx)", function() {
        url = $(this).attr("href");
        if (check_x(url) == true) return;
        ajax(url, "pagelink");
        return false;
    });
    
    
    $("body").on("submit", "#search .s-form", function() {
        ajax(this.action + '?=' + $(this).find("#s").val(), 'search', $(this).serialize());
        return false;
    });
    
    $("body").on("click", "#comments_paginate a", function() {
        ajax($(this).attr("href"), "comtpagenav");
        return false;
    });

    核心就是ajax(reqUrl, msg, data)函數(shù)了,還有兩個(gè)函數(shù)需要說明一下
    1、check_x(url)函數(shù) —— 這是檢查a標(biāo)簽的鏈接中是否有需要排除的字符,有時(shí)候某些a標(biāo)簽是不需要ajax請(qǐng)求的,比如/wp-login.php,圖片鏈接帶有.jpg、.gif、.png 等等,都不需要ajax請(qǐng)求,我們得把它們排除掉,加入到check_x(url)內(nèi)的排除列表內(nèi)。

    2、rerun()函數(shù) —— 這個(gè)函數(shù)方便我們對(duì)其他js腳本進(jìn)行重新加載,相當(dāng)于一個(gè)回調(diào)函數(shù),比如有的站用了多說評(píng)論系統(tǒng),ajax請(qǐng)求時(shí)是不會(huì)請(qǐng)求css和js的,只抓取html結(jié)構(gòu),所以ajax加載后多說需要的js就不會(huì)一起加過來,這時(shí)候就需要把多說的js放進(jìn)rerun()函數(shù)進(jìn)行重新加載。


    好了,PJAX教程就介紹到這里,適合有一定js基礎(chǔ)的朋友看,如果連js都不懂,那只能靠百度了。

    第三部分

    原文來源: http://www.inlojv.com/5011.html

    全站pjax教程一和二已經(jīng)將重點(diǎn)與核心代碼呈現(xiàn)過了,還有一些執(zhí)行上的問題在此補(bǔ)充一下

    1、并不是所有的pjax代碼都相同?

    網(wǎng)上有很多所謂的全站ajax代碼,其實(shí)僅僅是頁面ajax,全站還要兼顧很多東西,搜索、評(píng)論、重載回調(diào)等等,另外有一些pushstate的使用也不相同,有的pjax后退是沒有緩存的,這樣這些代碼的前進(jìn)和后退,就會(huì)重新請(qǐng)求一次push進(jìn)去的歷史鏈接,所以你會(huì)發(fā)現(xiàn)有的后退是重新執(zhí)行一遍代碼會(huì)有l(wèi)oading效果,而有的不是,是很干脆地切換回去。教程[二]提供的代碼屬于后者。

    2、ajax替換頁面容器所用的函數(shù)不同

    比如教程[二]中ajax執(zhí)行成功后有這么一句$(ajx_content).replaceWith($(data).filter(ajx_content));,有一些代碼則不同,有可能是這樣的:$(ajx_content).html($(data).filter(ajx_content).html());,還有的用的不是filter()而是find()?。這兩個(gè)函數(shù)是有區(qū)別的,一個(gè)是針對(duì)同級(jí)元素,一個(gè)是針對(duì)子元素;當(dāng)對(duì)請(qǐng)求頁面進(jìn)行剪裁時(shí),容器可能暴露在最外面,此時(shí)就需要用filter;當(dāng)沒有剪裁時(shí)就只能用find。

    3、“剪裁”的方式

    有的小伙伴可能對(duì)“剪裁”并不熟悉,只是生搬硬套,這也導(dǎo)致了后面需要做很多工作,比如:ajax請(qǐng)求后瀏覽器的頁面標(biāo)題需要通過修改頁面結(jié)構(gòu)來組合獲取。其實(shí)剪裁的時(shí)候保留title標(biāo)簽,title就可以直接用document.title = $(data).filter("title").text();來獲取了。

    4、重載回調(diào)

    這個(gè)算是個(gè)很大的難題,因?yàn)榻鉀Q這樣的問題其實(shí)相當(dāng)于把jquery的基礎(chǔ)給學(xué)了一遍,我不是專業(yè)的,現(xiàn)在也還不是很明白這些代碼的執(zhí)行到底應(yīng)該怎么描述。ajax請(qǐng)求不會(huì)請(qǐng)求到容器之外的腳本文件,除非你把js寫在容器之內(nèi),比如之前我試過把百度分享代碼寫在footer.php,但ajax始終不加載,只能把它寫在single.php的容器里面。 還有很多插件會(huì)加載額外的js腳本,比如多說評(píng)論、某蝦米音樂插件、圖片燈箱、代碼高亮 等等,它們?cè)赼jax請(qǐng)求過來后都會(huì)失效,這時(shí)候就需要為ajax提供一個(gè)回調(diào)函數(shù),方便在ajax過程執(zhí)行完畢之后重新加載這些模塊的js腳本。


    有的插件提供了執(zhí)行函數(shù),比如slimbox燈箱,會(huì)有一個(gè)slimbox()函數(shù);Google prettify語法高亮,會(huì)有一個(gè)prettify()函數(shù),這些都可以在ajax回調(diào)時(shí)放進(jìn)去重新加載,使得加載后這些功能不失效。
    有的插件則不會(huì)提供這種函數(shù),比如多說,它只有一整個(gè)js腳本,加載方式可以看這里兩種方式執(zhí)行外部插件掛載的js腳本


    下面我就以最典型的Willin Kan版的ajax評(píng)論來舉個(gè)例子,因?yàn)楹芏嘈』锇橥瓿身撁鎍jax之后,評(píng)論ajax總是失效,下面先看看這個(gè)評(píng)論ajax代碼:

    var theme_dir = $('head #default-css').attr('href').split('style.css')[0]; // 主題路徑 ,以style.css分割href,第一段就是主題路徑
    
    /**
     * WordPress jQuery-Ajax-Comments v1.3 by Willin Kan.
     * URI: http://kan.willin.org/?p=1271
     */
    ??? var commentform = '#comment_form', // ××× form表單id
    ??? comment = 'c_tarea', // ××× textarea 的id 不帶#
    ??? commentlist = 'comment-list',? // ××× 評(píng)論列表ul或ol的class,不帶點(diǎn)
    ??? respond = '#respond',? // ××× 評(píng)論插入位置,插入在這個(gè)id之前
    ??? homeUrl = document.location.href.match(/http:\/\/([^\/]+)\//i)[0], // 主頁地址,用于下面的提交函數(shù)
    ??? txt1 = '<div id="loading" class="text-info"> 正在提交, 請(qǐng)稍候...</div>',
    ??? txt2 = '<div id="error">#</div>',
    ??? txt3 = '"><div class="text-success"> OK !',
    ??? edt1 = ' 刷新頁面之前您可以<a rel="nofollow" class="comment-reply-link" href="#edit" onclick=\'return addComment.moveForm("',
    ??? edt2 = ')\'>再次編輯評(píng)論</a></div>',
    ??? cancel_edit = '取消編輯',
    ??? edit,
    ??? num = 1,
    ??? $comments = $('#response'), // 評(píng)論數(shù)
    ??? $cancel = $('#cancel-comment-reply-link'),
    ??? cancel_text = $cancel.text(),
    ??? $submit = $(commentform+ '#submit');
    ??? $submit.attr('disabled', false),
    ??? $body = (window.opera) ? (document.compatMode == "CSS1Compat" ? $('html') : $('body')) : $('html,body'),
    ??? comm_array = [];
    ??? comm_array.push('');
    ??? $('#'+comment).after(txt1 + txt2); // ××× textarea的id或class
    ??? $('#loading').hide();
    ??? $('#error').hide();
    ??? // 評(píng)論提交
    // $(commentform).submit(? // 非動(dòng)態(tài)綁定
    $(document).on("submit", commentform, //動(dòng)態(tài)綁定
    ??? function() {
    ??????? if (edit) $('#'+comment).after('<input type="text" name="edit_id" id="edit_id" value="' + edit + '" style="display:none;" />');
    ??????? $submit.attr('disabled', true).fadeTo('slow', 0.5);
    ??????? $('#loading').slideDown();
    ??????? $.ajax({
    ??????????? url: theme_dir + '/comt-ajax.php',
    ??????????? data: $(this).serialize() ,
    ??????????? type: $(this).attr('method'),
    ??????????? error: function(request) {
    ??????????????? $('#loading').slideUp();
    ??????????????? $("#error").slideDown().html(request.responseText);
    ??????????????? setTimeout(function() {
    ??????????????????? $submit.attr('disabled', false).fadeTo('slow', 1);
    ??????????????????? $('#error').slideUp();
    ??????????????? },
    ??????????????? 3000);
    ??????????? },
    ??????????? success: function(data) {
    ??????????????? $('#loading').hide();
    ??????????????? comm_array.push($('#'+comment).val());
    ??????????????? $('textarea').each(function() {
    ??????????????????? this.value = ''
    ??????????????? });
    ??????????????? var t = addComment,
    ??????????????? cancel = t.I('cancel-comment-reply-link'),
    ??????????????? temp = t.I('wp-temp-form-div'),
    ??????????????? respond = t.I(t.respondId),
    ??????????????? post = t.I('comment_post_ID').value,
    ??????????????? parent = t.I('comment_parent').value;
    ?? ??? ??? ??? ?// 增加評(píng)論數(shù)
    ??????????????? if (!edit && $comments.length) { 
    ??????????????????? n = parseInt($comments.text().match(/\d+/)); // 匹配數(shù)字
    ??????????????????? $comments.text($comments.text().replace(n, n + 1));
    ??????????????? }
    ?? ??? ??? ??? ?// 評(píng)論顯示
    ??????????????? new_htm = '" id="new_comm_' + num + '"></';
    ??????????????? new_htm = (parent == '0') ? ('\n<ol style="clear:both;" class="'+commentlist+'" ' +? new_htm + 'ol>') : ('\n<ul class="children' + new_htm + 'ul>');
    ??????????????? ok_htm = '\n<div class="ajax-notice" id="success_' + num + txt3;
    ??????????????? div_ = (document.body.innerHTML.indexOf('div-comment-') == -1) ? '': ((document.body.innerHTML.indexOf('li-comment-') == -1) ? 'div-': '');
    ??????????????? ok_htm = ok_htm.concat(edt1, div_, 'comment-', parent, '", "', parent, '", "respond", "', post, '", ', num, edt2);
    ??????????????? ok_htm += '</span><span></span>\n';
    ??????????????? ok_htm += '</div>\n';
    ?? ??? ??? ??? ?if($('#comments .comment-list').length>0){ // ××××××××××××××××××××非嵌套評(píng)論時(shí),新評(píng)論顯示插入的位置(按自己的喜好修改顯示位置)
    ?? ??? ??? ??? ??? ?$('#comments .comment-list').before(new_htm);
    ?? ??? ??? ??? ?} else{
    ?? ??? ??? ??? ??? ?$('#respond').after(new_htm);
    ?? ??? ??? ??? ?}
    ??????????????? $('#new_comm_' + num).append(data);
    ??????????????? $('#new_comm_' + num + ' li').append(ok_htm);
    ??????????????? $body.animate({scrollTop: $('#new_comm_' + num).offset().top - 200},900);
    ??????????????? countdown();
    ??????????????? num++;
    ??????????????? edit = '';
    ??????????????? $('*').remove('#edit_id');
    ??????????????? cancel.style.display = 'none';
    ??????????????? cancel.onclick = null;
    ??????????????? t.I('comment_parent').value = '0';
    ??????????????? if (temp && respond) {
    ??????????????????? temp.parentNode.insertBefore(respond, temp);
    ??????????????????? temp.parentNode.removeChild(temp)
    ??????????????? }
    ??????????? }
    ??????? });
    ??????? return false;
    ??? });
    ??? addComment = {
    ??????? moveForm: function(commId, parentId, respondId, postId, num) {
    ??????????? var t = this,
    ??????????? div,
    ??????????? comm = t.I(commId),
    ??????????? respond = t.I(respondId),
    ??????????? cancel = t.I('cancel-comment-reply-link'),
    ??????????? parent = t.I('comment_parent'),
    ??????????? post = t.I('comment_post_ID');
    ??????????? if (edit) exit_prev_edit();
    ??????????? num ? (t.I(comment).value = comm_array[num], edit = t.I('new_comm_' + num).innerHTML.match(/(comment-)(\d+)/)[2], $new_sucs = $('#success_' + num), $new_sucs.hide(), $new_comm = $('#new_comm_' + num), $new_comm.hide(), $cancel.text(cancel_edit)) : $cancel.text(cancel_text);
    ??????????? t.respondId = respondId;
    ??????????? postId = postId || false;
    ??????????? if (!t.I('wp-temp-form-div')) {
    ??????????????? div = document.createElement('div');
    ??????????????? div.id = 'wp-temp-form-div';
    ??????????????? div.style.display = 'none';
    ??????????????? respond.parentNode.insertBefore(div, respond)
    ??????????? } ! comm ? (temp = t.I('wp-temp-form-div'), t.I('comment_parent').value = '0', temp.parentNode.insertBefore(respond, temp), temp.parentNode.removeChild(temp)) : comm.parentNode.insertBefore(respond, comm.nextSibling);
    ??????????? $body.animate({scrollTop: $('#respond').offset().top - 180},400);
    ??????????? if (post && postId) post.value = postId;
    ??????????? parent.value = parentId;
    ??????????? cancel.style.display = '';
    ??????????? cancel.onclick = function() {
    ??????????????? if (edit) exit_prev_edit();
    ??????????????? var t = addComment,
    ??????????????? temp = t.I('wp-temp-form-div'),
    ??????????????? respond = t.I(t.respondId);
    ??????????????? t.I('comment_parent').value = '0';
    ??????????????? if (temp && respond) {
    ??????????????????? temp.parentNode.insertBefore(respond, temp);
    ??????????????????? temp.parentNode.removeChild(temp);
    ??????????????? }
    ??????????????? this.style.display = 'none';
    ??????????????? this.onclick = null;
    ??????????????? return false;
    ??????????? };
    ??????????? try {
    ??????????????? t.I(comment).focus();
    ??????????? }
    ???????????? catch(e) {}
    ??????????? return false;
    ??????? },
    ??????? I: function(e) {
    ??????????? return document.getElementById(e);
    ??????? }
    ??? };
    ??? function exit_prev_edit() {
    ??????? $new_comm.show();
    ??????? $new_sucs.show();
    ??????? $('textarea').each(function() {
    ??????????? this.value = ''
    ??????? });
    ??????? edit = '';
    ??? }
    ??? var wait = 15,
    ??? submit_val = $submit.val();
    ??? function countdown() {
    ??????? if (wait > 0) {
    ??????????? $submit.val(wait);
    ??????????? wait--;
    ??????????? setTimeout(countdown, 1000);
    ??????? } else {
    ??????????? $submit.val(submit_val).attr('disabled', false).fadeTo('slow', 1);
    ??????????? wait = 15;
    ??????? }
    ??? }
    ??? function grin(a) {
    ??????? var b;
    ??????? a = " " + a + " ";
    ??????? if (document.getElementById(comment) && document.getElementById(comment).type == "textarea") {
    ??????????? b = document.getElementById(comment)
    ??????? } else {
    ??????????? return false
    ??????? }
    ??????? if (document.selection) {
    ??????????? b.focus();
    ??????????? sel = document.selection.createRange();
    ??????????? sel.text = a;
    ??????????? b.focus()
    ??????? } else if (b.selectionStart || b.selectionStart == "0") {
    ??????????? var c = b.selectionStart;
    ??????????? var d = b.selectionEnd;
    ??????????? var e = d;
    ??????????? b.value = b.value.substring(0, c) + a + b.value.substring(d, b.value.length);
    ??????????? e += a.length;
    ??????????? b.focus();
    ??????????? b.selectionStart = e;
    ??????????? b.selectionEnd = e
    ??????? } else {
    ??????????? b.value += a;
    ??????????? b.focus()
    ??????? }
    ??? }

    上面的代碼有些選擇器是針對(duì)我自己的主題的,所以僅供參考,這個(gè)不重要。重點(diǎn)是當(dāng)各種變量賦值完畢后,那一句$(document).on("submit", commentform,?,這個(gè)是關(guān)鍵,意思是這個(gè)on方法把submit事件冒泡綁定到了document上,這個(gè)時(shí)候submit事件里面的所有動(dòng)作就不會(huì)受到頁面ajax加載的影響。你可以注意到上面有一句$('#'+comment).after(txt1 + txt2);?這個(gè)是在提交評(píng)論時(shí)顯示的loading提示文字,它沒有被包含在submit事件里面,所以它是受到頁面ajax加載影響的!也就是說:頁面ajax加載后,你點(diǎn)擊評(píng)論提交按鈕,此時(shí)不會(huì)顯示loading提示文字,但卻能進(jìn)行ajax評(píng)論提交。如果你把這段提示放進(jìn)submit里面去,那么整個(gè)評(píng)論ajax就和頁面ajax完全相互獨(dú)立了,它們可以互不影響,完全兼容。


    另外,你可能注意到在$(document).on("submit", commentform,?上一句注釋是這樣的$(commentform).submit(,這表示你沒有用on方法將submit冒泡到document之上,此時(shí)這就和上面那個(gè)loading提示文字是一樣的,整個(gè)評(píng)論ajax就會(huì)受到頁面ajax的影響。那么如果不用on方法,應(yīng)該怎么兼容?看下面的代碼:

    var theme_dir = $('head #default-css').attr('href').split('style.css')[0]; // 主題路徑 ,以style.css分割href,第一段就是主題路徑
    /**
    ?* WordPress jQuery-Ajax-Comments v1.3 by Willin Kan.
    ?* URI: http://kan.willin.org/?p=1271
    ?*/
    $(document).ready(function() {
    ??? ajaxComt();
    });
    function ajaxComt(){
    ??? var commentform = '#comment_form', // ××× form表單id
    ??? comment = 'c_tarea', // ××× textarea 的id 不帶#
    ??? commentlist = 'comment-list',? // ××× 評(píng)論列表ul或ol的class,不帶點(diǎn)
    ??? respond = '#respond',? // ××× 評(píng)論插入位置,插入在這個(gè)id之前
    ??? homeUrl = document.location.href.match(/http:\/\/([^\/]+)\//i)[0], // 主頁地址,用于下面的提交函數(shù)
    ??? txt1 = '<div id="loading" class="text-info"> 正在提交, 請(qǐng)稍候...</div>',
    ??? txt2 = '<div id="error">#</div>',
    ??? txt3 = '"><div class="text-success"> OK !',
    ??? edt1 = ' 刷新頁面之前您可以<a rel="nofollow" class="comment-reply-link" href="#edit" onclick=\'return addComment.moveForm("',
    ??? edt2 = ')\'>再次編輯評(píng)論</a></div>',
    ??? cancel_edit = '取消編輯',
    ??? edit,
    ??? num = 1,
    ??? $comments = $('#response'), // 評(píng)論數(shù)
    ??? $cancel = $('#cancel-comment-reply-link'),
    ??? cancel_text = $cancel.text(),
    ??? $submit = $(commentform+ '#submit');
    ??? $submit.attr('disabled', false),
    ??? $body = (window.opera) ? (document.compatMode == "CSS1Compat" ? $('html') : $('body')) : $('html,body'),
    ??? comm_array = [];
    ??? comm_array.push('');
    ??? $('#'+comment).after(txt1 + txt2); // ××× textarea的id或class
    ??? $('#loading').hide();
    ??? $('#error').hide();
    ??? // 評(píng)論提交
    $(commentform).submit(? // 非動(dòng)態(tài)綁定
    // $(document).on("submit", commentform, // 動(dòng)態(tài)綁定
    ??? function() {
    ??????? if (edit) $('#'+comment).after('<input type="text" name="edit_id" id="edit_id" value="' + edit + '" style="display:none;" />');
    ??????? $submit.attr('disabled', true).fadeTo('slow', 0.5);
    ??????? $('#loading').slideDown();
    ??????? $.ajax({
    ??????????? url: theme_dir + '/comt-ajax.php',
    ??????????? data: $(this).serialize() ,
    ??????????? type: $(this).attr('method'),
    ??????????? error: function(request) {
    ??????????????? $('#loading').slideUp();
    ??????????????? $("#error").slideDown().html(request.responseText);
    ??????????????? setTimeout(function() {
    ??????????????????? $submit.attr('disabled', false).fadeTo('slow', 1);
    ??????????????????? $('#error').slideUp();
    ??????????????? },
    ??????????????? 3000);
    ??????????? },
    ??????????? success: function(data) {
    ??????????????? $('#loading').hide();
    ??????????????? comm_array.push($('#'+comment).val());
    ??????????????? $('textarea').each(function() {
    ??????????????????? this.value = ''
    ??????????????? });
    ??????????????? var t = addComment,
    ??????????????? cancel = t.I('cancel-comment-reply-link'),
    ??????????????? temp = t.I('wp-temp-form-div'),
    ??????????????? respond = t.I(t.respondId),
    ??????????????? post = t.I('comment_post_ID').value,
    ??????????????? parent = t.I('comment_parent').value;
    ?? ??? ??? ??? ?// 增加評(píng)論數(shù)
    ??????????????? if (!edit && $comments.length) { 
    ??????????????????? n = parseInt($comments.text().match(/\d+/)); // 匹配數(shù)字
    ??????????????????? $comments.text($comments.text().replace(n, n + 1));
    ??????????????? }
    ?? ??? ??? ??? ?// 評(píng)論顯示
    ??????????????? new_htm = '" id="new_comm_' + num + '"></';
    ??????????????? new_htm = (parent == '0') ? ('\n<ol style="clear:both;" class="'+commentlist+'" ' +? new_htm + 'ol>') : ('\n<ul class="children' + new_htm + 'ul>');
    ??????????????? ok_htm = '\n<div class="ajax-notice" id="success_' + num + txt3;
    ??????????????? div_ = (document.body.innerHTML.indexOf('div-comment-') == -1) ? '': ((document.body.innerHTML.indexOf('li-comment-') == -1) ? 'div-': '');
    ??????????????? ok_htm = ok_htm.concat(edt1, div_, 'comment-', parent, '", "', parent, '", "respond", "', post, '", ', num, edt2);
    ??????????????? ok_htm += '</span><span></span>\n';
    ??????????????? ok_htm += '</div>\n';
    ?? ??? ??? ??? ?if($('#comments .comment-list').length>0){ // ××××××××××××××××××××非嵌套評(píng)論時(shí),新評(píng)論顯示插入的位置(按自己的喜好修改顯示位置)
    ?? ??? ??? ??? ??? ?$('#comments .comment-list').before(new_htm);
    ?? ??? ??? ??? ?} else{
    ?? ??? ??? ??? ??? ?$('#respond').after(new_htm);
    ?? ??? ??? ??? ?}
    ??????????????? $('#new_comm_' + num).append(data);
    ??????????????? $('#new_comm_' + num + ' li').append(ok_htm);
    ??????????????? $body.animate({scrollTop: $('#new_comm_' + num).offset().top - 200},900);
    ??????????????? countdown();
    ??????????????? num++;
    ??????????????? edit = '';
    ??????????????? $('*').remove('#edit_id');
    ??????????????? cancel.style.display = 'none';
    ??????????????? cancel.onclick = null;
    ??????????????? t.I('comment_parent').value = '0';
    ??????????????? if (temp && respond) {
    ??????????????????? temp.parentNode.insertBefore(respond, temp);
    ??????????????????? temp.parentNode.removeChild(temp)
    ??????????????? }
    ??????????? }
    ??????? });
    ??????? return false;
    ??? });
    ??? addComment = {
    ??????? moveForm: function(commId, parentId, respondId, postId, num) {
    ??????????? var t = this,
    ??????????? div,
    ??????????? comm = t.I(commId),
    ??????????? respond = t.I(respondId),
    ??????????? cancel = t.I('cancel-comment-reply-link'),
    ??????????? parent = t.I('comment_parent'),
    ??????????? post = t.I('comment_post_ID');
    ??????????? if (edit) exit_prev_edit();
    ??????????? num ? (t.I(comment).value = comm_array[num], edit = t.I('new_comm_' + num).innerHTML.match(/(comment-)(\d+)/)[2], $new_sucs = $('#success_' + num), $new_sucs.hide(), $new_comm = $('#new_comm_' + num), $new_comm.hide(), $cancel.text(cancel_edit)) : $cancel.text(cancel_text);
    ??????????? t.respondId = respondId;
    ??????????? postId = postId || false;
    ??????????? if (!t.I('wp-temp-form-div')) {
    ??????????????? div = document.createElement('div');
    ??????????????? div.id = 'wp-temp-form-div';
    ??????????????? div.style.display = 'none';
    ??????????????? respond.parentNode.insertBefore(div, respond)
    ??????????? } ! comm ? (temp = t.I('wp-temp-form-div'), t.I('comment_parent').value = '0', temp.parentNode.insertBefore(respond, temp), temp.parentNode.removeChild(temp)) : comm.parentNode.insertBefore(respond, comm.nextSibling);
    ??????????? $body.animate({scrollTop: $('#respond').offset().top - 180},400);
    ??????????? if (post && postId) post.value = postId;
    ??????????? parent.value = parentId;
    ??????????? cancel.style.display = '';
    ??????????? cancel.onclick = function() {
    ??????????????? if (edit) exit_prev_edit();
    ??????????????? var t = addComment,
    ??????????????? temp = t.I('wp-temp-form-div'),
    ??????????????? respond = t.I(t.respondId);
    ??????????????? t.I('comment_parent').value = '0';
    ??????????????? if (temp && respond) {
    ??????????????????? temp.parentNode.insertBefore(respond, temp);
    ??????????????????? temp.parentNode.removeChild(temp);
    ??????????????? }
    ??????????????? this.style.display = 'none';
    ??????????????? this.onclick = null;
    ??????????????? return false;
    ??????????? };
    ??????????? try {
    ??????????????? t.I(comment).focus();
    ??????????? }
    ???????????? catch(e) {}
    ??????????? return false;
    ??????? },
    ??????? I: function(e) {
    ??????????? return document.getElementById(e);
    ??????? }
    ??? };
    ??? function exit_prev_edit() {
    ??????? $new_comm.show();
    ??????? $new_sucs.show();
    ??????? $('textarea').each(function() {
    ??????????? this.value = ''
    ??????? });
    ??????? edit = '';
    ??? }
    ??? var wait = 15,
    ??? submit_val = $submit.val();
    ??? function countdown() {
    ??????? if (wait > 0) {
    ??????????? $submit.val(wait);
    ??????????? wait--;
    ??????????? setTimeout(countdown, 1000);
    ??????? } else {
    ??????????? $submit.val(submit_val).attr('disabled', false).fadeTo('slow', 1);
    ??????????? wait = 15;
    ??????? }
    ??? }
    ??? function grin(a) {
    ??????? var b;
    ??????? a = " " + a + " ";
    ??????? if (document.getElementById(comment) && document.getElementById(comment).type == "textarea") {
    ??????????? b = document.getElementById(comment)
    ??????? } else {
    ??????????? return false
    ??????? }
    ??????? if (document.selection) {
    ??????????? b.focus();
    ??????????? sel = document.selection.createRange();
    ??????????? sel.text = a;
    ??????????? b.focus()
    ??????? } else if (b.selectionStart || b.selectionStart == "0") {
    ??????????? var c = b.selectionStart;
    ??????????? var d = b.selectionEnd;
    ??????????? var e = d;
    ??????????? b.value = b.value.substring(0, c) + a + b.value.substring(d, b.value.length);
    ??????????? e += a.length;
    ??????????? b.focus();
    ??????????? b.selectionStart = e;
    ??????????? b.selectionEnd = e
    ??????? } else {
    ??????????? b.value += a;
    ??????????? b.focus()
    ??????? }
    ??? }
    }
    // end Ajax評(píng)論

    代碼的核心內(nèi)容和前面是一樣的,只不過我將整段評(píng)論代碼寫成了一個(gè)ajaxComt()函數(shù),也就是將代碼用function ajaxComt(){...}包住,可以看到,此時(shí)submit事件并非動(dòng)態(tài)綁定,只要這樣

    $(document).ready(function() {
    ??? ajaxComt();
    });

    就和原來不用函數(shù)包住的時(shí)候沒什么區(qū)別了。那么這個(gè)ajaxComt()函數(shù),就是我們放在頁面ajax回調(diào)里面重新加載的東西。ajax方法里面會(huì)有幾個(gè)執(zhí)行先后的參數(shù),beforeSend、success、complete ,我們可以把它放在complete里面:

    complete: function() { // 頁面ajax完成后加載
    ?? ?ajaxComt();
    }

    這樣就和動(dòng)態(tài)綁定沒什么區(qū)別了。說法的區(qū)別從我個(gè)人角度來看就是:前者屬于冒泡綁定,頁面ajax和評(píng)論ajax是互不影響的;后者屬于先后執(zhí)行,頁面ajax先執(zhí)行完畢再執(zhí)行一遍評(píng)論ajax 。

    第四部分

    原文來源: http://www.inlojv.com/5026.html

    教程進(jìn)行到第四已然顯得有些羅嗦了,本篇主要是本人記錄自己遇到的一些細(xì)節(jié)問題和網(wǎng)上的各種pjax代碼版本,權(quán)當(dāng)補(bǔ)充篇來看吧。

    搜索ajax表單序列化

    最近想把主題換成經(jīng)典的twentytwelve,也試著把它pjax化,其中遇到一個(gè)搜索ajax的問題,按理說其他主題能實(shí)現(xiàn),沒問題,這個(gè)也應(yīng)該可以,但我把代碼搬上去之后,發(fā)現(xiàn)搜索ajax返回沒有返回正確的頁面,這里首先要說的就是WordPress正常情況下的搜索請(qǐng)求鏈接應(yīng)該是這樣的http://127.0.0.1/?=xxx,xxx表示你搜索的關(guān)鍵字,而由于有后端的處理(也就是教程[一]中的“剪裁”),發(fā)送給ajax的請(qǐng)求鏈接一般是類似?ajx=container這樣的后綴(其他版本有可能是這樣?action=pjax),那么搜索ajax的請(qǐng)求鏈接能不能這樣http://127.0.0.1/?=xxx?ajx=container?答案是不能。只能把?號(hào)換成&號(hào),變成這樣http://127.0.0.1/?=xxx&ajx=container,所以在搜索ajax的請(qǐng)求鏈接上要加一些判斷,如果是搜索,那么得改一改鏈接附加的參數(shù)形式。


    以上只是一個(gè)細(xì)節(jié),我在修改twentytwelve時(shí)沒有返回應(yīng)有的頁面,把搜索鏈接http://127.0.0.1/?=xxx&ajx=container直接輸入到瀏覽器打開,發(fā)現(xiàn)也不是搜索結(jié)果頁面,找了半天才發(fā)現(xiàn)是form表單序列化的問題,$.ajax()方法有幾個(gè)參數(shù),其中我們要把序列化的表單信息放入到ajax方法的data參數(shù)內(nèi)。賦值?data = $('#searchform').serialize();?。其中#searchform是form表單的id

    wordpress全站PJAX系列教程 - wordpress開發(fā)

    以上只是一個(gè)例子,條件判斷可以按自己的思路來做改變。如此一來,搜索ajax就沒有問題了。

    插件

    GutenSpot - wordpress古登堡的圖像庫熱點(diǎn)插件

    2020-4-4 15:07:33

    資源

    Lately.js - 基于jQuery開發(fā)的好用的'Timeago'插件

    2018-7-13 15:06:44

    ??
    Npcink上的部份代碼及教程來源于互聯(lián)網(wǎng),僅供網(wǎng)友學(xué)習(xí)交流,若您喜歡本文可附上原文鏈接隨意轉(zhuǎn)載。
    無意侵害您的權(quán)益,請(qǐng)發(fā)送郵件至 1355471563#qq.com 或點(diǎn)擊右側(cè) 私信:Muze 反饋,我們將盡快處理。
    0 條回復(fù) A文章作者 M管理員
      暫無討論,說說你的看法吧
    ?
    個(gè)人中心
    購物車
    優(yōu)惠劵
    今日簽到
    有新私信 私信列表
    搜索
    主站蜘蛛池模板: 无码喷水一区二区浪潮AV| 波多野结衣在线观看一区二区三区| 国产精品99无码一区二区| 日本一区二区三区在线视频观看免费| 一区二区三区四区精品| 国模无码人体一区二区| 国产AV一区二区三区无码野战| 综合一区自拍亚洲综合图区| 亚洲综合无码一区二区| 一区二区高清视频在线观看| 亚洲AV无码一区二区乱子仑 | 午夜一区二区免费视频| 亚洲伦理一区二区| 中文字幕乱码一区二区免费| 老熟女高潮一区二区三区| 激情亚洲一区国产精品| 精品国产一区二区三区久久蜜臀| 无码成人一区二区| 国产精品被窝福利一区| 国产精品美女一区二区三区 | 丰满人妻一区二区三区免费视频| 一区二区三区观看免费中文视频在线播放 | 久久成人国产精品一区二区| 亚洲第一区在线观看| 日本v片免费一区二区三区| 日韩精品无码一区二区中文字幕 | 国产在线精品一区二区在线观看 | 国产亚洲一区二区三区在线观看| 激情爆乳一区二区三区| 久久久无码精品国产一区| 久久国产精品无码一区二区三区| 亚洲韩国精品无码一区二区三区| 亚洲乱码一区av春药高潮| 国产一区二区三区在线| 精品国产一区二区三区四区| 国产亚洲一区二区手机在线观看 | 免费一本色道久久一区| 亚洲熟妇成人精品一区| 国产精品乱码一区二区三区| 久久久久人妻精品一区三寸| 狠狠综合久久av一区二区|