BufferedReader.class.php

Go to the documentation of this file.
00001 <?php
00002 /***************************************************************************
00003  *   Copyright (C) 2007 by Ivan Y. Khvostishkov                            *
00004  *                                                                         *
00005  *   This program is free software; you can redistribute it and/or modify  *
00006  *   it under the terms of the GNU Lesser General Public License as        *
00007  *   published by the Free Software Foundation; either version 3 of the    *
00008  *   License, or (at your option) any later version.                       *
00009  *                                                                         *
00010  ***************************************************************************/
00011 
00015     final class BufferedReader extends Reader
00016     {
00017         private $in             = null;
00018         private $closed         = false;
00019         
00020         private $buffer         = null;
00021         private $bufferLength   = 0;
00022         
00023         private $position       = 0;
00024         private $markPosition   = null;
00025         
00026         public function __construct(Reader $in)
00027         {
00028             $this->in = $in;
00029         }
00030         
00034         public static function create(Reader $in)
00035         {
00036             return new self($in);
00037         }
00038         
00042         public function close()
00043         {
00044             $this->closed = true;
00045             
00046             return $this;
00047         }
00048         
00049         public function isEof()
00050         {
00051             return $this->in->isEof();
00052         }
00053         
00054         public function markSupported()
00055         {
00056             return true;
00057         }
00058         
00062         public function mark()
00063         {
00064             $this->markPosition = $this->position;
00065             
00066             return $this;
00067         }
00068         
00072         public function reset()
00073         {
00074             $this->position = $this->markPosition;
00075             
00076             return $this;
00077         }
00078         
00079         public function available()
00080         {
00081             $this->ensureOpen();
00082             
00083             return ($this->bufferLength - $this->position);
00084         }
00085         
00086         public function read($count)
00087         {
00088             $this->ensureOpen();
00089             
00090             $remainingCount = $count;
00091             $availableCount = $this->available();
00092             
00093             if ($remainingCount <= $availableCount)
00094                 $readFromBuffer = $count;
00095             else
00096                 $readFromBuffer = $availableCount;
00097             
00098             $result = null;
00099             
00100             if ($readFromBuffer > 0) {
00101                 $result = mb_substr(
00102                     $this->buffer,
00103                     $this->position,
00104                     $readFromBuffer
00105                 );
00106                 
00107                 $this->position += $readFromBuffer;
00108                 $remainingCount -= $readFromBuffer;
00109             }
00110             
00111             if ($remainingCount > 0) {
00112                 $remaining = $this->in->read($remainingCount);
00113                 
00114                 if ($this->markPosition !== null) {
00115                     $this->buffer .= $remaining;
00116                     $remainingLength = mb_strlen($remaining);
00117                     
00118                     $this->bufferLength += $remainingLength;
00119                     $this->position += $remainingLength;
00120                 }
00121                 
00122                 if ($remaining !== null)
00123                     $result .= $remaining;
00124             }
00125             
00126             return $result;
00127         }
00128         
00129         /* void */ private function ensureOpen()
00130         {
00131             if ($this->closed)
00132                 throw new IOException('stream has been closed');
00133         }
00134     }
00135 ?>