Пример #1
0
/**
 * Find next and previous articles relative to a provided threshold level
 *
 * @param int $id The "pivot" article's id; use zero (0) to indicate $thisarticle
 * @param scalar $threshold The value to compare against if $id != 0
 * @param string $s string Optional section restriction if $id != 0
 * @return array An array populated with article data from the next and previous article
 */
function getNextPrev($id = 0, $threshold = null, $s = '')
{
    if ($id !== 0) {
        // Pivot is specific article by ID: In lack of further information, revert to default sort order 'Posted desc'
        $atts = filterAtts(array('sortby' => 'Posted', 'sortdir' => 'desc'));
    } else {
        // Pivot is $thisarticle: Use article attributes to find its neighbours
        assert_article();
        global $thisarticle;
        if (!is_array($thisarticle)) {
            return array();
        }
        $atts = filterAtts();
        $m = preg_split('/\\s+/', $atts['sort']);
        if (empty($m[0]) || count($m) > 2 || preg_match('/[),]/', $m[0])) {
            // Either no explicit sort order or a complex clause, e.g. 'foo asc, bar desc' or 'FUNC(foo,bar) asc'
            // Fall back to chronologically descending order
            $atts['sortby'] = 'Posted';
            $atts['sortdir'] = 'desc';
        } else {
            // sort is like 'foo asc'
            $atts['sortby'] = $m[0];
            $atts['sortdir'] = isset($m[1]) && strtolower($m[1]) == 'desc' ? 'desc' : 'asc';
        }
        // atts w/ special treatment
        switch ($atts['sortby']) {
            case 'Posted':
                $threshold = 'from_unixtime(' . doSlash($thisarticle['posted']) . ')';
                $threshold_type = 'cooked';
                break;
            case 'Expires':
                $threshold = 'from_unixtime(' . doSlash($thisarticle['expires']) . ')';
                $threshold_type = 'cooked';
                break;
            case 'LastMod':
                $threshold = 'from_unixtime(' . doSlash($thisarticle['modified']) . ')';
                $threshold_type = 'cooked';
                break;
            default:
                // retrieve current threshold value per sort column from $thisarticle
                $acm = array_flip(article_column_map());
                $key = $acm[$atts['sortby']];
                $threshold = $thisarticle[$key];
                $threshold_type = 'raw';
                break;
        }
        $s = $thisarticle['section'];
    }
    $thenext = getNeighbour($threshold, $s, '>', $atts, $threshold_type);
    $out['next_id'] = $thenext ? $thenext['ID'] : '';
    $out['next_title'] = $thenext ? $thenext['Title'] : '';
    $out['next_utitle'] = $thenext ? $thenext['url_title'] : '';
    $out['next_posted'] = $thenext ? $thenext['uposted'] : '';
    $theprev = getNeighbour($threshold, $s, '<', $atts, $threshold_type);
    $out['prev_id'] = $theprev ? $theprev['ID'] : '';
    $out['prev_title'] = $theprev ? $theprev['Title'] : '';
    $out['prev_utitle'] = $theprev ? $theprev['url_title'] : '';
    $out['prev_posted'] = $theprev ? $theprev['uposted'] : '';
    return $out;
}
Пример #2
0
/**
 * Find next and previous articles relative to a provided threshold level.
 *
 * @param  int    $id        The "pivot" article's id; use zero (0) to indicate $thisarticle
 * @param  scalar $threshold The value to compare against if $id != 0
 * @param  string $s         Optional section restriction if $id != 0
 * @return array An array populated with article data
 */
function getNextPrev($id = 0, $threshold = null, $s = '')
{
    if ($id !== 0) {
        // Pivot is specific article by ID: In lack of further information,
        // revert to default sort order 'Posted desc'.
        $atts = filterAtts(array('sortby' => "Posted", 'sortdir' => "DESC"));
    } else {
        // Pivot is $thisarticle: Use article attributes to find its neighbours.
        assert_article();
        global $thisarticle;
        if (!is_array($thisarticle)) {
            return array();
        }
        $atts = filterAtts();
        $m = preg_split('/\\s+/', $atts['sort']);
        // If in doubt, fall back to chronologically descending order.
        if (empty($m[0]) || count($m) > 2 || !preg_match('/^(?:[0-9a-zA-Z$_\\x{0080}-\\x{FFFF}]+|`[\\x{0001}-\\x{FFFF}]+`)$/u', $m[0])) {
            $atts['sortby'] = "Posted";
            $atts['sortdir'] = "DESC";
        } else {
            // Sort is like 'foo asc'.
            $atts['sortby'] = $m[0];
            $atts['sortdir'] = isset($m[1]) && strtolower($m[1]) == 'desc' ? "DESC" : "ASC";
        }
        // Attributes with special treatment.
        switch ($atts['sortby']) {
            case 'Posted':
                $threshold = "FROM_UNIXTIME(" . doSlash($thisarticle['posted']) . ")";
                $threshold_type = 'cooked';
                break;
            case 'Expires':
                $threshold = "FROM_UNIXTIME(" . doSlash($thisarticle['expires']) . ")";
                $threshold_type = 'cooked';
                break;
            case 'LastMod':
                $threshold = "FROM_UNIXTIME(" . doSlash($thisarticle['modified']) . ")";
                $threshold_type = 'cooked';
                break;
            default:
                // Retrieve current threshold value per sort column from $thisarticle.
                $acm = array_flip(article_column_map());
                $key = $acm[$atts['sortby']];
                $threshold = $thisarticle[$key];
                $threshold_type = 'raw';
                break;
        }
        $s = $thisarticle['section'];
    }
    $out['next'] = getNeighbour($threshold, $s, '>', $atts, $threshold_type);
    $out['prev'] = getNeighbour($threshold, $s, '<', $atts, $threshold_type);
    return $out;
}