Wp wp sorgusu kullanarak üst tüm alt sayfaları almak


13

İşte kodum

$my_wp_query = new WP_Query();
$all_wp_pages = $my_wp_query->query(array('post_type' => 'page','post_parent'=>$parid,'orderby'=>'title','order'=>'ASC' ));

Yalnızca birinci düzey alt sayfaları görüntüler. Tüm alt sayfaya, alt alt sayfaya ... ve hepsine ihtiyacım var. Bir çözüm aradım ve get_pages ve wp_list_pages kullanarak tüm alt sayfaları alabilirsiniz.

Ama gerçekten özel post meta değerine göre sıralamak gerekir. Bu yüzden özel sorgu kullanmak zorunda.

lütfen yardım et. Teşekkürler


1
Aşağıda bir cevap bulduğunu söylüyorsun, ne oldu?
Drew Baker

Yanıtlar:


6

Neden sadece kullanmıyorsunuz get_pages()?

Örneğin

<?php
// Determine parent page ID
$parent_page_id = ( '0' != $post->post_parent ? $post->post_parent : $post->ID );
// Get child pages as array
$page_tree_array = get_pages( array(
    'child_of' => $parent_page_id;
) );
?>

Ancak gerçekten bir WP_Query()nesne olarak olması gerekiyorsa , benzer bir yöntem kullanın:

<?php
// Determine parent page ID
$parent_page_id = ( '0' != $post->post_parent ? $post->post_parent : $post->ID );
// Build WP_Query() argument array
$page_tree_query_args = array(
    'post_parent' => $parent_page_id;
);
// Get child pages as a WP_Query() object
$page_tree_query = new WP_Query( $page_tree_query_args );
?>

Get_pages () işlevini kullanırsak, özel alanlar için sıralamayı (sort_column) uygulayamazdık. Yalnızca yazı tablosu alanlarını kabul eder. Özel alan için sıralama uygulamak gerekir. Bu yüzden sadece wp sorgusu () kullanın. Alternatif bir yol var mı?
phpuser

Kullandığım cevabın ikinci yarısını gördün mü WP_Query()?
Chip Bennett

Bu kodu denedim ama sadece birinci seviye alt sayfaları döndürür. Alt sayfa >> alt alt >> vb ... (birden çok sayfa alt seviyeleri.) Gerekir. Sonunda çözümü buldum. Cevabınız için teşekkürler
phpuser

7
çözümün nedir?
JCHASE11

Yukarıdaki dizi tanımlarının içinde sözdizimi hatalarına neden olan bazı noktalı virgüller vardır.
ptrin

4

Sorun

Kavramakta sorun yaşadığınız şey "X'i nasıl yaparım?" Bu 1 adımlık bir eylem değil, çok aşamalı bir süreçtir ve parçalanması gerekir.

Bunu yapmanız gerekmez:

get all the posts that are a child of X ordered by meta

Bunu yapmanız gerekir:

get all the posts that are a child of X
    for each child, get all the posts that are a child
        foreach child of that child get all the posts that are a child
            ...
                hmmm we don't have any more children left

Take our list of posts and order them by meta

Genel Çözüm

Bu nedenle, sonuna kadar, kodlamadan sonsuz şekilde nasıl yapacağınızı anlamak için, yinelemeli işlevleri anlamanız gerekir.

Örneğin

function make_zero( $amount ) {
    $amount = $amount - 1;
    if ( $amount > 1 ){
        return make_zero( $amount );
    }
    return $amount;
}

Çözüm için Bu Soruna Özyineleme Uygulama

Böylece ebeveyniniz $paridve meta meta anahtarınız var $metakey.

Çocuklarını yakalama işlevine geçelim.

$children = get_children_with_meta( $parid, $metakey );

Sonra $ children dizisini sıralayacağız, anahtarlar posta kimlikleri ve değerler meta değerler olacak.

asort($children);

ve işlevi şöyle tanımlayalım:

function get_children_with_meta( $parent_id, $metakey ) {
    $q = new WP_Query( array( 'post_parent' => $parent_id, 'meta_key' => $metakey ));
    if ( $q->have_posts() ) {
        $children - array();
        while ( $q->have_posts() ) {
            $q->the_post();
            $meta_value = get_post_meta(get_the_ID(), $metakey, true );
            $children[get_the_ID() ] = $meta_value;
        }
        return $children;
    } else {
        // there are no children!!
        return array();
    }
}

Bu size en düşükten en yükseğe doğru sıralanmış bir dizi posta kimliği ve değeri verir. En yüksekten en düşüğe doğru yapmak için diğer PHP sıralama işlevlerini kullanabilirsiniz.

Peki Ya Çocuk Çocukları?

Döngünümüzün ortasında, ebeveyn kimliği yerine alt öğeyi geçerek yinelemeli bir çağrı yapmamız gerekiyor.

Yani bu:

$q->the_post();
$meta_value = get_post_meta(get_the_ID(), $metakey, true );
$children[get_the_ID() ] = $meta_value;

Bu olur:

$q->the_post();
$meta_value = get_post_meta(get_the_ID(), $metakey, true );
$children[get_the_ID() ] = $meta_value;

// now get the childrens children
$grandchildren = get_children_with_meta( get_the_ID(), $metakey );

// merge the grandchildren and the children into the same list
$children = array_merge( $children, $grandchildren );

Bu modifikasyon ile fonksiyon şimdi çocukları, çocuk çocuklarını, çocuk çocuk çocuklarını alır ..... vb.

Sonunda, aşağıdaki gibi kimlikler almak için dizideki değerleri kesebilirsiniz:

$post_ids = array_keys( $children );
$q = new WP_Query( array( 'post__in' => $post_ids );
// etc

Bu stratejiyi kullanarak meta anahtar değerini başka bir metrikle değiştirebilir veya özyinelemeli işlevleri başka şekillerde kullanabilirsiniz.

Tam kod sadece birkaç saniye temel anlama ve hızlı kopyala yapıştırma gerektirdiğinden, tam kopyala yapıştırma kod bloğuyla zekanıza hakaret etmem.

Avantajları

  • Herhangi bir yazı tipi ve veri formu için değişiklik çalışmaları ile
  • İç içe işaretleme oluşturmak için değiştirilebilir
  • Döndürülen dizileri geçici olarak yerleştirerek hızlandırmak için kolayca önbellekleyin
  • WP_Query sonuna sayfalama uygulanarak sayfalama ile ayarlanabilir

Karşılaşacağınız Sorunlar

  • Onları bulana kadar kaç çocuğun olduğunu bilmenin hiçbir yolu yoktur, bu nedenle performans maliyetleri ölçeklendirilmez
  • İstediğiniz çok fazla sorgu oluşturacak ve içerdiği potansiyel derinlikler nedeniyle doğası gereği maliyetli olacaktır.

Benim önerim

Sayfa hiyerarşinizi düzleştirmenizi veya bunun yerine bir sınıflandırma kullanmanızı öneririm. Örneğin, yayınları derecelendiriyorsanız, 1,2,3,4 ve 5 vb. Terimler içeren bir Sayfa Derecelendirmesi sınıflandırmasına sahip olursunuz.

Alternatif olarak, gezinme menülerini kullanın ve bu sorunu tamamen atlayın


3

Mevcut tüm alt sayfaları tekrar edin

İşte yinelemeli bir yaklaşım get_children. Şunlara aşağıdakileri ekleyin functions.php:

function get_all_subpages($page, $args = '', $output = OBJECT) {
    // Validate 'page' parameter
    if (! is_numeric($page))
        $page = 0;

    // Set up args
    $default_args = array(
        'post_type' => 'page',
    );
    if (empty($args))
        $args = array();
    elseif (! is_array($args))
        if (is_string($args))
            parse_str($args, $args);
        else
            $args = array();
    $args = array_merge($default_args, $args);
    $args['post_parent'] = $page;

    // Validate 'output' parameter
    $valid_output = array(OBJECT, ARRAY_A, ARRAY_N);
    if (! in_array($output, $valid_output))
        $output = OBJECT;

    // Get children
    $subpages = array();
    $children = get_children($args, $output);
    foreach ($children as $child) {
        $subpages[] = $child;

        if (OBJECT === $output)
            $page = $child->ID;
        elseif (ARRAY_A === $output)
            $page = $child['ID'];
        else
            $page = $child[0];

        // Get subpages by recursion
        $subpages = array_merge($subpages, get_all_subpages($page, $args, $output));
    }

    return $subpages;
}

Bu nasıl kullanılır

Yukarıdaki işlevi istediğiniz yerde kullanın, örneğin şöyle:

$all_current_subpages = get_all_subpages(0);

İşlev bir argsparametreyi (sorgu dizesi veya dizisi) ve bir outputtürü (yukarıya bakın) desteklemez.

Böylece şu şekilde de kullanabilirsiniz:

$args = array(
    'post_status' => 'private',
    'order_by' => 'post_date',
    'order' => 'DESC',
);
$all_current_subpages = get_all_subpages(42, $args, ARRAY_A);

Ve bağımlılık nedeniyle get_children=> get_posts=> WP_Querybaşlangıçta bu sorunun yazarı tarafından talep edildiği gibi meta değerleri kullanabilirsiniz.



2

Bir üst sayfanın tüm çocuk kimliklerini alan özyinelemeli bir işlev yaptım. Kimlikleri aldıktan sonra, sayfalar için sorgu yaparız ve sonuçları meta anahtar / değer ile sıralayabiliriz.

// Gets all the children ids of post_parent
function _get_children_ids( $post_parent ) {
    $results = new WP_Query( array(
        'post_type' => 'page',
        'post_parent' => $post_parent
    ) );

    $child_ids = array();
    if ( $results->found_posts > 0 )
        foreach ( $results->posts as $post ) // add each child id to array
            $child_ids[] = $post->ID;

    if ( ! empty( $child_ids ) )
        foreach ( $child_ids as $child_id ) // add further children to array
            $child_ids = array_merge( $child_ids, _get_children_ids( $child_id ) );

    return $child_ids;
}

$children_ids = _get_children_ids( 9 ); // use your numeric page id or get_the_id()

$results = new WP_Query( array(
    'post_type'   => 'page',
    'post__in'   => $children_ids
    #'meta_key'   => 'meta_key', // your meta key
    #'orderby'    => 'meta_key',
    /* 'meta_query' => array( // optional meta_query
        array(
            'key' => 'meta_key', // key
            'value' => array(3, 4), // values
            'compare' => 'IN', // operator
        )
    ) */
) );

var_dump( $results );

Çocukları meta anahtar / değere göre hiyerarşik bir şekilde sıralamanız gerekirse, meta_key ve order_by değerlerini _get_children_ids işlevindeki (son WP_Query yerine) WP_Query'ye geçirmelisiniz.

Değilse, tüm alt kimliği almak için daha basit bir yöntem:

$children = get_pages( 'child_of=9');

$children_ids = array();
if ( ! empty( $children ) )
    foreach ( $children as $post )
        $children_ids[] = $post->ID;

-1

BU ÇALIŞMAYI YAPIYORUM, SADECE SAYFANIZA KODU YAPMAK İSTİYORUM.PHP DOSYASI

//REDIRECT TO FIRST CHILD FROM PARENT PAGE

// Build WP_Query() argument array
$page_tree_query_args = array(
    'post_parent' => $post -> ID,
    'post_type' => 'page',
    'order' => 'asc'
);
// Get child pages as a WP_Query() object
$page_tree_query = new WP_Query( $page_tree_query_args );
if(!empty($page_tree_query -> posts)){
    $first_subpage = $page_tree_query -> posts[0] -> ID;
    wp_redirect( get_permalink( $first_subpage ) );
    exit;   
}

Bu A) çalışmıyor ( $post -> ID?), B) ne istendi değil, C) çok iyi açıklanmadı.
tfrommen
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.