diff --git a/CHANGELOG.md b/CHANGELOG.md index 94f018b4..a5672cd8 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -27,6 +27,7 @@ and this project adheres to [Semantic Versioning](http://semver.org/). ### BREAKING CHANGE - Standardization of array keys used for style, see the [migration guide](./docs/topics/migration-from-PHPExcel.md). +- Easier usage of PDF writers, and other custom readers and writers, see the [migration guide](./docs/topics/migration-from-PHPExcel.md). ## [1.0.0-beta] - 2017-08-17 diff --git a/docs/index.md b/docs/index.md index 402059b6..a9f59bfb 100644 --- a/docs/index.md +++ b/docs/index.md @@ -19,7 +19,7 @@ spreadsheet file formats, like Excel and LibreOffice Calc. |HTML | ✓ | ✓ | |SYLK | ✓ | | |CSV | ✓ | ✓ | -|PDF (using either the tcPDF, DomPDF or mPDF libraries, which need to be installed separately)| | ✓ | +|PDF (using either the TCPDF, Dompdf or mPDF libraries, which need to be installed separately)| | ✓ | # Getting started diff --git a/docs/topics/migration-from-PHPExcel.md b/docs/topics/migration-from-PHPExcel.md index 1dad7d05..495c3313 100644 --- a/docs/topics/migration-from-PHPExcel.md +++ b/docs/topics/migration-from-PHPExcel.md @@ -43,6 +43,28 @@ Before | After `'PDF'` | `'Pdf'` `'SYLK'` | `'Slk'` +### Simplified IOFactory + +The following methods : + +- `PHPExcel_IOFactory::getSearchLocations()` +- `PHPExcel_IOFactory::setSearchLocations()` +- `PHPExcel_IOFactory::addSearchLocation()` + +were replaced by `IOFactory::registerReader()` and `IOFactory::registerWriter()`. That means +IOFactory now relies on classes autoloading. + +Before: + +```php +\PHPExcel_IOFactory::addSearchLocation($type, $location, $classname); +``` + +After: + +```php +\PhpOffice\PhpSpreadsheet\IOFactory::registerReader($type, $classname); +``` ### Removed deprecated things @@ -148,15 +170,33 @@ autoloading mechanism. ### Writing PDF -`PHPExcel_Settings::getPdfRenderer()` and `PHPExcel_Settings::setPdfRenderer()` -were removed. `PHPExcel_Settings::getPdfRendererName()` and -`PHPExcel_Settings::setPdfRendererName()` were renamed as `setDefaultPdfWriter()` -and `setDefaultPdfWriter()` respectively. And PDF libraries must be installed via -composer. So the only thing to do is to specify a default writer class like so: +PDF libraries must be installed via composer. And the following methods were removed +and are replaced by `IOFactory::registerWriter()` instead: + +- `PHPExcel_Settings::getPdfRenderer()` +- `PHPExcel_Settings::setPdfRenderer()` +- `PHPExcel_Settings::getPdfRendererName()` +- `PHPExcel_Settings::setPdfRendererName()` were renamed as `setDefaultPdfWriter()` + +Before: ```php -$rendererName = \PhpOffice\PhpSpreadsheet\Writer\Pdf\MPDF::class; -\PhpOffice\PhpSpreadsheet\Settings::setDefaultPdfWriter($rendererName); +\PHPExcel_Settings::setPdfRendererName(PHPExcel_Settings::PDF_RENDERER_MPDF); +\PHPExcel_Settings::setPdfRenderer($somePath); +$writer = \PHPExcel_IOFactory::createWriter($spreadsheet, 'PDF'); +``` + +After: + +```php +$writer = \PhpOffice\PhpSpreadsheet\IOFactory::createWriter($spreadsheet, 'Mpdf'); + +// Or alternatively +\PhpOffice\PhpSpreadsheet\IOFactory::registerWriter('Pdf', \PhpOffice\PhpSpreadsheet\Writer\Pdf\Mpdf::class); +$writer = \PhpOffice\PhpSpreadsheet\IOFactory::createWriter($spreadsheet, 'Pdf'); + +// Or alternatively +$writer = new \PhpOffice\PhpSpreadsheet\Writer\Pdf\Mpdf($spreadsheet); ``` ### PclZip and ZipArchive diff --git a/docs/topics/reading-and-writing-to-file.md b/docs/topics/reading-and-writing-to-file.md index b0ef11b1..0e642120 100644 --- a/docs/topics/reading-and-writing-to-file.md +++ b/docs/topics/reading-and-writing-to-file.md @@ -739,7 +739,7 @@ regarding to styling cells, number formatting, ... ### \PhpOffice\PhpSpreadsheet\Writer\Pdf PhpSpreadsheet’s PDF Writer is a wrapper for a 3rd-Party PDF Rendering -library such as tcPDF, mPDF or DomPDF. You must now install a PDF +library such as TCPDF, mPDF or Dompdf. You must now install a PDF rendering library yourself; but PhpSpreadsheet will work with a number of different libraries. @@ -747,9 +747,9 @@ Currently, the following libraries are supported: Library | Downloadable from | PhpSpreadsheet writer --------|-------------------------------------|---------------------- -tcPDF | https://github.com/tecnickcom/tcpdf | TcPdf -mPDF | https://github.com/mpdf/mpdf | MPDF -domPDF | https://github.com/dompdf/dompdf | DomPDF +TCPDF | https://github.com/tecnickcom/tcpdf | Tcpdf +mPDF | https://github.com/mpdf/mpdf | Mpdf +Dompdf | https://github.com/dompdf/dompdf | Dompdf The different libraries have different strengths and weaknesses. Some generate better formatted output than others, some are faster or use @@ -757,19 +757,26 @@ less memory than others, while some generate smaller .pdf files. It is the developers choice which one they wish to use, appropriate to their own circumstances. -Before instantiating a Writer via `IOFactory` to generate PDF output, -you will need to indicate which writer you are using: +You can instantiate a writer with its specific name, like so: ``` php -$rendererName = \PhpOffice\PhpSpreadsheet\Writer\Pdf\MPDF::class; -\PhpOffice\PhpSpreadsheet\Settings::setDefaultPdfWriter($rendererName); -$writer = \PhpOffice\PhpSpreadsheet\IOFactory\IOFactory::createWriter($spreadsheet, 'Pdf'); +$writer = \PhpOffice\PhpSpreadsheet\IOFactory::createWriter($spreadsheet, 'Mpdf'); +``` + +Or you can register which writer you are using with a more generic name, +so you don't need to remember which library you chose, only that you want +to write PDF files: + +``` php +$class = \PhpOffice\PhpSpreadsheet\Writer\Pdf\Mpdf::class; +\PhpOffice\PhpSpreadsheet\IOFactory::registerWriter('Pdf', $class); +$writer = \PhpOffice\PhpSpreadsheet\IOFactory::createWriter($spreadsheet, 'Pdf'); ``` Or you can instantiate directly the writer of your choice like so: ``` php -$writer = \PhpOffice\PhpSpreadsheet\Writer\Pdf\MPDF($spreadsheet); +$writer = \PhpOffice\PhpSpreadsheet\Writer\Pdf\Mpdf($spreadsheet); ``` #### Writing a spreadsheet @@ -778,7 +785,7 @@ Once you have identified the Renderer that you wish to use for PDF generation, you can write a .pdf file using the following code: ``` php -$writer = new \PhpOffice\PhpSpreadsheet\Writer\Pdf\MPDF($spreadsheet); +$writer = new \PhpOffice\PhpSpreadsheet\Writer\Pdf\Mpdf($spreadsheet); $writer->save("05featuredemo.pdf"); ``` @@ -810,7 +817,7 @@ This can be slow on large spreadsheets, and maybe even unwanted. You can however disable formula pre-calculation: ``` php -$writer = new \PhpOffice\PhpSpreadsheet\Writer\Pdf\MPDF($spreadsheet); +$writer = new \PhpOffice\PhpSpreadsheet\Writer\Pdf\Mpdf($spreadsheet); $writer->setPreCalculateFormulas(false); $writer->save("05featuredemo.pdf"); diff --git a/samples/Basic/01_Simple_download_pdf.php b/samples/Basic/01_Simple_download_pdf.php index 7b53c4f2..9a8507c5 100644 --- a/samples/Basic/01_Simple_download_pdf.php +++ b/samples/Basic/01_Simple_download_pdf.php @@ -2,7 +2,6 @@ use PhpOffice\PhpSpreadsheet\Helper\Sample; use PhpOffice\PhpSpreadsheet\IOFactory; -use PhpOffice\PhpSpreadsheet\Settings; use PhpOffice\PhpSpreadsheet\Spreadsheet; require_once __DIR__ . '/../../src/Bootstrap.php'; @@ -14,10 +13,6 @@ if ($helper->isCli()) { return; } -// Change these values to select the Rendering library that you wish to use -// and its directory location on your server -$rendererName = \PhpOffice\PhpSpreadsheet\Writer\Pdf\MPDF::class; - // Create new Spreadsheet object $spreadsheet = new Spreadsheet(); @@ -49,7 +44,7 @@ $spreadsheet->getActiveSheet()->setShowGridLines(false); // Set active sheet index to the first sheet, so Excel opens this as the first sheet $spreadsheet->setActiveSheetIndex(0); -Settings::setDefaultPdfWriter($rendererName); +IOFactory::registerWriter('Pdf', \PhpOffice\PhpSpreadsheet\Writer\Pdf\Mpdf::class); // Redirect output to a client’s web browser (PDF) header('Content-Type: application/pdf'); diff --git a/samples/Basic/26_Utf8.php b/samples/Basic/26_Utf8.php index 45a9ad60..af048246 100644 --- a/samples/Basic/26_Utf8.php +++ b/samples/Basic/26_Utf8.php @@ -1,14 +1,9 @@ log('Load Xlsx template file'); $reader = IOFactory::createReader('Xlsx'); @@ -19,7 +14,7 @@ $helper->write($spreadsheet, __FILE__, ['Xlsx', 'Xls', 'Html']); // Export to PDF (.pdf) $helper->log('Write to PDF format'); -Settings::setDefaultPdfWriter($rendererName); +IOFactory::registerWriter('Pdf', \PhpOffice\PhpSpreadsheet\Writer\Pdf\Dompdf::class); $helper->write($spreadsheet, __FILE__, ['Pdf']); // Remove first two rows with field headers before exporting to CSV diff --git a/samples/Chart/32_Chart_read_write_PDF.php b/samples/Chart/32_Chart_read_write_PDF.php index 987020ac..6400ab49 100644 --- a/samples/Chart/32_Chart_read_write_PDF.php +++ b/samples/Chart/32_Chart_read_write_PDF.php @@ -5,11 +5,7 @@ use PhpOffice\PhpSpreadsheet\Settings; require __DIR__ . '/../Header.php'; -// Change these values to select the Rendering library that you wish to use -// for PDF files, and its directory location on your server -$rendererName = \PhpOffice\PhpSpreadsheet\Writer\Pdf\MPDF::class; - -Settings::setDefaultPdfWriter($rendererName); +IOFactory::registerWriter('Pdf', \PhpOffice\PhpSpreadsheet\Writer\Pdf\Mpdf::class); // Change these values to select the Rendering library that you wish to use // for Chart images, and its directory location on your server diff --git a/samples/Pdf/21_Pdf_Domdf.php b/samples/Pdf/21_Pdf_Domdf.php index 4c6c7f07..aea4c96d 100644 --- a/samples/Pdf/21_Pdf_Domdf.php +++ b/samples/Pdf/21_Pdf_Domdf.php @@ -1,6 +1,6 @@ getActiveSheet()->setShowGridLines(false); $helper->log('Set orientation to landscape'); $spreadsheet->getActiveSheet()->getPageSetup()->setOrientation(PageSetup::ORIENTATION_LANDSCAPE); -$rendererName = \PhpOffice\PhpSpreadsheet\Writer\Pdf\DomPDF::class; -$helper->log("Write to PDF format using {$rendererName}"); -Settings::setDefaultPdfWriter($rendererName); +$className = \PhpOffice\PhpSpreadsheet\Writer\Pdf\Dompdf::class; +$helper->log("Write to PDF format using {$className}"); +IOFactory::registerWriter('Pdf', $className); // Save $helper->write($spreadsheet, __FILE__, ['Pdf']); diff --git a/samples/Pdf/21_Pdf_TCPDF.php b/samples/Pdf/21_Pdf_TCPDF.php index 11c1d4fb..9a8593e1 100644 --- a/samples/Pdf/21_Pdf_TCPDF.php +++ b/samples/Pdf/21_Pdf_TCPDF.php @@ -1,6 +1,6 @@ getActiveSheet()->setShowGridLines(false); $helper->log('Set orientation to landscape'); $spreadsheet->getActiveSheet()->getPageSetup()->setOrientation(PageSetup::ORIENTATION_LANDSCAPE); -$rendererName = \PhpOffice\PhpSpreadsheet\Writer\Pdf\TcPDF::class; -$helper->log("Write to PDF format using {$rendererName}"); -Settings::setDefaultPdfWriter($rendererName); +$className = \PhpOffice\PhpSpreadsheet\Writer\Pdf\Tcpdf::class; +$helper->log("Write to PDF format using {$className}"); +IOFactory::registerWriter('Pdf', $className); // Save $helper->write($spreadsheet, __FILE__, ['Pdf']); diff --git a/samples/Pdf/21_Pdf_mPDF.php b/samples/Pdf/21_Pdf_mPDF.php index faad16fe..b99c2250 100644 --- a/samples/Pdf/21_Pdf_mPDF.php +++ b/samples/Pdf/21_Pdf_mPDF.php @@ -1,6 +1,6 @@ getActiveSheet()->setShowGridLines(false); $helper->log('Set orientation to landscape'); $spreadsheet->getActiveSheet()->getPageSetup()->setOrientation(PageSetup::ORIENTATION_LANDSCAPE); -$rendererName = \PhpOffice\PhpSpreadsheet\Writer\Pdf\MPDF::class; -$helper->log("Write to PDF format using {$rendererName}"); -Settings::setDefaultPdfWriter($rendererName); +$className = \PhpOffice\PhpSpreadsheet\Writer\Pdf\Mpdf::class; +$helper->log("Write to PDF format using {$className}"); +IOFactory::registerWriter('Pdf', $className); // Save $helper->write($spreadsheet, __FILE__, ['Pdf']); diff --git a/src/PhpSpreadsheet/Helper/Migrator.php b/src/PhpSpreadsheet/Helper/Migrator.php index 7162d8d9..bdfcad13 100644 --- a/src/PhpSpreadsheet/Helper/Migrator.php +++ b/src/PhpSpreadsheet/Helper/Migrator.php @@ -60,9 +60,9 @@ class Migrator 'PHPExcel_Writer_OpenDocument_Thumbnails' => \PhpOffice\PhpSpreadsheet\Writer\Ods\Thumbnails::class, 'PHPExcel_Writer_OpenDocument_WriterPart' => \PhpOffice\PhpSpreadsheet\Writer\Ods\WriterPart::class, 'PHPExcel_Writer_PDF_Core' => \PhpOffice\PhpSpreadsheet\Writer\Pdf::class, - 'PHPExcel_Writer_PDF_DomPDF' => \PhpOffice\PhpSpreadsheet\Writer\Pdf\DomPDF::class, - 'PHPExcel_Writer_PDF_mPDF' => \PhpOffice\PhpSpreadsheet\Writer\Pdf\MPDF::class, - 'PHPExcel_Writer_PDF_tcPDF' => \PhpOffice\PhpSpreadsheet\Writer\Pdf\TcPDF::class, + 'PHPExcel_Writer_PDF_DomPDF' => \PhpOffice\PhpSpreadsheet\Writer\Pdf\Dompdf::class, + 'PHPExcel_Writer_PDF_mPDF' => \PhpOffice\PhpSpreadsheet\Writer\Pdf\Mpdf::class, + 'PHPExcel_Writer_PDF_tcPDF' => \PhpOffice\PhpSpreadsheet\Writer\Pdf\Tcpdf::class, 'PHPExcel_Writer_Excel5_BIFFwriter' => \PhpOffice\PhpSpreadsheet\Writer\Xls\BIFFwriter::class, 'PHPExcel_Writer_Excel5_Escher' => \PhpOffice\PhpSpreadsheet\Writer\Xls\Escher::class, 'PHPExcel_Writer_Excel5_Font' => \PhpOffice\PhpSpreadsheet\Writer\Xls\Font::class, diff --git a/src/PhpSpreadsheet/IOFactory.php b/src/PhpSpreadsheet/IOFactory.php index 858cfa47..a116334a 100644 --- a/src/PhpSpreadsheet/IOFactory.php +++ b/src/PhpSpreadsheet/IOFactory.php @@ -4,75 +4,36 @@ namespace PhpOffice\PhpSpreadsheet; use PhpOffice\PhpSpreadsheet\Shared\File; -class IOFactory +/** + * Factory to create readers and writers easily. + * + * It is not required to use this class, but it should make it easier to read and write files. + * Especially for reading files with an unknown format. + */ +abstract class IOFactory { - /** - * Search locations. - * - * @var array - */ - private static $searchLocations = [ - ['type' => 'IWriter', 'path' => 'PhpSpreadsheet/Writer/{0}.php', 'class' => '\\PhpOffice\\PhpSpreadsheet\\Writer\\{0}'], - ['type' => 'IReader', 'path' => 'PhpSpreadsheet/Reader/{0}.php', 'class' => '\\PhpOffice\\PhpSpreadsheet\\Reader\\{0}'], + private static $readers = [ + 'Xlsx' => Reader\Xlsx::class, + 'Xls' => Reader\Xls::class, + 'Xml' => Reader\Xml::class, + 'Ods' => Reader\Ods::class, + 'Slk' => Reader\Slk::class, + 'Gnumeric' => Reader\Gnumeric::class, + 'Html' => Reader\Html::class, + 'Csv' => Reader\Csv::class, ]; - /** - * Autoresolve classes. - * - * @var array - */ - private static $autoResolveClasses = [ - 'Xlsx', - 'Xls', - 'Xml', - 'Ods', - 'Slk', - 'Gnumeric', - 'Html', - 'Csv', + private static $writers = [ + 'Xls' => Writer\Xls::class, + 'Xlsx' => Writer\Xlsx::class, + 'Ods' => Writer\Ods::class, + 'Csv' => Writer\Csv::class, + 'Html' => Writer\Html::class, + 'Tcpdf' => Writer\Pdf\Tcpdf::class, + 'Dompdf' => Writer\Pdf\Dompdf::class, + 'Mpdf' => Writer\Pdf\Mpdf::class, ]; - /** - * Private constructor for IOFactory. - */ - private function __construct() - { - } - - /** - * Get search locations. - * - * @return array - */ - public static function getSearchLocations() - { - return self::$searchLocations; - } - - /** - * Set search locations. - * - * @param array $value - * - * @throws Reader\Exception - */ - public static function setSearchLocations(array $value) - { - self::$searchLocations = $value; - } - - /** - * Add search location. - * - * @param string $type Example: IWriter - * @param string $location Example: PhpSpreadsheet/Writer/{0}.php - * @param string $classname Example: Writer\{0} - */ - public static function addSearchLocation($type, $location, $classname) - { - self::$searchLocations[] = ['type' => $type, 'path' => $location, 'class' => $classname]; - } - /** * Create Writer\IWriter. * @@ -85,32 +46,15 @@ class IOFactory */ public static function createWriter(Spreadsheet $spreadsheet, $writerType) { - // Search type - $searchType = 'IWriter'; - - if ($writerType === 'Pdf') { - $pdfWriter = Settings::getDefaultPdfWriter(); - if ($pdfWriter === null) { - throw new Exception('PDF default writer has not been defined.'); - } - - return new $pdfWriter($spreadsheet); + if (!isset(self::$writers[$writerType])) { + throw new Writer\Exception("No writer found for type $writerType"); } - // Include class - foreach (self::$searchLocations as $searchLocation) { - if ($searchLocation['type'] == $searchType) { - $className = str_replace('{0}', $writerType, $searchLocation['class']); + // Instantiate writer + $className = self::$writers[$writerType]; + $writer = new $className($spreadsheet); - $instance = new $className($spreadsheet); - if ($instance !== null) { - return $instance; - } - } - } - - // Nothing found... - throw new Writer\Exception("No $searchType found for type $writerType"); + return $writer; } /** @@ -124,23 +68,15 @@ class IOFactory */ public static function createReader($readerType) { - // Search type - $searchType = 'IReader'; - - // Include class - foreach (self::$searchLocations as $searchLocation) { - if ($searchLocation['type'] == $searchType) { - $className = str_replace('{0}', $readerType, $searchLocation['class']); - - $instance = new $className(); - if ($instance !== null) { - return $instance; - } - } + if (!isset(self::$readers[$readerType])) { + throw new Reader\Exception("No reader found for type $readerType"); } - // Nothing found... - throw new Reader\Exception("No $searchType found for type $readerType"); + // Instantiate reader + $className = self::$readers[$readerType]; + $reader = new $className(); + + return $reader; } /** @@ -181,81 +117,34 @@ class IOFactory /** * Create Reader\IReader for file using automatic Reader\IReader resolution. * - * @param string $pFilename The name of the spreadsheet file + * @param string $filename The name of the spreadsheet file * * @throws Reader\Exception * * @return Reader\IReader */ - public static function createReaderForFile($pFilename) + public static function createReaderForFile($filename) { - File::assertFile($pFilename); + File::assertFile($filename); // First, lucky guess by inspecting file extension - $pathinfo = pathinfo($pFilename); + $guessedReader = self::getReaderTypeFromExtension($filename); + if ($guessedReader !== null) { + $reader = self::createReader($guessedReader); - $extensionType = null; - if (isset($pathinfo['extension'])) { - switch (strtolower($pathinfo['extension'])) { - case 'xlsx': // Excel (OfficeOpenXML) Spreadsheet - case 'xlsm': // Excel (OfficeOpenXML) Macro Spreadsheet (macros will be discarded) - case 'xltx': // Excel (OfficeOpenXML) Template - case 'xltm': // Excel (OfficeOpenXML) Macro Template (macros will be discarded) - $extensionType = 'Xlsx'; - - break; - case 'xls': // Excel (BIFF) Spreadsheet - case 'xlt': // Excel (BIFF) Template - $extensionType = 'Xls'; - - break; - case 'ods': // Open/Libre Offic Calc - case 'ots': // Open/Libre Offic Calc Template - $extensionType = 'Ods'; - - break; - case 'slk': - $extensionType = 'Slk'; - - break; - case 'xml': // Excel 2003 SpreadSheetML - $extensionType = 'Xml'; - - break; - case 'gnumeric': - $extensionType = 'Gnumeric'; - - break; - case 'htm': - case 'html': - $extensionType = 'Html'; - - break; - case 'csv': - // Do nothing - // We must not try to use CSV reader since it loads - // all files including Excel files etc. - break; - default: - break; - } - - if ($extensionType !== null) { - $reader = self::createReader($extensionType); - // Let's see if we are lucky - if (isset($reader) && $reader->canRead($pFilename)) { - return $reader; - } + // Let's see if we are lucky + if (isset($reader) && $reader->canRead($filename)) { + return $reader; } } // If we reach here then "lucky guess" didn't give any result // Try walking through all the options in self::$autoResolveClasses - foreach (self::$autoResolveClasses as $autoResolveClass) { + foreach (self::$readers as $type => $class) { // Ignore our original guess, we know that won't work - if ($autoResolveClass !== $extensionType) { - $reader = self::createReader($autoResolveClass); - if ($reader->canRead($pFilename)) { + if ($type !== $guessedReader) { + $reader = self::createReader($type); + if ($reader->canRead($filename)) { return $reader; } } @@ -263,4 +152,79 @@ class IOFactory throw new Reader\Exception('Unable to identify a reader for this file'); } + + /** + * Guess a reader type from the file extension, if any. + * + * @param string $filename + * + * @return null|string + */ + private static function getReaderTypeFromExtension($filename) + { + $pathinfo = pathinfo($filename); + if (!isset($pathinfo['extension'])) { + return null; + } + + switch (strtolower($pathinfo['extension'])) { + case 'xlsx': // Excel (OfficeOpenXML) Spreadsheet + case 'xlsm': // Excel (OfficeOpenXML) Macro Spreadsheet (macros will be discarded) + case 'xltx': // Excel (OfficeOpenXML) Template + case 'xltm': // Excel (OfficeOpenXML) Macro Template (macros will be discarded) + return 'Xlsx'; + case 'xls': // Excel (BIFF) Spreadsheet + case 'xlt': // Excel (BIFF) Template + return 'Xls'; + case 'ods': // Open/Libre Offic Calc + case 'ots': // Open/Libre Offic Calc Template + return 'Ods'; + case 'slk': + return 'Slk'; + case 'xml': // Excel 2003 SpreadSheetML + return 'Xml'; + case 'gnumeric': + return 'Gnumeric'; + case 'htm': + case 'html': + return 'Html'; + case 'csv': + // Do nothing + // We must not try to use CSV reader since it loads + // all files including Excel files etc. + return null; + default: + return null; + } + } + + /** + * Register a writer with its type and class name. + * + * @param string $writerType + * @param string $writerClass + */ + public static function registerWriter($writerType, $writerClass) + { + if (!is_a($writerClass, Writer\IWriter::class, true)) { + throw new Writer\Exception('Registered writers must implement ' . Writer\IWriter::class); + } + + self::$writers[$writerType] = $writerClass; + } + + /** + * Register a reader with its type and class name. + * + * @param string $readerType + * @param string $readerClass + */ + public static function registerReader($readerType, $readerClass) + { + if (!is_a($readerClass, Reader\IReader::class, true)) { + throw new Reader\Exception('Registered readers must implement ' . Reader\IReader::class); + } + + self::$readers[$readerType] = $readerClass; + } } diff --git a/src/PhpSpreadsheet/Settings.php b/src/PhpSpreadsheet/Settings.php index 1f71cda6..66cbfcca 100644 --- a/src/PhpSpreadsheet/Settings.php +++ b/src/PhpSpreadsheet/Settings.php @@ -3,7 +3,6 @@ namespace PhpOffice\PhpSpreadsheet; use PhpOffice\PhpSpreadsheet\Collection\Memory; -use PhpOffice\PhpSpreadsheet\Writer\Pdf; use Psr\SimpleCache\CacheInterface; class Settings @@ -31,15 +30,6 @@ class Settings */ private static $chartRendererPath; - /** - * Name of the external Library used for rendering PDF files - * e.g. - * mPDF. - * - * @var string - */ - private static $defaultPdfWriter; - /** * Default options for libxml loader. * @@ -142,30 +132,6 @@ class Settings return self::$chartRendererPath; } - /** - * Identify to PhpSpreadsheet the default writer to use for PDF. - * - * @param string $writerClassName Internal reference name of the library - */ - public static function setDefaultPdfWriter($writerClassName) - { - if (!is_a($writerClassName, Pdf::class, true)) { - throw new Exception('"' . $writerClassName . '" is not a valid PDF writer class name'); - } - self::$defaultPdfWriter = $writerClassName; - } - - /** - * Return the default PDF writer that PhpSpreadsheet is currently configured to use (e.g. dompdf). - * - * @return null|string Internal reference name of the PDF Rendering Library that PhpSpreadsheet is - * currently configured to use - */ - public static function getDefaultPdfWriter() - { - return self::$defaultPdfWriter; - } - /** * Set default options for libxml loader. * diff --git a/src/PhpSpreadsheet/Writer/Html.php b/src/PhpSpreadsheet/Writer/Html.php index ca92abad..be1f2ea7 100644 --- a/src/PhpSpreadsheet/Writer/Html.php +++ b/src/PhpSpreadsheet/Writer/Html.php @@ -1177,7 +1177,7 @@ class Html extends BaseWriter implements IWriter // Sheet index $sheetIndex = $pSheet->getParent()->getIndex($pSheet); - // DomPDF and breaks + // Dompdf and breaks if ($this->isPdf && count($pSheet->getBreaks()) > 0) { $breaks = $pSheet->getBreaks(); diff --git a/src/PhpSpreadsheet/Writer/Pdf/DomPDF.php b/src/PhpSpreadsheet/Writer/Pdf/Dompdf.php similarity index 98% rename from src/PhpSpreadsheet/Writer/Pdf/DomPDF.php rename to src/PhpSpreadsheet/Writer/Pdf/Dompdf.php index 363dd127..761c90cd 100644 --- a/src/PhpSpreadsheet/Writer/Pdf/DomPDF.php +++ b/src/PhpSpreadsheet/Writer/Pdf/Dompdf.php @@ -6,7 +6,7 @@ use PhpOffice\PhpSpreadsheet\Worksheet\PageSetup; use PhpOffice\PhpSpreadsheet\Writer\IWriter; use PhpOffice\PhpSpreadsheet\Writer\Pdf; -class DomPDF extends Pdf implements IWriter +class Dompdf extends Pdf implements IWriter { /** * Save Spreadsheet to file. diff --git a/src/PhpSpreadsheet/Writer/Pdf/MPDF.php b/src/PhpSpreadsheet/Writer/Pdf/Mpdf.php similarity index 98% rename from src/PhpSpreadsheet/Writer/Pdf/MPDF.php rename to src/PhpSpreadsheet/Writer/Pdf/Mpdf.php index 385eab6a..e9289bcd 100644 --- a/src/PhpSpreadsheet/Writer/Pdf/MPDF.php +++ b/src/PhpSpreadsheet/Writer/Pdf/Mpdf.php @@ -7,7 +7,7 @@ use PhpOffice\PhpSpreadsheet\Worksheet\PageSetup; use PhpOffice\PhpSpreadsheet\Writer\IWriter; use PhpOffice\PhpSpreadsheet\Writer\Pdf; -class MPDF extends Pdf implements IWriter +class Mpdf extends Pdf implements IWriter { /** * Save Spreadsheet to file. diff --git a/src/PhpSpreadsheet/Writer/Pdf/TcPDF.php b/src/PhpSpreadsheet/Writer/Pdf/Tcpdf.php similarity index 98% rename from src/PhpSpreadsheet/Writer/Pdf/TcPDF.php rename to src/PhpSpreadsheet/Writer/Pdf/Tcpdf.php index e5e9d2e1..c4b7aa55 100644 --- a/src/PhpSpreadsheet/Writer/Pdf/TcPDF.php +++ b/src/PhpSpreadsheet/Writer/Pdf/Tcpdf.php @@ -6,7 +6,7 @@ use PhpOffice\PhpSpreadsheet\Worksheet\PageSetup; use PhpOffice\PhpSpreadsheet\Writer\IWriter; use PhpOffice\PhpSpreadsheet\Writer\Pdf; -class TcPDF extends Pdf implements IWriter +class Tcpdf extends Pdf implements IWriter { /** * Save Spreadsheet to file. diff --git a/tests/PhpSpreadsheetTests/IOFactoryTest.php b/tests/PhpSpreadsheetTests/IOFactoryTest.php index df1eb464..da9600d4 100644 --- a/tests/PhpSpreadsheetTests/IOFactoryTest.php +++ b/tests/PhpSpreadsheetTests/IOFactoryTest.php @@ -3,31 +3,117 @@ namespace PhpOffice\PhpSpreadsheetTests; use PhpOffice\PhpSpreadsheet\IOFactory; +use PhpOffice\PhpSpreadsheet\Reader; +use PhpOffice\PhpSpreadsheet\Spreadsheet; +use PhpOffice\PhpSpreadsheet\Writer; use PHPUnit_Framework_TestCase; class IOFactoryTest extends PHPUnit_Framework_TestCase { + /** + * @dataProvider providerCreateWriter + * + * @param string $name + * @param string $expected + */ + public function testCreateWriter($name, $expected) + { + $spreadsheet = new Spreadsheet(); + $actual = IOFactory::createWriter($spreadsheet, $name); + self::assertInstanceOf($expected, $actual); + } + + public function providerCreateWriter() + { + return [ + ['Xls', Writer\Xls::class], + ['Xlsx', Writer\Xlsx::class], + ['Ods', Writer\Ods::class], + ['Csv', Writer\Csv::class], + ['Html', Writer\Html::class], + ['Mpdf', Writer\Pdf\Mpdf::class], + ['Tcpdf', Writer\Pdf\Tcpdf::class], + ['Dompdf', Writer\Pdf\Dompdf::class], + ]; + } + + public function testRegisterWriter() + { + IOFactory::registerWriter('Pdf', Writer\Pdf\Mpdf::class); + $spreadsheet = new Spreadsheet(); + $actual = IOFactory::createWriter($spreadsheet, 'Pdf'); + self::assertInstanceOf(Writer\Pdf\Mpdf::class, $actual); + } + + /** + * @dataProvider providerCreateReader + * + * @param string $name + * @param string $expected + */ + public function testCreateReader($name, $expected) + { + $actual = IOFactory::createReader($name); + self::assertInstanceOf($expected, $actual); + } + + public function providerCreateReader() + { + return [ + ['Xls', Reader\Xls::class], + ['Xlsx', Reader\Xlsx::class], + ['Xml', Reader\Xml::class], + ['Ods', Reader\Ods::class], + ['Gnumeric', Reader\Gnumeric::class], + ['Csv', Reader\Csv::class], + ['Slk', Reader\Slk::class], + ['Html', Reader\Html::class], + ]; + } + + public function testRegisterReader() + { + IOFactory::registerReader('Custom', Reader\Html::class); + $actual = IOFactory::createReader('Custom'); + self::assertInstanceOf(Reader\Html::class, $actual); + } + /** * @dataProvider providerIdentify * - * @param mixed $file - * @param mixed $expected + * @param string $file + * @param string $expectedName + * @param string $expectedClass */ - public function testIdentify($file, $expected) + public function testIdentify($file, $expectedName, $expectedClass) { $actual = IOFactory::identify($file); - self::assertSame($expected, $actual); + self::assertSame($expectedName, $actual); + } + + /** + * @dataProvider providerIdentify + * + * @param string $file + * @param string $expectedName + * @param string $expectedClass + */ + public function testCreateReaderForFile($file, $expectedName, $expectedClass) + { + $actual = IOFactory::createReaderForFile($file); + self::assertInstanceOf($expectedClass, $actual); } public function providerIdentify() { return [ - ['../samples/templates/26template.xlsx', 'Xlsx'], - ['../samples/templates/GnumericTest.gnumeric', 'Gnumeric'], - ['../samples/templates/30template.xls', 'Xls'], - ['../samples/templates/OOCalcTest.ods', 'Ods'], - ['../samples/templates/SylkTest.slk', 'Slk'], - ['../samples/templates/Excel2003XMLTest.xml', 'Xml'], + ['../samples/templates/26template.xlsx', 'Xlsx', Reader\Xlsx::class], + ['../samples/templates/GnumericTest.gnumeric', 'Gnumeric', Reader\Gnumeric::class], + ['../samples/templates/30template.xls', 'Xls', Reader\Xls::class], + ['../samples/templates/OOCalcTest.ods', 'Ods', Reader\Ods::class], + ['../samples/templates/SylkTest.slk', 'Slk', Reader\Slk::class], + ['../samples/templates/Excel2003XMLTest.xml', 'Xml', Reader\Xml::class], + ['../samples/templates/46readHtml.html', 'Html', Reader\Html::class], ]; } @@ -46,4 +132,20 @@ class IOFactoryTest extends PHPUnit_Framework_TestCase { IOFactory::identify('.'); } + + /** + * @expectedException \PhpOffice\PhpSpreadsheet\Writer\Exception + */ + public function testRegisterInvalidWriter() + { + IOFactory::registerWriter('foo', 'bar'); + } + + /** + * @expectedException \PhpOffice\PhpSpreadsheet\Reader\Exception + */ + public function testRegisterInvalidReader() + { + IOFactory::registerReader('foo', 'bar'); + } }