2012-01-15 12 views

答えて

6

私はあなたが探しているそれらのIDを取得する機能を作った。私はあなたがモデルでそれを宣言することをお勧め:それは、次または前のレコードの対応するIDを返します

YourModel::getNextOrPrevId($id /*(current id)*/, "prev" /*(or "next")*/); 

public static function getNextOrPrevId($currentId, $nextOrPrev) 
{ 
    $records=NULL; 
    if($nextOrPrev == "prev") 
     $order="id DESC"; 
    if($nextOrPrev == "next") 
     $order="id ASC"; 

    $records=YourModel::model()->findAll(
     array('select'=>'id', 'order'=>$order) 
     ); 

    foreach($records as $i=>$r) 
     if($r->id == $currentId) 
      return isset($records[$i+1]->id) ? $records[$i+1]->id : NULL; 

    return NULL; 
} 

だから、それを使用するためにあなたがしなければならないすべてはこれです。

私はそれを試していませんでしたので、試してみて、何かがうまくいかない場合は教えてください。

+0

と私はPhotoController – Abudayah

+0

致命的なエラーでその関数を書く:未定義のメソッドの写真:: getPrevOrNextId(の呼び出し) – Abudayah

2

他の機能に情報を渡すためのプライベートvarを作成します。モデルで

class Model1 ..... 
{ 
    ... 
    private _prevId = null; 
    private _nextId = null; 
    ... 

    public function afterFind() //this function will be called after your every find call 
    { 
    //find/calculate/set $this->_prevId; 
    //find/calculate/set $this->_nextId; 
    } 

    public function getPrevId() { 
     return $this->prevId; 
    } 

    public function getNextId() { 
     return $this->nextId; 
    } 

} 

がViewDetalリンクで生成されたコードを確認し、配列( 'ID' =に

$model(or $data)->prevId/nextId 

を使用して_VIEWファイルの中前/ネットリンクについて修正>#)セクション。

6

私はYii2の私のモデルでは、以下の機能を追加しました:

public function getNext() { 
    $next = $this->find()->where(['>', 'id', $this->id])->one(); 
    return $next; 
} 

public function getPrev() { 
    $prev = $this->find()->where(['<', 'id', $this->id])->orderBy('id desc')->one(); 
    return $prev; 
} 
+1

これまでのところ最良の答えです。ほとんどの人は - > all()を使用しますが、リソースIMOの無駄です。 – vanarie

1

を元の答えを取り、少しのクリーンアップとYii2のためにそれを適応:

/** 
* [nextOrPrev description] 
* @source http://stackoverflow.com/questions/8872101/get-next-previous-id-record-in-database-on-yii 
* @param integer $currentId [description] 
* @param string $nextOrPrev [description] 
* @return integer   [description] 
*/ 
public static function nextOrPrev($currentId, $nextOrPrev = 'next') 
{ 
    $order = ($nextOrPrev == 'next') ? 'id ASC' : 'id DESC'; 
    $records = \namespace\path\Model::find()->orderBy($order)->all(); 

    foreach ($records as $i => $r) { 

     if ($r->id == $currentId) { 
      return ($records[$i+1]->id ? $records[$i+1]->id : NULL); 
     } 

    } 

    return false; 
} 
0

とき、以前のソリューションは問題があります最初または最後のレコードを取得し、データベースへの複数の呼び出しを行っています。ここでは1つのクエリで動作し、私の作業溶液は、エンド・オブ・テーブルを処理し、エンド・オブ・テーブルにあるボタンを無効にします。

public static function NextOrPrev($currentId) 
{ 
    $records = <Table>::find()->orderBy('id DESC')->all(); 

    foreach ($records as $i => $record) { 
     if ($record->id == $currentId) { 
      $next = isset($records[$i - 1]->id)?$records[$i - 1]->id:null; 
      $prev = isset($records[$i + 1]->id)?$records[$i + 1]->id:null; 
      break; 
     } 
    } 
    return ['next'=>$next, 'prev'=>$prev]; 
} 

コントローラ内::

モデル内

ビュー内

 public function actionView($id) 
{ 
    $index = <modelName>::nextOrPrev($id); 
    $nextID = $index['next']; 
    $disableNext = ($nextID===null)?'disabled':null; 
    $prevID = $index['prev']; 
    $disablePrev = ($prevID===null)?'disabled':null; 

    // usual detail-view model 
    $model = $this->findModel($id); 

    return $this->render('view', [ 
     'model' => $model, 
     'nextID'=>$nextID, 
     'prevID'=>$prevID, 
     'disableNext'=>$disableNext, 
     'disablePrev'=>$disablePrev, 
    ]); 
} 

<?= Html::a('Next', ['view', 'id' => $nextID], ['class' => 'btn btn-primary r-align btn-sm '.$disableNext]) ?> 
<?= Html::a('Prev', ['view', 'id' => $prevID], ['class' => 'btn btn-primary r-align btn-sm '.$disablePrev]) ?> 
1

私の実装はSearchModelに基づいています。

コントローラー:

public function actionView($id) 
{ 
    // ... some code before 

    // Get prev and next orders 
    // Setup search model 
    $searchModel = new OrderSearch(); 
    $orderSearch = \yii\helpers\Json::decode(Yii::$app->getRequest()->getCookies()->getValue('s-' . Yii::$app->user->identity->id)); 
    $params = []; 
    if (!empty($orderSearch)){ 
     $params['OrderSearch'] = $orderSearch; 
    } 
    $dataProvider = $searchModel->search($params); 
    $sort = $dataProvider->getSort(); 
    $sort->defaultOrder = ['created' => SORT_DESC]; 
    $dataProvider->setSort($sort); 

    // Get page number by searching current ID key in models 
    $pageNum = array_search($id, array_column($dataProvider->getModels(), 'id')); 
    $count = $dataProvider->getCount(); 
    $dataProvider->pagination->pageSize = 1; 

    $orderPrev = $orderNext = null; 
    if ($pageNum > 0) { 
     $dataProvider->pagination->setPage($pageNum - 1); 
     $dataProvider->refresh(); 
     $orderPrev = $dataProvider->getModels()[0]; 
    } 
    if ($pageNum < $count) { 
     $dataProvider->pagination->setPage($pageNum + 1); 
     $dataProvider->refresh(); 
     $orderNext = $dataProvider->getModels()[0]; 
    } 
    // ... some code after 
} 

OrderSearch:

public function search($params) 
{ 
    // Set cookie with search params 
    Yii::$app->response->cookies->add(new \yii\web\Cookie([ 
     'name' => 's-' . Yii::$app->user->identity->id, 
     'value' => \yii\helpers\Json::encode($params['OrderSearch']), 
     'expire' => 2147483647, 
    ])); 

    // ... search model code here ... 
} 

PS:あなたは、オブジェクトの配列のarray_columnを使用できるかどうかを確認してください。 これはPHP 7+でうまくいきますが、下位バージョンでは自分でidを抽出する必要があります。おそらく、array_walkまたはarray_filterをPHP 5で使用することをお勧めします。4+

関連する問題