/**
* Recursively render this view.
*/
public function recursiveRender()
{
// get data source
if (!$this->source) {
// force grid sorting implemented in Grid_Advanced
if ($this->owner instanceof Grid_Advanced) {
$this->owner->getIterator();
}
// set data source for Paginator
if ($this->owner->model) {
$this->setSource($this->owner->model);
} elseif ($this->owner->dq) {
$this->setSource($this->owner->dq);
} else {
throw $this->exception('Unable to find source for Paginator');
}
}
// calculate found rows
if ($this->source instanceof DB_dsql) {
$this->source->preexec();
$this->found_rows = $this->source->foundRows();
} elseif ($this->source instanceof Model) {
$this->found_rows = (int) $this->source->count();
} else {
$this->found_rows = count($this->source);
}
// calculate current page and total pages
$this->cur_page = (int) floor($this->skip / $this->ipp) + 1;
$this->total_pages = (int) ceil($this->found_rows / $this->ipp);
if ($this->cur_page > $this->total_pages || $this->cur_page == 1 && $this->skip != 0) {
$this->cur_page = 1;
if ($this->memorize) {
$this->memorize('skip', $this->skip = 0);
}
if ($this->source instanceof DB_dsql) {
$this->source->limit($this->ipp, $this->skip);
$this->source->rewind();
// re-execute the query
} elseif ($this->source instanceof Model) {
$this->source->setLimit($this->ipp, $this->skip);
} else {
// Imants: not sure if this is correct, but it was like this before
$this->source->setLimit($this->ipp, $this->skip);
}
}
// no need for paginator if there is only one page
if ($this->total_pages <= 1) {
return $this->destroy();
}
if ($this->cur_page > 1) {
/** @type View $v */
$v = $this->add('View', null, 'prev');
$v->setElement('a')->setAttr('href', $this->app->url($this->base_page, $u = array($this->skip_var => $pn = max(0, $this->skip - $this->ipp))))->setAttr('data-skip', $pn)->set('« Prev');
} else {
$this->template->tryDel('prev');
}
if ($this->cur_page < $this->total_pages) {
/** @type View $v */
$v = $this->add('View', null, 'next');
$v->setElement('a')->setAttr('href', $this->app->url($this->base_page, $u = array($this->skip_var => $pn = $this->skip + $this->ipp)))->setAttr('data-skip', $pn)->set('Next »');
} else {
$this->template->tryDel('next');
}
// First page
if ($this->cur_page > $this->range + 1) {
/** @type View $v */
$v = $this->add('View', null, 'first');
$v->setElement('a')->setAttr('href', $this->app->url($this->base_page, $u = array($this->skip_var => $pn = max(0, 0))))->setAttr('data-skip', $pn)->set('1');
if ($this->cur_page > $this->range + 2) {
/** @type View $v */
$v = $this->add('View', null, 'points_left');
$v->setElement('span')->set('...');
}
}
// Last page
if ($this->cur_page < $this->total_pages - $this->range) {
/** @type View $v */
$v = $this->add('View', null, 'last');
$v->setElement('a')->setAttr('href', $this->app->url($this->base_page, $u = array($this->skip_var => $pn = max(0, ($this->total_pages - 1) * $this->ipp))))->setAttr('data-skip', $pn)->set($this->total_pages);
if ($this->cur_page < $this->total_pages - $this->range - 1) {
/** @type View $v */
$v = $this->add('View', null, 'points_right');
$v->setElement('span')->set('...');
}
}
// generate source for Paginator Lister (pages, links, labels etc.)
$data = array();
//setting cur as array seems not working in atk4.3. String is working
$tplcur = $this->template->get('cur');
$tplcur = isset($tplcur[0]) ? $tplcur[0] : '';
$range = range(max(1, $this->cur_page - $this->range), min($this->total_pages, $this->cur_page + $this->range));
foreach ($range as $p) {
$data[] = array('href' => $this->app->url($this->base_page, array($this->skip_var => $pn = ($p - 1) * $this->ipp)), 'pn' => $pn, 'cur' => $p == $this->cur_page ? $tplcur : '', 'label' => $p);
}
if ($this->ajax_reload) {
$this->js('click', $this->owner->js()->reload(array($this->skip_var => $this->js()->_selectorThis()->attr('data-skip'))))->_selector('#' . $this->name . ' a');
}
parent::setSource($data);
return parent::recursiveRender();
}