44

Im trying to build a little site using XML instead of a database.

I would like to build a next and prev button which will work relative to the content I have displayed.

I found the php function next() and prev() as well as current() but I do not know how to set the pointer to a specific position to be able to navigate relative to the current page.

$list=array('page1','page2','page3')

eg if im displaying contents of page2 how could I tell php i am at $list[1] so that next($list) shows page3?

Thanks in advance

chris
  • 2,913
  • 4
  • 43
  • 48
  • 1
    This is a little late, but it might help someone. You can use [array_slice](http://php.net/manual/en/function.array-slice.php) to get the exact key/value of an array from a specific position. – machineaddict Mar 26 '15 at 10:58

9 Answers9

41

If your array is always indexed consistently (eg. 'page1' is always at index '0'), it's fairly simple:

$List = array('page1', 'page2', 'page3', 'page4', 'page5');
$CurrentPage = 3; // 'page4'

while (key($List) !== $CurrentPage) next($List); // Advance until there's a match

I personally don't rely on automatic indexing because there's always a chance that the automatic index might change. You should consider explicitly defining the keys:

$List = array(
    '1' => 'page1',
    '2' => 'page2',
    '3' => 'page3',
);

EDIT: If you want to test the values of the array (instead of the keys), use current():

while (current($List) !== $CurrentPage) next($List);
matpie
  • 17,033
  • 9
  • 61
  • 82
  • 1
    Unfortunately there isn't a pointer manipulator function to which you can pass an index. next, current, reset, end, etc, that's all you have. The above is the correct solution if you must use PHP's internal pointer and not a plain old array subscript index. – Trey Apr 27 '09 at 23:16
  • how would I match based on the value of the array eg page1 instead of the position 1? – chris Apr 27 '09 at 23:34
  • 2
    Actually, you will want to use `current()`. in_array is for seeing if a value is in an array. http://php.net/current – matpie Apr 28 '09 at 07:14
  • 13
    If the array doesn't contain the key, your code would end in an infinite loop. You should check if the pointer didn't reach the end: `while (key($List) !== $CurrentPage && key($List) !== null) next($List);` – VaclavSir Sep 04 '14 at 09:49
7

Using the functions below, you can get the next and previous values of the array. If current value is not valid or it is the last (first - for prev) value in the array, then:

  • the function getNextVal(...) returns the first element value
  • the function getPrevVal(...) returns the last element value

The functions are cyclic.

function getNextVal(&$array, $curr_val)
{
    $next = 0;
    reset($array);

    do
    {
        $tmp_val = current($array);
        $res = next($array);
    } while ( ($tmp_val != $curr_val) && $res );

    if( $res )
    {
        $next = current($array);
    }

    return $next;
}

function getPrevVal(&$array, $curr_val)
{
    end($array);
    $prev = current($array);

    do
    {
        $tmp_val = current($array);
        $res = prev($array);
    } while ( ($tmp_val != $curr_val) && $res );

    if( $res )
    {
        $prev = current($array);
    }

    return $prev;
}
Andrei Krivoshei
  • 715
  • 7
  • 16
  • There is an error in getNextVal(). When declaring $next in line 1, it should be $next = reset($array);. Otherwise for the last index you will get 0 instead of the 1st index of the array (cyclic). – Shivaas Jan 31 '11 at 11:01
4

Using the functions below, you can get the next and previous KEYs of the array. If current key is not valid or it is the last (first - for prev) key in the array, then:

  • the function getNext(...) returns 0 (the first element key)
  • the function getPrev(...) returns the key of the last array element

The functions are cyclic.

function getNext(&$array, $curr_key)
{
    $next = 0;
    reset($array);

    do
    {
        $tmp_key = key($array);
        $res = next($array);
    } while ( ($tmp_key != $curr_key) && $res );

    if( $res )
    {
        $next = key($array);
    }

    return $next;
}

function getPrev(&$array, $curr_key)
{
    end($array);
    $prev = key($array);

    do
    {
        $tmp_key = key($array);
        $res = prev($array);
    } while ( ($tmp_key != $curr_key) && $res );

    if( $res )
    {
        $prev = key($array);
    }

    return $prev;
}
Andrei Krivoshei
  • 715
  • 7
  • 16
3

another aproach without loops or search.

list($prev,$next) = getPrevNext($oObjects,$sCurrentKey);

function getPrevNext($aArray,$key){
    $aKeys = array_keys($aArray); //every element of aKeys is obviously unique
    $aIndices = array_flip($aKeys); //so array can be flipped without risk
    $i = $aIndices[$key]; //index of key in aKeys
    if ($i > 0) $prev = $aArray[$aKeys[$i-1]]; //use previous key in aArray
    if ($i < count($aKeys)-1) $next = $aArray[$aKeys[$i+1]]; //use next key in aArray
    return array($prev,$next);
}
tjungcl
  • 31
  • 1
2

The internal array pointer is mainly used for looping over an array within one PHP script. I wouldn't recommend using it for moving from page to page.

For that, just keep track of the page number and the page size (number of items per page). Then, when you're loading another page, you can use them to decide which array items to show. For example:

$pageNum = $_GET["pageNum"];
$pageSize = 10;
$startIndex = ($pageNum - 1) * $pageSize;
$endIndex = ($startIndex + $pageSize) - 1;

(or something similar)

JW.
  • 50,691
  • 36
  • 115
  • 143
1

I use this code for set internal pointer with key of array.

reset($List);
while (key($List) !== $id && key($List) !== null) next($List);
if(key($List) === null) end($List);

After that you can use prev() or next().

Update follow notice from @VaclavSir

EThaiZone
  • 311
  • 1
  • 8
  • The end of the array is better detectable with the `key` function: `if(key($List) === null) end($List);` Because there can be a `false` value in the array, but there can't be a `null` as a key. – VaclavSir Sep 04 '14 at 09:56
0

Try this

 public function getNextVal(&$array, $curr_val){

    foreach($array as $k=>$v){
        if($v['your_key'] == $curr_val){
            if(isset($array[$k+1]))
                return $array[$k+1];
            else
                return $array[0];
        }
    }

}

public function getPrevVal(&$array, $curr_val){

    foreach($array as $k=>$v){
        if($v['your_key'] == $curr_val){
            if(isset($array[$k-1]))
                return $array[$k-1];
            else
                return end($array);
        }
    }
}

for array like this:

array (size=3)
0 => 
array (size=11)
  'id' => string '21' (length=2)
  'cat' => string '1' (length=1)
  'gal' => string '1' (length=1)
  'type' => string 'image' (length=5)
  'name' => string 'chalk_art_dies-irea_2nd_pic' (length=27)
  'permalink' => string 'chalk-art-dies-irea-2nd-pic' (length=27)
  'url' => string 'rxNsPoEiJboJQ32.jpg' (length=19)
  'content' => string '' (length=0)
  'date' => string '1432076359' (length=10)
  'order' => string '20' (length=2)
  'views' => string '0' (length=1)
 1 => 
   array (size=11)
  'id' => string '10' (length=2)
  'cat' => string '1' (length=1)
  'gal' => string '1' (length=1)
  'type' => string 'image' (length=5)
  'name' => string '3dchalkart' (length=10)
  'permalink' => string '3dchalkart' (length=10)
  'url' => string 's57i5DKueUEI4lu.jpg' (length=19)
  'content' => string '' (length=0)
  'date' => string '1432076358' (length=10)
  'order' => string '9' (length=1)
  'views' => string '0' (length=1)
  2 => 
Burhan Ibrahimi
  • 367
  • 3
  • 14
0

current and next functions are deprecated for objects since PHP 8.1

Here is a way to do it using ArrayIterator

Keys

$list = new ArrayIterator(array('page1', 'page2', 'page3'));
$currentPage = 1;

$list->seek($currentPage);
echo $list->current(); // 'page2'

Values

$list = new ArrayIterator(array('page1', 'page2', 'page3'));

while ($list->current() !== 'page2') {
    $list->next();
}

echo $list->current(); // 'page2'
Reynadan
  • 649
  • 4
  • 18
-1

Here's the complete @tjunglc 's approach with looping:

protected function getPrevNext($aArray,$key)
{
    $aKeys = array_keys($aArray); //every element of aKeys is obviously unique
    $aIndices = array_flip($aKeys); //so array can be flipped without risk
    $i = $aIndices[$key]; //index of key in aKeys
    if ($i > 0) $prev = $aArray[$aKeys[$i-1]]; //use previous key in aArray
    if ($i < count($aKeys)-1) $next = $aArray[$aKeys[$i+1]]; //use next key in aArray
    if (!isset($prev)) $prev = end($aArray);
    if (!isset($next)) $next = reset($aArray);
    return array($prev,$next);
}

Oh and thankx @tjunglc for this :)

Blaž Oražem
  • 862
  • 7
  • 11