WordPress.org

Make WordPress Core

Ticket #7743: 7743_paged_walker.diff

File 7743_paged_walker.diff, 3.8 KB (added by hailin, 13 years ago)

patch

  • C:/xampp/htdocs/wordpress_trunk/wp-includes/classes.php

     
    409409
    410410/*
    411411 * A class for displaying various tree-like structures.
     412 * The algorithm achieves O(n) in complexity
    412413 * Extend the Walker class to use it, see examples at the bottom
    413414 */
    414415class Walker {
     
    438439
    439440                $id = $element->$id_field;
    440441
    441                 // descend only the depth is right and there are chilrens for this element
     442                // descend only when the depth is right and there are childrens for this element
    442443                if ( ($max_depth == 0 || $max_depth > $depth+1 ) && isset( $children_elements[$id]) ) {
    443444
    444445                        foreach( $children_elements[ $id ] as $child ){
     
    543544
    544545                 return $output;
    545546        }
     547       
     548        /**
     549         * paged_walk() - produce a page of nested elements
     550         *
     551         * Given an array of hierarchical elements, the maximum depth, a specific page number,
     552         * and number of elements per page, this function first determines all top level root elements
     553         * belonging to that page, then lists them and all of their children in hierarchical order.
     554         *
     555         * @package WordPress
     556         * @since 2.7
     557         * @param $max_depth = 0  means display all levels; $max_depth > 0  specifies the number of display levels.
     558         * @param $page_num the specific page number, beginning with 1.
     559         * @return XHTML of the specified page of elements
     560         */
     561        function paged_walk( $elements, $max_depth, $page_num, $per_page ) {
     562       
     563                /* sanity check */
     564                if ( empty($elements) || $max_depth<0 || $page_num<1 || $per_page<0 )
     565                        return '';
     566               
     567                $args = array_slice( func_get_args(), 4 );
     568                $output = '';
     569               
     570                $id_field = $this->db_fields['id'];
     571                $parent_field = $this->db_fields['parent'];
     572               
     573                /*
     574                 * seperate elements into two buckets: top level and children elements
     575                 * children_elements is two dimensional array, eg.
     576                 * children_elements[10][] contains all sub-elements whose parent is 10.
     577                 */
     578                $top_level_elements = array();
     579                $children_elements  = array();
     580                foreach ( $elements as $e) {
     581                        if ( 0 == $e->$parent_field )
     582                                $top_level_elements[] = $e;
     583                        else
     584                                $children_elements[ $e->$parent_field ][] = $e;
     585                }
     586       
     587                $count = -1;
     588                $start = ( (int)$page_num - 1 ) * (int)$per_page;
     589                $end   = $start + $per_page;
     590                $total_top = count( $top_level_elements );
     591
     592                foreach( $top_level_elements as $e ){
     593                               
     594                        $count++;
     595                       
     596                        //for the last page, need to unset earlier children in order to keep track of orphans
     597                        if ( $end >= $total_top && $count < $start )
     598                                        $this->unset_children( $e, $children_elements );
     599                               
     600                        if ( $count < $start )
     601                                continue;
     602                               
     603                        if ( $count >= $end )
     604                                break;
     605                                       
     606                        $this->display_element( $e, $children_elements, $max_depth, 0, $args, $output );
     607                }
     608                       
     609                if ( $end >= $total_top && count( $children_elements ) > 0 ){
     610                        $empty_array = array();
     611                        foreach ( $children_elements as $orphans )
     612                                foreach( $orphans as $op )
     613                                        $this->display_element( $op, $empty_array, 1, 0, $args, $output );
     614                }
     615               
     616                return $output;
     617        }
     618       
     619        function get_number_of_root_elements( $elements ){
     620               
     621                $num = 0;
     622                $parent_field = $this->db_fields['parent'];
     623               
     624                foreach ( $elements as $e) {
     625                        if ( 0 == $e->$parent_field )
     626                                $num++;
     627                }
     628                return $num;
     629        }
     630       
     631        // unset all the children for a given top level element
     632        function unset_children( $e, &$children_elements ){
     633       
     634                if ( !$e || !$children_elements )
     635                        return;
     636                       
     637                $id_field = $this->db_fields['id'];
     638                $id = $e->$id_field;
     639               
     640                foreach ( (array)$children_elements[$id] as $child )
     641                        $this->unset_children( $child, $children_elements );
     642                       
     643                unset( $children_elements[$id] );
     644
     645        }
    546646}
    547647
    548648class Walker_Page extends Walker {