<?php
namespace SabaiApps\Framework\Model\EntityCollection;

use SabaiApps\Framework\Model\Model;
use SabaiApps\Framework\Model\AbstractEntity;
use SabaiApps\Framework\DB\AbstractRowset;

/**
 * RowsetEntityCollection class for managing collections of entities retrieved from a database rowset.
 * Provides methods for iterating and accessing entities within the rowset.
 */
abstract class RowsetEntityCollection extends AbstractEntityCollection {

	protected $_rs, $_emptyEntity, $_count;

	/**
	 * Constructor.
	 *
	 * @param string         $name Name of the entity.
	 * @param AbstractRowset $rs Rowset object containing entity data.
	 * @param AbstractEntity $emptyEntity Empty entity instance for cloning.
	 * @param Model          $model Model instance.
	 */
	public function __construct( $name, AbstractRowset $rs, AbstractEntity $emptyEntity, Model $model ) {
		parent::__construct( $model, $name );
		$this->_rs          = $rs;
		$this->_emptyEntity = $emptyEntity;
	}

	/**
	 * Counts the number of entities in the rowset.
	 *
	 * @return int Number of entities.
	 */
	#[\ReturnTypeWillChange]
	public function count() {
		if ( ! isset( $this->_count ) ) {
			$this->_count = count( $this->_rs );
		}

		return $this->_count;
	}

	/**
	 * Checks if the current entity is valid.
	 *
	 * @return bool True if valid, false otherwise.
	 */
	#[\ReturnTypeWillChange]
	public function valid() {
		return $this->_key < $this->count();
	}

	/**
	 * Gets the current entity by index.
	 *
	 * @param int $index Index of the entity.
	 * @return AbstractEntity Current entity.
	 */
	public function getCurrent( $index ) {
		$this->_rs->seek( $index );
		$entity = clone $this->_emptyEntity;
		$this->_loadRow( $entity, $this->_rs->fetchAssoc() );

		return $entity;
	}

	/**
	 * Loads a row into an entity.
	 *
	 * @param AbstractEntity $entity Entity instance.
	 * @param array          $row Row data.
	 */
	protected function _loadRow( AbstractEntity $entity, array $row ) {
		$entity->initVars( $row );
	}
}
