Commit a789dd02 authored by tguillon's avatar tguillon
Browse files

Début de la résolution des annexes PDF.

parent 53491cd2
......@@ -13,6 +13,10 @@ Configure::write('FusionConv.FusionConvConverterCloudooo.port', '8011');
Configure::write('PDFTK_EXEC', '/usr/bin/pdftk');
Configure::write('PDFINFO_EXEC', '/usr/bin/pdfinfo');
/* Configuration GhostScript */
// Résolution d'image (pixels) : Agit sur la rapidité de génération des annexes (Conversion pdf et doc en image)
Configure::write('GS_RESOLUTION', '300');
//Dossier qui va contenir tout les fichiers uploder
define('FICHIER', "files");
......
......@@ -848,7 +848,7 @@ class FichesController extends AppController {
// On vérifie que les infos du modèle existe bien
if (!empty($modele) && file_exists(CHEMIN_MODELES.$modele['Modele']['fichier'])) {
$file = $modele['Modele']['fichier'];
$pdf = $this->Fiche->preparationGeneration(
$tabId,
$file,
......
......@@ -21,6 +21,7 @@
*/
App::uses('AppModel', 'Model');
App::uses('Conversion', 'Utility');
require_once APP . 'Vendor' . DS . 'phpgedooo_client' . DS . 'src' . DS . 'GDO_PartType.php';
require_once APP . 'Vendor' . DS . 'phpgedooo_client' . DS . 'src' . DS . 'GDO_IterationType.php';
......@@ -169,10 +170,10 @@ class Fiche extends AppModel {
*/
public function preparationGeneration($tabId, $file, $cheminFile, $idOrganisation, $historique = false) {
$donnees = [];
// On récupère et met en forme les informations de l'organisation
$donnees = $this->_preparationGenerationOrganisation($idOrganisation, $donnees);
// On récupère et met en forme les numéro d'enregistrement du traitement
$donnees = $this->_preparationGenerationNumeroEnregistrement($tabId, $donnees);
......@@ -181,7 +182,7 @@ class Fiche extends AppModel {
* information sur le déclarant au moment de la création du traitement
*/
foreach ((array)json_decode($tabId) as $key => $id) {
$donnees['traitement'][$key] = $this->_preparationGenerationValeurTraitement($id, $donnees['traitement'][$key],$historique);
$donnees['traitement'][$key] = $this->_preparationGenerationValeurTraitement($id, $donnees['traitement'][$key], $historique);
}
if ($historique == true) {
......@@ -448,7 +449,7 @@ class Fiche extends AppModel {
];
}
}
unset($donnees['valeur_fichiers']);
// unset($donnees['valeur_fichiers']);
if ($historique == true) {
$donnees = $this->_preparationAnnexe($id, $donnees);
......@@ -456,10 +457,10 @@ class Fiche extends AppModel {
return ($donnees);
}
private function _preparationAnnexe($id, $donnees) {
$annexe = false;
private function _preparationAnnexe($id, $donnees) {
// On chercher si le traitement comporte des annexe(s)
$fileAnnexes = $this->Fichier->find('all', [
'conditions' => [
......@@ -468,17 +469,33 @@ class Fiche extends AppModel {
]);
if (!empty($fileAnnexes)) {
$annexe = true;
}
if ($annexe == true) {
foreach ($fileAnnexes as $key => $fileAnnexe) {
$donnees['fichiers'][$key]['valeur_annexe'] = [
'value' => file_get_contents(
CHEMIN_PIECE_JOINT . $fileAnnexe['Fichier']['url']
),
'type' => 'file'
];
$filename = CHEMIN_PIECE_JOINT . $fileAnnexe['Fichier']['url'];
if (file_exists($filename)) {
$mime = mime_content_type($filename);
switch($mime) {
case 'application/pdf':
$content = Conversion::pdf2odt($filename);
break;
case 'application/vnd.oasis.opendocument.text':
$content = file_get_contents($filename);
break;
default:
$msgstr = 'Type MIME %s non pris en charge pour le fichier %s';
throw new RuntimeException(sprintf($msgstr, $mime, $filename));
}
//debug($content);
//print_r($content);die();
$donnees['fichiers'][$key]['valeur_annexe'] = [
'value' => $content,
'type' => 'file'
];
} else {
debug("PAS TROUVER" . CHEMIN_PIECE_JOINT . $fileAnnexe['Fichier']['url']);
}
}
}
......@@ -545,13 +562,15 @@ class Fiche extends AppModel {
$data = [];
$types = [];
$correspondances = [];
$this->_format($MainPart, $donnees, $data, $types, $correspondances);
$Document = FusionConvBuilder::main($MainPart, $data, $types, $correspondances);
//echo '<pre>';
//print_r(FusionConvDebugger::allPathsToCsv($MainPart, true));die();
//echo '</pre>';
$sMimeType = 'application/vnd.oasis.opendocument.text';
$Template = new phpgedooo_client\GDO_ContentType("", 'model.odt', "application/vnd.oasis.opendocument.text", "binary", file_get_contents($cheminFile . $file));
$Fusion = new phpgedooo_client\GDO_FusionType($Template, $sMimeType, $Document);
......
<?php
App::uses('File', 'Utility');
App::uses('Folder', 'Utility');
function tempdir()
{
$tempfile=tempnam(sys_get_temp_dir(),'');
// you might want to reconsider this line when using this snippet.
// it "could" clash with an existing directory and this line will
// try to delete the existing one. Handle with caution.
if (file_exists($tempfile)) { unlink($tempfile); }
mkdir($tempfile);
if (is_dir($tempfile)) { return $tempfile; }
}
abstract class Conversion
{
public static function convert($data, $dataExtention, $dataSortieExtention)
{
require_once 'XML/RPC2/Client.php';
$options = [
'uglyStructHack' => true
];
$url = 'http://' . Configure::read('FusionConv.cloudooo_host') . ':' . Configure::read('FusionConv.cloudooo_port');
$client = XML_RPC2_Client::create($url, $options);
try {
$result = $client->convertFile(base64_encode($data), $dataExtention, $dataSortieExtention, false, true);
return base64_decode($result, true);
} catch (XML_RPC2_FaultException $e) {
CakeLog::error('Exception #' . $e->getFaultCode() . ' : ' . $e->getFaultString());
return false;
}
}
public static function pdf2odt($path)
{
$folderPath = tempdir();
$pdf = new File($path);
$folder = new Folder($folderPath, true, 0755);
//Preparation de la commande ghostscript
$PDFTK_EXEC = Configure::read('PDFTK_EXEC');
$PDFINFO_EXEC = Configure::read('PDFINFO_EXEC');
$GS_RESOLUTION = Configure::read('GS_RESOLUTION');
$NbrPage = trim(shell_exec($PDFINFO_EXEC . ' ' . $pdf->pwd() . ' | grep -a Pages: | sed -e "s/ *Pages: *//g"'));
if ($NbrPage > 0) {
for ($i = 1; $i <= $NbrPage; $i++) {
$pageName = 'page_' . sprintf('%04d', $i);
shell_exec($PDFTK_EXEC . ' ' . $pdf->pwd() . ' cat ' . $i . ' output ' . $folder->pwd() . DS . $pageName . '.pdf-orign 2>&1');
shell_exec($PDFTK_EXEC . ' ' . $folder->pwd() . DS . $pageName . '.pdf-orign dump_data output ' . $folder->pwd() . DS . $pageName . '.txt 2>&1');
shell_exec($PDFTK_EXEC . ' ' . $folder->pwd() . DS . $pageName . '.pdf-orign update_info ' . $folder->pwd() . DS . $pageName . '.txt output ' . $folder->pwd() . DS . $pageName . '.pdf 2>&1');
}
} else {
return ''; //GESTION DES ERREURS A FAIRE
}
//$pdf->delete(); // @fixme
$files = $folder->find('.*\.pdf', true);
$i = 1;
foreach ($files as $file) {
$file = new File($folder->pwd() . DS . $file);
$imagick = new Imagick();
$imagick->setResolution($GS_RESOLUTION, $GS_RESOLUTION);
$imagick->readImage($file->pwd() . '[0]');
$imagick->setImageFormat('png');
$imagick->writeImage($folder->pwd() . DS . $i . '.png');
if ($imagick->getImageHeight() > $imagick->getImageWidth()) {
$orientaion = 'portrait';
} else {
$orientaion = 'landscape';
}
$pageParam[$i] = ['path' => $folder->pwd() . DS . $i . '.png',
'name' => $i . '.png',
'orientation' => $orientaion];
CakeLog::debug('page ' . $i . '| orientation=' . $orientaion);
$imagick->clear();
$file->close();
$i++;
}
//génération du fichier ODT
if (empty($pageParam)) {
throw new InternalErrorException('Impossible de convertir le fichier : paramètres manquants');
}
static::generateOdtFileWithImages($folder, $pageParam);
$file = new File($folder->pwd() . DS . 'result.odt');
$content = $file->read();
$file->close();
$folder->delete();
return $content;
}
/**
* @param $folder
* @param $aPagePng
*/
public static function generateOdtFileWithImages(&$folder, $aPagePng)
{
App::import('Vendor', 'phpodt/phpodt');
$odt = ODT::getInstance(true, $folder->pwd() . DS . 'result.odt');
$pageStyleP = new PageStyle('myPageStylePortrait', 'Standard');
$pageStyleP->setOrientation(StyleConstants::PORTRAIT);
$pageStyleP->setHorizontalMargin('0cm', '0cm');
$pageStyleP->setVerticalMargin('0cm', '0cm');
$pStyleP = new ParagraphStyle('myPStyleP', 'Standard');
$pStyleP->setBreakAfter(StyleConstants::PAGE);
$pageStyleL = new PageStyle('myPageStyleLandscape', 'Landscape');
$pageStyleL->setOrientation(StyleConstants::LANDSCAPE);
$pageStyleL->setHorizontalMargin('0cm', '0cm');
$pageStyleL->setVerticalMargin('0cm', '0cm');
$pStyleL = new ParagraphStyle('myPStyleL', 'Landscape');
$pStyleL->setBreakBefore(StyleConstants::PAGE);
foreach ($aPagePng as $keyPage => $page) {
if ($page['orientation'] == 'landscape') {
$p = new Paragraph($pStyleL);
$p->addImage($page['path'], '29.7cm', '21cm', true, $page['name'], 'paragraph');
} else {
$p = new Paragraph($pStyleP);
$p->addImage($page['path'], '21cm', '29.7cm', true, $page['name'], 'paragraph');
}
}
$odt->output();
}
}
<?php
//require_once 'class.contentautostyle.php';
//require_once 'exceptions/class.styleexception.php';
include_once 'phpodt.php';
/**
* A Class representing style properties for table cells.
*
* @author Issam RACHDI
*/
class CellStyle extends ContentAutoStyle {
private $cellProp;
/**
*
* @param DOMDocument $contentDoc
* @param string $name
*/
public function __construct($name) {
parent::__construct($name);
$this->styleElement->setAttribute('style:family', 'table-cell');
$this->cellProp = $this->contentDocument->createElement('style:table-cell-properties');
$this->styleElement->appendChild($this->cellProp);
}
/**
* Specifies the vertical alignment of text in a table cell
*
* @param type $vAlign Possible values are StyleConstants::(TOP|MIDDLE|BOTTOM|AUTO)
*/
public function setVerticalAlign($vAlign) {
switch ($vAlign) {
case StyleConstants::TOP:
$vAlign = 'top';break;
case StyleConstants::MIDDLE:
$vAlign = 'middle';break;
case StyleConstants::BOTTOM:
$vAlign = 'bottom';break;
case StyleConstants::AUTO:
$vAlign = 'automatic';break;
default:
throw new StyleException('Invalid vertical align value');
}
$this->cellProp->setAttribute('style:vertical-align', $vAlign);
}
// /**
// * Specifies the source of the text-alignment. If the value of this attribute is StyleConstants::FIX,
// * the value specified with setVerticalAlign is used. If the value is StyleConstants::VALUE_TYPE,
// * the text alignment depends on the value-type of the cell.
// *
// * @param type $src
// */
// public function setTextAlignSrc($src) {
// switch ($src) {
// case StyleConstants::FIX:
// $src = 'fix';break;
// case StyleConstants::VALUE_TYPE:
// $src = 'value-type';break;
// default:
// throw new StyleException('Invalid text align source value');
// }
// $this->cellProp->setAttribute('style:text-align-source', $src);
// }
/**
* Specifies the direction of characters in a cell. The most common direction is left to right
* (StyleConstants::LTR). The other direction is top to bottom (StyleConstants::TTB), where the
* characters in the cell are stacked but not rotated.
*
* @param integer $direction
*/
public function setDirection($direction) {
switch ($direction) {
case StyleConstants::LTR:
$direction = 'ltr';break;
case StyleConstants::TTB:
$direction = 'ttb';break;
default:
throw new StyleException('Invalid cell direction value');
}
$this->cellProp->setAttribute('style:direction', $direction);
}
/**
* Specifies the vertical glyph orientation.
* The property specifies an angle or automatic mode. The only possible angle is 0, which disables
* this feature.
*
* @param integer $orientation
*/
public function setVertGlyphOrient($orientation) {
switch ($orientation) {
case StyleConstants::AUTO:
$orientation = 'auto';break;
case 0:
$orientation = '0';break;
default:
throw new StyleException('Invalid vertical glyph orientation value');
}
$this->cellProp->setAttribute('style:glyph-orientation-vertical', $orientation);
}
/**
* Sets the background color of the cell.
*
* @param color $color
*/
public function setBgColor($color) {
if (!isColor($color)) {
throw new StyleException('Invalid color value');
}
$this->cellProp->setAttribute('fo:background-color', $color);
}
/**
* Specifies a background image for a cell. Note that if you specify the position, the image
* will not be repeated
*
* @param string $image The image's path.
* @param integer $repeat Specifies whether the background image is repeated or stretched.
* @param integer $position Specifies where to position the background image.
* Valid values are StyleConstants::(LEFT|RIGHT|CENTER|TOP|BOTTOM)
*/
public function setBgImage($image, $repeat = StyleConstants::REPEAT, $position = -1) {
$file = fopen($image, 'r');
if (!$file) {
throw new StyleException('Cannot open image');
}
switch($repeat) {
case StyleConstants::REPEAT:
$repeat = 'repeat';break;
case StyleConstants::NO_REPEAT:
$repeat = 'no-repeat';break;
case StyleConstants::STRETCH:
$repeat = 'stretch';break;
default:
throw new StyleException('Invalid repeat value');
}
switch($position) {
case -1:
break;
case StyleConstants::LEFT:
$position = 'left';break;
case StyleConstants::RIGHT:
$position = 'right';break;
case StyleConstants::CENTER:
$position = 'center';break;
case StyleConstants::TOP:
$position = 'top';break;
case StyleConstants::BOTTOM:
$position = 'left';break;
default:
throw new StyleException('Invalid background-position value');
}
$dataImg = fread($file, filesize($image));
$dateImgB64 = base64_encode($dataImg);
fclose($file);
$binaryElement = $this->contentDocument->createElement('office:binary-data', $dateImgB64);
$imageElement = $this->contentDocument->createElement('style:background-image');
$imageElement->setAttribute('style:repeat', $repeat);
if ($position != -1) {
$imageElement->setAttribute('style:position', $position);
}
$imageElement->appendChild($binaryElement);
$this->cellProp->appendChild($imageElement);
}
/**
* Specifies the border properties for cell.
*
* @param color $borderColor Border color
* @param integer $borderStyle Valid values: StyleConstants::(SOLID|DOUBLE)
* @param integer|length $borderWidth Can be a length, or one of these values: StyleConstants::(THIN|THICK|MEDIUM)
* @param string $position
*/
function setBorder($borderColor = '#000000', $borderStyle = StyleConstants::SOLID,
$borderWidth = StyleConstants::THIN, $position = '') {
if (!isColor($borderColor)) {
throw new StyleException('Invalid border-color value');
}
switch ($borderStyle) {
case StyleConstants::SOLID:
$borderStyle = 'solid';break;
case StyleConstants::DOUBLE:
$borderStyle = 'double';break;
default:
throw new StyleException('Invalid border-style value');
}
switch ($borderWidth) {
case StyleConstants::THIN:
$borderWidth = 'thin';break;
case StyleConstants::THICK:
$borderWidth = 'thick';break;
case StyleConstants::MEDIUM:
$borderWidth = 'medium';break;
default:
if (!isLengthValue($borderWidth, true)) {
throw new StyleException('Invalid border-width value');
}
}
if (!empty($position)) {
if (!in_array($position, array('top', 'bottom', 'left', 'right'))) {
$position = '';
} else {
$position = '-'.$position;
}
}
$this->cellProp->setAttribute('fo:border'.$position, "$borderWidth $borderStyle $borderColor");
}
/**
* Specifies the top border properties for a cell.
*
* @param color $borderColor Border color
* @param int $borderStyle Valid values: StyleConstants::(SOLID|DOUBLE)
* @param int|length $borderWidth Can be a length, or one of these values: StyleConstants::(THIN|THICK|MEDIUM)
*/
function setTopBorder($borderColor = '#000000', $borderStyle = StyleConstants::SOLID,
$borderWidth = StyleConstants::THIN) {
$this->setBorder($borderColor, $borderStyle, $borderWidth, 'top');
}
/**
* Specifies the bottom border properties for a cell.
*
* @param color $borderColor Border color
* @param int $borderStyle Valid values: StyleConstants::(SOLID|DOUBLE)
* @param int|length $borderWidth Can be a length, or one of these values: StyleConstants::(THIN|THICK|MEDIUM)
*/
function setBottomBorder($borderColor = '#000000', $borderStyle = StyleConstants::SOLID,
$borderWidth = StyleConstants::THIN) {
$this->setBorder($borderColor, $borderStyle, $borderWidth, 'bottom');
}
/**
* Specifies the left border properties for a cell.
*
* @param color $borderColor Border color
* @param int $borderStyle Valid values: StyleConstants::(SOLID|DOUBLE)
* @param int|length $borderWidth Can be a length, or one of these values: StyleConstants::(THIN|THICK|MEDIUM)
*/
function setLeftBorder($borderColor = '#000000', $borderStyle = StyleConstants::SOLID,
$borderWidth = StyleConstants::THIN) {
$this->setBorder($borderColor, $borderStyle, $borderWidth, 'left');
}
/**
* Specifies the right border properties for a cell.
*
* @param color $borderColor Border color
* @param int $borderStyle Valid values: StyleConstants::(SOLID|DOUBLE)
* @param int|length $borderWidth Can be a length, or one of these values: StyleConstants::(THIN|THICK|MEDIUM)
*/
function setRightBorder($borderColor = '#000000', $borderStyle = StyleConstants::SOLID,
$borderWidth = StyleConstants::THIN) {
$this->setBorder($borderColor, $borderStyle, $borderWidth, 'right');
}
/**
* Specifies the spacing around a table cell.
*
* @param length $padding
* @param string $position
*/
function setPadding($padding, $position = '') {
if (!isLengthValue($padding, true) && !isNumeric($padding)) {
throw new StyleException('Invalid padding value');
}
if (!empty($position)) {
if (!in_array($position, array('top', 'bottom', 'left', 'right'))) {
$position = '';
} else {
$position = '-'.$position;
}
}
$this->cellProp->setAttribute('fo:padding'.$position, $padding);
}
/**
* Specifies the spacing on top of a table cell.
*
* @param length $padding
*/
function setTopPadding($padding) {
$this->setPadding($padding, 'top');
}
/**
* Specifies the spacing in the bottom of a table cell.
*
* @param length $padding
*/
function setBottomPadding($padding) {
$this->setPadding($padding, 'bottom');
}
/**
* Specifies the spacing in the left side of a table cell.
*
* @param length $padding
*/
function setLeftPadding($padding) {
$this->setPadding($padding, 'left');
}
/**
* Specifies the spacing in the right side of a table cell.
*
* @param length $padding
*/
function setRightPadding($padding) {
$this->setPadding($padding, 'right');
}
// /**
// * Specifies whether text wraps within a table cell.
// * @param integer $wrapOption
// */
// function setWrapOption($wrapOption) {
// switch ($wrapOption) {
// case StyleConstants::WRAP:
// $wrapOption = 'wrap';break;
// case StyleConstants::NO_WRAP: