Як створити пошук під час автоматичного заповнення?


22

На даний момент я намагаюся створити функцію пошуку в wordpress, яка відображає результати пошуку під панеллю пошуку. Приклад є на веб-сайті Світового банку (екрани нижче). Я не шукаю автозаповнення, як ви могли б знайти на Google.com, яке завершує введені вами слова, скоріше я хочу, щоб він знаходив фактичні публікації на сайті.

Я спробував зробити скраб за допомогою Wordpress Answers та інших подібних ресурсів, але я лише зіткнувся з реалізацією пошуку типу Google, який не є тим, що я шукаю. Будемо дуже вдячні за будь-яку допомогу чи точки в правильному напрямку.

пошук-перед

пошук після


Що ви хочете, коли користувач натискає пропозицію? Просто заповніть його пошуковим вікном?
Рарст

Перенесе вас на відповідну посаду. Користувач все ще може набирати та отримувати результати пошуку, як правило, лише натискання пропозицій спрямовуватиме до публікації.
mmaximalist

Я маю на увазі швидке рішення щодо заповнення, але зв’язувати більш проблематично ... Подумаю про це.
Рарст

Відповіді:


20

Далі використовується jQuery UI Autocomplete, який включений у WordPress з 3.3. (Я запозичив формат у @Rarst : D).

Це все ще не точно те, що ви хочете, але дає хорошу вихідну точку. Далі використовується базовий стиль інтерфейсу jQuery, але ви можете використовувати той, який наразі працює над trac, і викликати його з папки плагіна.

class AutoComplete {

    static $action = 'my_autocomplete';//Name of the action - should be unique to your plugin.

    static function load() {
        add_action( 'init', array( __CLASS__, 'init'));
    }

    static function init() {
        //Register style - you can create your own jQuery UI theme and store it in the plug-in folder
        wp_register_style('my-jquery-ui','http://ajax.googleapis.com/ajax/libs/jqueryui/1.8/themes/base/jquery-ui.css');    
        add_action( 'get_search_form', array( __CLASS__, 'get_search_form' ) );
        add_action( 'wp_print_footer_scripts', array( __CLASS__, 'print_footer_scripts' ), 11 );
        add_action( 'wp_ajax_'.self::$action, array( __CLASS__, 'autocomplete_suggestions' ) );
        add_action( 'wp_ajax_nopriv_'.self::$action, array( __CLASS__, 'autocomplete_suggestions' ) );
    }

    static function get_search_form( $form ) {
        wp_enqueue_script( 'jquery-ui-autocomplete' );
        wp_enqueue_style('my-jquery-ui');
        return $form;
    }

    static function print_footer_scripts() {
        ?>
    <script type="text/javascript">
    jQuery(document).ready(function ($){
        var ajaxurl = '<?php echo admin_url( 'admin-ajax.php' ); ?>';
        var ajaxaction = '<?php echo self::$action ?>';
        $("#secondary #searchform #s").autocomplete({
            delay: 0,
            minLength: 0,
            source: function(req, response){  
                $.getJSON(ajaxurl+'?callback=?&action='+ajaxaction, req, response);  
            },
            select: function(event, ui) {
                window.location.href=ui.item.link;
            },
        });
    });
    </script><?php
    }

    static function autocomplete_suggestions() {
        $posts = get_posts( array(
            's' => trim( esc_attr( strip_tags( $_REQUEST['term'] ) ) ),
        ) );
        $suggestions=array();

        global $post;
        foreach ($posts as $post): 
                    setup_postdata($post);
            $suggestion = array();
            $suggestion['label'] = esc_html($post->post_title);
            $suggestion['link'] = get_permalink();

            $suggestions[]= $suggestion;
        endforeach;

        $response = $_GET["callback"] . "(" . json_encode($suggestions) . ")";  
        echo $response;  
        exit;
    }
}
AutoComplete::load();

12

Гаразд, це був би дуже базовий приклад коду, який використовує нативний suggest.js, WP-ядро для Ajax і прив'язується до форми пошуку за замовчуванням (від немодифікованого get_search_form()виклику). Це не саме те, про що ви просили, але поступовий пошук - це величезний біль, щоб стати ідеальним. :)

class Incremental_Suggest {

    static function on_load() {

        add_action( 'init', array( __CLASS__, 'init' ) );
    }

    static function init() {

        add_action( 'wp_print_scripts', array( __CLASS__, 'wp_print_scripts' ) );
        add_action( 'get_search_form', array( __CLASS__, 'get_search_form' ) );
        add_action( 'wp_print_footer_scripts', array( __CLASS__, 'wp_print_footer_scripts' ), 11 );
        add_action( 'wp_ajax_incremental_suggest', array( __CLASS__, 'wp_ajax_incremental_suggest' ) );
        add_action( 'wp_ajax_nopriv_incremental_suggest', array( __CLASS__, 'wp_ajax_incremental_suggest' ) );
    }

    static function wp_print_scripts() {

        ?>
    <style type="text/css">
        .ac_results {
            padding: 0;
            margin: 0;
            list-style: none;
            position: absolute;
            z-index: 10000;
            display: none;
            border-width: 1px;
            border-style: solid;
        }

        .ac_results li {
            padding: 2px 5px;
            white-space: nowrap;
            text-align: left;
        }

        .ac_over {
            cursor: pointer;
        }

        .ac_match {
            text-decoration: underline;
        }
    </style>
    <?php
    }

    static function get_search_form( $form ) {

        wp_enqueue_script( 'suggest' );

        return $form;
    }

    static function wp_print_footer_scripts() {

        ?>
    <script type="text/javascript">
        jQuery(document).ready(function ($) {
            $('#s').suggest('<?php echo admin_url( 'admin-ajax.php' ); ?>' + '?action=incremental_suggest');
        });
    </script><?php
    }

    static function wp_ajax_incremental_suggest() {

        $posts = get_posts( array(
            's' => $_REQUEST['q'],
        ) );

        $titles = wp_list_pluck( $posts, 'post_title' );
        $titles = array_map( 'esc_html', $titles );
        echo implode( "\n", $titles );

        die;
    }
}

Incremental_Suggest::on_load();

0

Ви, звичайно, повинні робити це за допомогою Ajax, але тут є проблема. Оскільки WordPress використовує MySQL, ви можете перенапружити сервер від пошуку, якщо ви спробуєте заповнити пошук реальними запитами до бази даних через Ajax, але ви можете зробити це, щоб розробити систему, де всі публікації зберігаються в один великий "wp_options" поле, а тоді, коли виконується пошук, ви запитуєте це замість реального пошуку. Але пам’ятайте, що вам потрібно оновлювати цю частину тексту / серіалізованої змінної щоразу, коли ви створюєте чи редагуєте публікацію.

Якщо ви не бажаєте витрачати якийсь час на розробку цього рішення, я б не рекомендував вам робити такий вид "живого пошуку".


2
У такому випадку використання ресурсів запитів MySQL було б зовсім незначним порівняно з хітом завантаження ядра WP для запитів Ajax.
Рарст

1
Залежить від того, як ви намагаєтеся виконати запит Ajax, в цьому випадку вам не дуже потрібне все ядро ​​WP для вашої відповіді, найкращим сценарієм буде лише завантаження $ wpdb та пошук вашого поля. Але, погодившись, використання основного URL-адреси Ajax WP обидва вони можуть стати причиною проблеми, якщо вона не буде добре розроблена.
Вебкор

1
Так, я просто зауважую, що продуктивність MySQL не була б вузьким місцем (якщо тільки ви не потрапите в сотні тисяч постів і подібних). Ядро WP набагато набагато повільніше. Мережа також повільніше.
Рарст

Так, але зробити якесь «Скалінг» з машинами WP Core набагато простіше та швидше. З MySQL машини повільніше і важче. Але при нормальній установці я з вами згоден.
Вебкор
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.