問題描述

我正在使用 jQuery UI Sortable 構建前端後台佈局編輯器。

帖子在背景圖像中以 300px x 250px 的方式佈置。使用 WordPress 管理員創建和編輯帖子,但我想允許站點管理員使用前端的拖放界面調整框的順序。

我已經拖放可排序的部分工作,但需要提出一種方法來保存框的狀態 (順序) 。理想情況下,我希望能夠將狀態保存為一個選項,並將其構建到查詢中。

對帖子的查詢是一個簡單的 WP_Query,它也可以從自定義元框獲取數據,以確定單獨的框佈局。

$args= array(
      'meta_key' => 'c3m_shown_on',
       'meta_value'=> 'home' );
    $box_query = new WP_Query($args);  ?>
        <ul id="sortable">
            <?php
    while ($box_query->have_posts()) : $box_query->the_post(); global $post; global $prefix;
    $box_size = c3m_get_field($prefix.'box_size', FALSE);
    $box_image = c3m_get_field($prefix.'post_box_image', FALSE);
    $overlay_class = c3m_get_field($prefix.'overlay_class', FALSE);

    if ( c3m_get_field($prefix.'external_link', FALSE) ) {
    $post_link = c3m_get_field($prefix.'external_link', FALSE);
    } else
            { $post_link = post_permalink();
    } ?>
     <li class="<?php echo $box_size;?>  ui-state-default">
        <article <?php post_class() ?> id="post-<?php the_ID(); ?>">
            <?php echo  '<a href="'.$post_link.'" ><img src="'.esc_url($box_image).'" alt="Image via xxxxx.com" /></a>'; ?>
                <div class="post-box <?php echo $overlay_class;?>">
                <?php if ( c3m_get_field( $prefix.'text_display', FALSE) ) { ?>
                <h2><a href="<?php%20echo%20$post_link?>"><?php the_title();?></a></h2>
                <p><?php echo substr($post->post_excerpt, 0, 90) . '...'; ?></p>
                <?php } ?>
                </div>
         </article>
     </li>
    <?php endwhile; ?>
       </ul>
</section>

javascript 只是基本的默認可排序説明

jQuery(document).ready(function() {
    jQuery("#sortable").sortable();
  });

有可用的方法可以使用 cookies 保存狀態,但我還需要禁用非管理員用户的可排序的拖放,所以我真的需要保存到數據庫。

我正在尋找最具創意和最有用的方法,並將獲得 100 分的賞金,以獲得最佳答案。

更新:

我得到了 somatic’s 的回答工作與一個小的變化。

ajaxurl 不返回非管理頁面上的值,因此我使用 wp_localize_script( 'functions', 'MyAjax', array( 'ajaxurl' => admin_url( 'admin-ajax.php' ) ) ); 來定義值,並將選項下的 JavaScript 行更改為:url: MyAjax.ajaxurl,

為了限制訪問權限,只能將訂單安排到管理員,我添加了一個條件到我的 wp_enqueue_script 函數:

    function c3m_load_scripts() {
    if ( current_user_can( 'edit_posts' ) ) {
        wp_enqueue_script( 'jquery-ui' );
        wp_enqueue_script( 'functions', get_bloginfo( 'stylesheet_directory' ) . '/_/js/functions.js', array( 'jquery', 'jquery-ui' ), false);
        wp_localize_script( 'functions', 'MyAjax', array( 'ajaxurl' => admin_url( 'admin-ajax.php' ) ) );
    }
}

我要做一些更多的測試,並將這個問題標記為已解決,並獎勵賞金。

最佳解決方案

Brady 是正確的,處理自定義帖子類型訂單的保存和顯示的最佳方式是使用 menu_order 屬性

這裏是使列表排序的 jQuery,並將數據通過 ajax 傳遞給 wordpress:

jQuery(document).ready(function($) {
    var itemList = $('#sortable');

    itemList.sortable({
        update: function(event, ui) {
            $('#loading-animation').show(); // Show the animate loading gif while waiting

            opts = {
                url: ajaxurl, // ajaxurl is defined by WordPress and points to /wp-admin/admin-ajax.php
                type: 'POST',
                async: true,
                cache: false,
                dataType: 'json',
                data:{
                    action: 'item_sort', // Tell WordPress how to handle this ajax request
                    order: itemList.sortable('toArray').toString() // Passes ID's of list items in  1,3,2 format
                },
                success: function(response) {
                    $('#loading-animation').hide(); // Hide the loading animation
                    return;
                },
                error: function(xhr,textStatus,e) {  // This can be expanded to provide more information
                    alert(e);
                    // alert('There was an error saving the updates');
                    $('#loading-animation').hide(); // Hide the loading animation
                    return;
                }
            };
            $.ajax(opts);
        }
    });
});

這是一個 wordpress 函數,它監聽 ajax 回調並在 DB 上執行更改:

function my_save_item_order() {
    global $wpdb;

    $order = explode(',', $_POST['order']);
    $counter = 0;
    foreach ($order as $item_id) {
        $wpdb->update($wpdb->posts, array( 'menu_order' => $counter ), array( 'ID' => $item_id) );
        $counter++;
    }
    die(1);
}
add_action('wp_ajax_item_sort', 'my_save_item_order');
add_action('wp_ajax_nopriv_item_sort', 'my_save_item_order');

以您保存的順序顯示帖子的關鍵是將 menu_order 屬性添加到查詢 args 中:

$args= array(
    'meta_key' => 'c3m_shown_on',
    'meta_value'=> 'home'
    'orderby' => 'menu_order',
    'order' => 'ASC'
);

$box_query = new WP_Query($args);

然後運行你的循環並輸出每個項目…(第一行是核心的 wp 加載動畫 – 你最初要通過 css 隱藏它,然後 jquery 函數將在處理時顯示)

<img src="<?php%20bloginfo('url');%20?>/wp-admin/images/loading.gif" id="loading-animation" />
<ul id="sortable">
    <li id="{echo post ID here}">{echo title or other name here}</li>
</ul>

代碼靈感來自於 soulsizzle 的 excellent tutorial

次佳解決方案

http://jsfiddle.net/TbR69/1/

遠遠沒有完成,但是想法是發送一個拖放的 ajax 請求。您也可以僅在單擊”save” 按鈕或某些事件後觸發 ajax 請求。將發送包含帖子 ID 和新訂單的數組。

那麼你必須更新服務器端的數據庫中的帖子。最後,將 order 參數添加到 WP_Query 循環中。

我希望這能讓你開始。任何人都可以隨意繼續玩弄。

參考文獻

注:本文內容整合自 Google/Baidu/Bing 輔助翻譯的英文資料結果。如果您對結果不滿意,可以加入我們改善翻譯效果:薇曉朵技術論壇。