function _getImage(&$file, $firsttime=true, $allowvector=true, $orig_srcpath=false) { // firsttime i.e. whether to add to this->images - use false when calling iteratively // Image Data passed directly as var:varname if (preg_match('/var:\s*(.*)/',$file, $v)) { $data = $this->$v[1]; $file = md5($data); } // mPDF 5.5.13 if (preg_match('/data:image\/(gif|jpeg|png);base64,(.*)/',$file, $v)) { $type = $v[1]; $data = base64_decode($v[2]); $file = md5($data); } // mPDF 5.6.02 if ($firsttime && $file && substr($file,0,5)!='data:') { $file = urlencode_part($file); } if ($firsttime && $orig_srcpath && substr($orig_srcpath,0,5)!='data:') { $orig_srcpath = urlencode_part($orig_srcpath); } $ppUx = 0; if ($orig_srcpath && isset($this->images[$orig_srcpath])) { $file=$orig_srcpath; return $this->images[$orig_srcpath]; } if (isset($this->images[$file])) { return $this->images[$file]; } else if ($orig_srcpath && isset($this->formobjects[$orig_srcpath])) { $file=$orig_srcpath; return $this->formobjects[$file]; } else if (isset($this->formobjects[$file])) { return $this->formobjects[$file]; } // Save re-trying image URL's which have already failed else if ($firsttime && isset($this->failedimages[$file])) { return $this->_imageError($file, $firsttime, ''); } if (empty($data)) { $type = ''; $data = ''; if ($orig_srcpath && $this->basepathIsLocal && $check = @fopen($orig_srcpath,"rb")) { fclose($check); $file=$orig_srcpath; $data = file_get_contents($file); $type = $this->_imageTypeFromString($data); } if (!$data && $check = @fopen($file,"rb")) { fclose($check); $data = file_get_contents($file); $type = $this->_imageTypeFromString($data); } if ((!$data || !$type) && !ini_get('allow_url_fopen') ) { // only worth trying if remote file and !ini_get('allow_url_fopen') $this->file_get_contents_by_socket($file, $data); // needs full url?? even on local (never needed for local) if ($data) { $type = $this->_imageTypeFromString($data); } } if ((!$data || !$type) && !ini_get('allow_url_fopen') && function_exists("curl_init")) { $this->file_get_contents_by_curl($file, $data); // needs full url?? even on local (never needed for local) if ($data) { $type = $this->_imageTypeFromString($data); } } } if (!$data) { return $this->_imageError($file, $firsttime, 'Could not find image file'); } if (empty($type)) { $type = $this->_imageTypeFromString($data); } if (($type == 'wmf' || $type == 'svg') && !$allowvector) { return $this->_imageError($file, $firsttime, 'WMF or SVG image file not supported in this context'); } // SVG if ($type == 'svg') { if (!class_exists('SVG', false)) { include(_MPDF_PATH .'classes/svg.php'); } $svg = new SVG($this); $family=$this->FontFamily; $style=$this->FontStyle; $size=$this->FontSizePt; $info = $svg->ImageSVG($data); //Restore font if($family) $this->SetFont($family,$style,$size,false); if (!$info) { return $this->_imageError($file, $firsttime, 'Error parsing SVG file'); } $info['type']='svg'; $info['i']=count($this->formobjects)+1; $this->formobjects[$file]=$info; return $info; } // JPEG if ($type == 'jpeg' || $type == 'jpg') { $hdr = $this->_jpgHeaderFromString($data); if (!$hdr) { return $this->_imageError($file, $firsttime, 'Error parsing JPG header'); } $a = $this->_jpgDataFromHeader($hdr); $j = strpos($data,'JFIF'); if ($j) { //Read resolution $unitSp=ord(substr($data,($j+7),1)); if ($unitSp > 0) { $ppUx=$this->_twobytes2int(substr($data,($j+8),2)); // horizontal pixels per meter, usually set to zero if ($unitSp == 2) { // = dots per cm (if == 1 set as dpi) $ppUx=round($ppUx/10 *25.4); } } } if ($a[2] == 'DeviceCMYK' && (($this->PDFA && $this->restrictColorSpace!=3) || $this->restrictColorSpace==2)) { // convert to RGB image if (!function_exists("gd_info")) { $this->Error("JPG image may not use CMYK color space (".$file.")."); } if ($this->PDFA && !$this->PDFAauto) { $this->PDFAXwarnings[] = "JPG image may not use CMYK color space - ".$file." - (Image converted to RGB. NB This will alter the colour profile of the image.)"; } $im = @imagecreatefromstring($data); if ($im) { $tempfile = _MPDF_TEMP_PATH.'_tempImgPNG'.RAND(1,10000).'.png'; imageinterlace($im, false); $check = @imagepng($im, $tempfile); if (!$check) { return $this->_imageError($file, $firsttime, 'Error creating temporary file ('.$tempfile.') whilst using GD library to parse JPG(CMYK) image'); } $info = $this->_getImage($tempfile, false); if (!$info) { return $this->_imageError($file, $firsttime, 'Error parsing temporary file ('.$tempfile.') created with GD library to parse JPG(CMYK) image'); } imagedestroy($im); unlink($tempfile); $info['type']='jpg'; if ($firsttime) { $info['i']=count($this->images)+1; $this->images[$file]=$info; } return $info; } else { return $this->_imageError($file, $firsttime, 'Error creating GD image file from JPG(CMYK) image'); } } else if ($a[2] == 'DeviceRGB' && ($this->PDFX || $this->restrictColorSpace==3)) { // Convert to CMYK image stream - nominally returned as type='png' $info = $this->_convImage($data, $a[2], 'DeviceCMYK', $a[0], $a[1], $ppUx, false); if (($this->PDFA && !$this->PDFAauto) || ($this->PDFX && !$this->PDFXauto)) { $this->PDFAXwarnings[] = "JPG image may not use RGB color space - ".$file." - (Image converted to CMYK. NB This will alter the colour profile of the image.)"; } } else if (($a[2] == 'DeviceRGB' || $a[2] == 'DeviceCMYK') && $this->restrictColorSpace==1) { // Convert to Grayscale image stream - nominally returned as type='png' $info = $this->_convImage($data, $a[2], 'DeviceGray', $a[0], $a[1], $ppUx, false); } else { $info = array('w'=>$a[0],'h'=>$a[1],'cs'=>$a[2],'bpc'=>$a[3],'f'=>'DCTDecode','data'=>$data, 'type'=>'jpg'); if ($ppUx) { $info['set-dpi'] = $ppUx; } } if (!$info) { return $this->_imageError($file, $firsttime, 'Error parsing or converting JPG image'); } if ($firsttime) { $info['i']=count($this->images)+1; $this->images[$file]=$info; } return $info; } // PNG else if ($type == 'png') { //Check signature if(substr($data,0,8)!=chr(137).'PNG'.chr(13).chr(10).chr(26).chr(10)) { return $this->_imageError($file, $firsttime, 'Error parsing PNG identifier'); } //Read header chunk if(substr($data,12,4)!='IHDR') { return $this->_imageError($file, $firsttime, 'Incorrect PNG file (no IHDR block found)'); } $w=$this->_fourbytes2int(substr($data,16,4)); $h=$this->_fourbytes2int(substr($data,20,4)); $bpc=ord(substr($data,24,1)); $errpng = false; $pngalpha = false; if($bpc>8) { $errpng = 'not 8-bit depth'; } $ct=ord(substr($data,25,1)); if($ct==0) { $colspace='DeviceGray'; } elseif($ct==2) { $colspace='DeviceRGB'; } elseif($ct==3) { $colspace='Indexed'; } elseif($ct==4) { $colspace='DeviceGray'; $errpng = 'alpha channel'; $pngalpha = true; } else { $colspace='DeviceRGB'; $errpng = 'alpha channel'; $pngalpha = true; } if(ord(substr($data,26,1))!=0) { $errpng = 'compression method'; } if(ord(substr($data,27,1))!=0) { $errpng = 'filter method'; } if(ord(substr($data,28,1))!=0) { $errpng = 'interlaced file'; } $j = strpos($data,'pHYs'); if ($j) { //Read resolution $unitSp=ord(substr($data,($j+12),1)); if ($unitSp == 1) { $ppUx=$this->_fourbytes2int(substr($data,($j+4),4)); // horizontal pixels per meter, usually set to zero $ppUx=round($ppUx/1000 *25.4); } } if (($colspace == 'DeviceRGB' || $colspace == 'Indexed') && ($this->PDFX || $this->restrictColorSpace==3)) { // Convert to CMYK image stream - nominally returned as type='png' $info = $this->_convImage($data, $colspace, 'DeviceCMYK', $w, $h, $ppUx, $pngalpha); if (($this->PDFA && !$this->PDFAauto) || ($this->PDFX && !$this->PDFXauto)) { $this->PDFAXwarnings[] = "PNG image may not use RGB color space - ".$file." - (Image converted to CMYK. NB This will alter the colour profile of the image.)"; } } else if (($colspace == 'DeviceRGB' || $colspace == 'Indexed') && $this->restrictColorSpace==1) { // Convert to Grayscale image stream - nominally returned as type='png' $info = $this->_convImage($data, $colspace, 'DeviceGray', $w, $h, $ppUx, $pngalpha); } else if (($this->PDFA || $this->PDFX) && $pngalpha) { // Remove alpha channel if ($this->restrictColorSpace==1) { // Grayscale $info = $this->_convImage($data, $colspace, 'DeviceGray', $w, $h, $ppUx, $pngalpha); } else if ($this->restrictColorSpace==3) { // CMYK $info = $this->_convImage($data, $colspace, 'DeviceCMYK', $w, $h, $ppUx, $pngalpha); } else if ($this->PDFA ) { // RGB $info = $this->_convImage($data, $colspace, 'DeviceRGB', $w, $h, $ppUx, $pngalpha); } if (($this->PDFA && !$this->PDFAauto) || ($this->PDFX && !$this->PDFXauto)) { $this->PDFAXwarnings[] = "Transparency (alpha channel) not permitted in PDFA or PDFX files - ".$file." - (Image converted to one without transparency.)"; } } else if ($errpng || $pngalpha) { if (function_exists('gd_info')) { $gd = gd_info(); } else {$gd = array(); } if (!isset($gd['PNG Support'])) { return $this->_imageError($file, $firsttime, 'GD library required for PNG image ('.$errpng.')'); } $im = imagecreatefromstring($data); if (!$im) { return $this->_imageError($file, $firsttime, 'Error creating GD image from PNG file ('.$errpng.')'); } $w = imagesx($im); $h = imagesy($im); if ($im) { $tempfile = _MPDF_TEMP_PATH.'_tempImgPNG'.RAND(1,10000).'.png'; // Alpha channel set if ($pngalpha) { if ($this->PDFA) { $this->Error("PDFA1-b does not permit images with alpha channel transparency (".$file.")."); } $imgalpha = imagecreate($w, $h); // generate gray scale pallete for ($c = 0; $c < 256; ++$c) { ImageColorAllocate($imgalpha, $c, $c, $c); } // extract alpha channel $gammacorr = 2.2; // gamma correction for ($xpx = 0; $xpx < $w; ++$xpx) { for ($ypx = 0; $ypx < $h; ++$ypx) { //$colorindex = imagecolorat($im, $xpx, $ypx); //$col = imagecolorsforindex($im, $colorindex); //$gamma2 = (pow((((127 - $col['alpha']) * 255 / 127) / 255), $gammacorr) * 255); $alpha = (imagecolorat($im, $xpx, $ypx) & 0x7F000000) >> 24; if ($alpha < 127) { if ($alpha==0) { $gamma = 255; } else $gamma = (pow((((127 - $alpha) * 255 / 127) / 255), $gammacorr) * 255); imagesetpixel($imgalpha, $xpx, $ypx, $gamma); } } } // create temp alpha file $tempfile_alpha = _MPDF_TEMP_PATH.'_tempMskPNG'.RAND(1,10000).'.png'; if (!is_writable($tempfile_alpha)) { ob_start(); $check = @imagepng($imgalpha); if (!$check) { return $this->_imageError($file, $firsttime, 'Error creating temporary image object whilst using GD library to parse PNG image'); } imagedestroy($imgalpha); $this->_tempimg = ob_get_contents(); $this->_tempimglnk = 'var:_tempimg'; ob_end_clean(); // extract image without alpha channel $imgplain = imagecreatetruecolor($w, $h); imagecopy($imgplain, $im, 0, 0, 0, 0, $w, $h); // create temp image file $minfo = $this->_getImage($this->_tempimglnk, false); if (!$minfo) { return $this->_imageError($file, $firsttime, 'Error parsing temporary file image object created with GD library to parse PNG image'); } ob_start(); $check = @imagepng($imgplain); if (!$check) { return $this->_imageError($file, $firsttime, 'Error creating temporary image object whilst using GD library to parse PNG image'); } $this->_tempimg = ob_get_contents(); $this->_tempimglnk = 'var:_tempimg'; ob_end_clean(); $info = $this->_getImage($this->_tempimglnk, false); if (!$info) { return $this->_imageError($file, $firsttime, 'Error parsing temporary file image object created with GD library to parse PNG image'); } imagedestroy($imgplain); $imgmask = count($this->images)+1; $minfo['cs'] = 'DeviceGray'; $minfo['i']=$imgmask ; $this->images[$tempfile_alpha] = $minfo; } else { $check = @imagepng($imgalpha, $tempfile_alpha); if (!$check) { return $this->_imageError($file, $firsttime, 'Failed to create temporary image file ('.$tempfile_alpha.') parsing PNG image with alpha channel ('.$errpng.')'); } imagedestroy($imgalpha); // extract image without alpha channel $imgplain = imagecreatetruecolor($w, $h); imagecopy($imgplain, $im, 0, 0, 0, 0, $w, $h); // create temp image file $check = @imagepng($imgplain, $tempfile); if (!$check) { return $this->_imageError($file, $firsttime, 'Failed to create temporary image file ('.$tempfile.') parsing PNG image with alpha channel ('.$errpng.')'); } imagedestroy($imgplain); // embed mask image $minfo = $this->_getImage($tempfile_alpha, false); unlink($tempfile_alpha); if (!$minfo) { return $this->_imageError($file, $firsttime, 'Error parsing temporary file ('.$tempfile_alpha.') created with GD library to parse PNG image'); } $imgmask = count($this->images)+1; $minfo['cs'] = 'DeviceGray'; $minfo['i']=$imgmask ; $this->images[$tempfile_alpha] = $minfo; // embed image, masked with previously embedded mask $info = $this->_getImage($tempfile, false); unlink($tempfile); if (!$info) { return $this->_imageError($file, $firsttime, 'Error parsing temporary file ('.$tempfile.') created with GD library to parse PNG image'); } } $info['masked'] = $imgmask; if ($ppUx) { $info['set-dpi'] = $ppUx; } $info['type']='png'; if ($firsttime) { $info['i']=count($this->images)+1; $this->images[$file]=$info; } return $info; } else { // No alpha/transparency set imagealphablending($im, false); imagesavealpha($im, false); imageinterlace($im, false); if (!is_writable($tempfile)) { ob_start(); $check = @imagepng($im); if (!$check) { return $this->_imageError($file, $firsttime, 'Error creating temporary image object whilst using GD library to parse PNG image'); } $this->_tempimg = ob_get_contents(); $this->_tempimglnk = 'var:_tempimg'; ob_end_clean(); $info = $this->_getImage($this->_tempimglnk, false); if (!$info) { return $this->_imageError($file, $firsttime, 'Error parsing temporary file image object created with GD library to parse PNG image'); } imagedestroy($im); } else { $check = @imagepng($im, $tempfile ); if (!$check) { return $this->_imageError($file, $firsttime, 'Failed to create temporary image file ('.$tempfile.') parsing PNG image ('.$errpng.')'); } imagedestroy($im); $info = $this->_getImage($tempfile, false) ; unlink($tempfile ); if (!$info) { return $this->_imageError($file, $firsttime, 'Error parsing temporary file ('.$tempfile.') created with GD library to parse PNG image'); } } if ($ppUx) { $info['set-dpi'] = $ppUx; } $info['type']='png'; if ($firsttime) { $info['i']=count($this->images)+1; $this->images[$file]=$info; } return $info; } } } else { $parms='/DecodeParms <</Predictor 15 /Colors '.($ct==2 ? 3 : 1).' /BitsPerComponent '.$bpc.' /Columns '.$w.'>>'; //Scan chunks looking for palette, transparency and image data $pal=''; $trns=''; $pngdata=''; $p = 33; do { $n=$this->_fourbytes2int(substr($data,$p,4)); $p += 4; $type=substr($data,$p,4); $p += 4; if($type=='PLTE') { //Read palette $pal=substr($data,$p,$n); $p += $n; $p += 4; } elseif($type=='tRNS') { //Read transparency info $t=substr($data,$p,$n); $p += $n; if($ct==0) $trns=array(ord(substr($t,1,1))); elseif($ct==2) $trns=array(ord(substr($t,1,1)),ord(substr($t,3,1)),ord(substr($t,5,1))); else { $pos=strpos($t,chr(0)); if(is_int($pos)) $trns=array($pos); } $p += 4; } elseif($type=='IDAT') { $pngdata.=substr($data,$p,$n); $p += $n; $p += 4; } elseif($type=='IEND') { break; } else if (preg_match('/[a-zA-Z]{4}/',$type)) { $p += $n+4; } else { return $this->_imageError($file, $firsttime, 'Error parsing PNG image data'); } } while($n); if (!$pngdata) { return $this->_imageError($file, $firsttime, 'Error parsing PNG image data - no IDAT data found'); } if($colspace=='Indexed' and empty($pal)) { return $this->_imageError($file, $firsttime, 'Error parsing PNG image data - missing colour palette'); } $info = array('w'=>$w,'h'=>$h,'cs'=>$colspace,'bpc'=>$bpc,'f'=>'FlateDecode','parms'=>$parms,'pal'=>$pal,'trns'=>$trns,'data'=>$pngdata); $info['type']='png'; if ($ppUx) { $info['set-dpi'] = $ppUx; } } if (!$info) { return $this->_imageError($file, $firsttime, 'Error parsing or converting PNG image'); } if ($firsttime) { $info['i']=count($this->images)+1; $this->images[$file]=$info; } return $info; } // GIF else if ($type == 'gif') { if (function_exists('gd_info')) { $gd = gd_info(); } else {$gd = array(); } if (isset($gd['GIF Read Support']) && $gd['GIF Read Support']) { $im = @imagecreatefromstring($data); if ($im) { $tempfile = _MPDF_TEMP_PATH.'_tempImgPNG'.RAND(1,10000).'.png'; imagealphablending($im, false); imagesavealpha($im, false); imageinterlace($im, false); if (!is_writable($tempfile)) { ob_start(); $check = @imagepng($im); if (!$check) { return $this->_imageError($file, $firsttime, 'Error creating temporary image object whilst using GD library to parse GIF image'); } $this->_tempimg = ob_get_contents(); $this->_tempimglnk = 'var:_tempimg'; ob_end_clean(); $info = $this->_getImage($this->_tempimglnk, false); if (!$info) { return $this->_imageError($file, $firsttime, 'Error parsing temporary file image object created with GD library to parse GIF image'); } imagedestroy($im); } else { $check = @imagepng($im, $tempfile); if (!$check) { return $this->_imageError($file, $firsttime, 'Error creating temporary file ('.$tempfile.') whilst using GD library to parse GIF image'); } $info = $this->_getImage($tempfile, false); if (!$info) { return $this->_imageError($file, $firsttime, 'Error parsing temporary file ('.$tempfile.') created with GD library to parse GIF image'); } imagedestroy($im); unlink($tempfile); } $info['type']='gif'; if ($firsttime) { $info['i']=count($this->images)+1; $this->images[$file]=$info; } return $info; } else { return $this->_imageError($file, $firsttime, 'Error creating GD image file from GIF image'); } } if (!class_exists('gif', false)) { include_once(_MPDF_PATH.'classes/gif.php'); } $gif=new CGIF(); $h=0; $w=0; $gif->loadFile($data, 0); if(isset($gif->m_img->m_gih->m_bLocalClr) && $gif->m_img->m_gih->m_bLocalClr) { $nColors = $gif->m_img->m_gih->m_nTableSize; $pal = $gif->m_img->m_gih->m_colorTable->toString(); if($bgColor != -1) { $bgColor = $gif->m_img->m_gih->m_colorTable->colorIndex($bgColor); } $colspace='Indexed'; } elseif(isset($gif->m_gfh->m_bGlobalClr) && $gif->m_gfh->m_bGlobalClr) { $nColors = $gif->m_gfh->m_nTableSize; $pal = $gif->m_gfh->m_colorTable->toString(); if((isset($bgColor)) and $bgColor != -1) { $bgColor = $gif->m_gfh->m_colorTable->colorIndex($bgColor); } $colspace='Indexed'; } else { $nColors = 0; $bgColor = -1; $colspace='DeviceGray'; $pal=''; } $trns=''; if(isset($gif->m_img->m_bTrans) && $gif->m_img->m_bTrans && ($nColors > 0)) { $trns=array($gif->m_img->m_nTrans); } $gifdata=$gif->m_img->m_data; $w=$gif->m_gfh->m_nWidth; $h=$gif->m_gfh->m_nHeight; $gif->ClearData(); if($colspace=='Indexed' and empty($pal)) { return $this->_imageError($file, $firsttime, 'Error parsing GIF image - missing colour palette'); } if ($this->compress) { $gifdata=gzcompress($gifdata); $info = array( 'w'=>$w, 'h'=>$h, 'cs'=>$colspace, 'bpc'=>8, 'f'=>'FlateDecode', 'pal'=>$pal, 'trns'=>$trns, 'data'=>$gifdata); } else { $info = array( 'w'=>$w, 'h'=>$h, 'cs'=>$colspace, 'bpc'=>8, 'pal'=>$pal, 'trns'=>$trns, 'data'=>$gifdata); } $info['type']='gif'; if ($firsttime) { $info['i']=count($this->images)+1; $this->images[$file]=$info; } return $info; } /*-- IMAGES-BMP --*/ // BMP (Windows Bitmap) else if ($type == 'bmp') { if (!class_exists('bmp', false)) { include(_MPDF_PATH.'classes/bmp.php'); } if (empty($this->bmp)) { $this->bmp = new bmp($this); } $info = $this->bmp->_getBMPimage($data, $file); if (isset($info['error'])) { return $this->_imageError($file, $firsttime, $info['error']); } if ($firsttime) { $info['i']=count($this->images)+1; $this->images[$file]=$info; } return $info; } /*-- END IMAGES-BMP --*/ /*-- IMAGES-WMF --*/ // WMF else if ($type == 'wmf') { if (!class_exists('wmf', false)) { include(_MPDF_PATH.'classes/wmf.php'); } if (empty($this->wmf)) { $this->wmf = new wmf($this); } $wmfres = $this->wmf->_getWMFimage($data); if ($wmfres[0]==0) { if ($wmfres[1]) { return $this->_imageError($file, $firsttime, $wmfres[1]); } return $this->_imageError($file, $firsttime, 'Error parsing WMF image'); } $info = array('x'=>$wmfres[2][0],'y'=>$wmfres[2][1],'w'=>$wmfres[3][0],'h'=>$wmfres[3][1],'data'=>$wmfres[1]); $info['i']=count($this->formobjects)+1; $info['type']='wmf'; $this->formobjects[$file]=$info; return $info; } /*-- END IMAGES-WMF --*/ // UNKNOWN TYPE - try GD imagecreatefromstring else { if (function_exists('gd_info')) { $gd = gd_info(); } else {$gd = array(); } if (isset($gd['PNG Support']) && $gd['PNG Support']) { $im = @imagecreatefromstring($data); if (!$im) { return $this->_imageError($file, $firsttime, 'Error parsing image file - image type not recognised, and not supported by GD imagecreate'); } $tempfile = _MPDF_TEMP_PATH.'_tempImgPNG'.RAND(1,10000).'.png'; imagealphablending($im, false); imagesavealpha($im, false); imageinterlace($im, false); $check = @imagepng($im, $tempfile); if (!$check) { return $this->_imageError($file, $firsttime, 'Error creating temporary file ('.$tempfile.') whilst using GD library to parse unknown image type'); } $info = $this->_getImage($tempfile, false); imagedestroy($im); unlink($tempfile); if (!$info) { return $this->_imageError($file, $firsttime, 'Error parsing temporary file ('.$tempfile.') created with GD library to parse unknown image type'); } $info['type']='png'; if ($firsttime) { $info['i']=count($this->images)+1; $this->images[$file]=$info; } return $info; } } return $this->_imageError($file, $firsttime, 'Error parsing image file - image type not recognised'); }
public function draw(SVGRenderingHelper $rh, $scaleX, $scaleY, $offsetX = 0, $offsetY = 0) { $rh->push(); $opacity = $this->getStyle('opacity'); if (isset($opacity) && is_numeric($opacity)) { $opacity = floatval($opacity); $rh->scaleOpacity($opacity); } // original (document fragment) width for unit parsing $ow = $rh->getWidth() / $scaleX; $cx = ($offsetX + $this->cx) * $scaleX; $cy = ($offsetY + $this->cy) * $scaleY; $rx = $this->rx * $scaleX; $ry = $this->ry * $scaleY; $fill = $this->getComputedStyle('fill'); if (isset($fill) && $fill !== 'none') { $fillColor = SVG::parseColor($fill, true); $rh->fillEllipse($cx, $cy, $rx, $ry, $fillColor); } $stroke = $this->getComputedStyle('stroke'); if (isset($stroke) && $stroke !== 'none') { $strokeColor = SVG::parseColor($stroke, true); $rh->setStrokeWidth(SVG::convertUnit($this->getComputedStyle('stroke-width'), $ow) * $scaleX); $rh->drawEllipse($cx, $cy, $rx, $ry, $strokeColor); } $rh->pop(); }
public function draw(SVGRenderingHelper $rh, $scaleX, $scaleY, $offsetX = 0, $offsetY = 0) { $rh->push(); $opacity = $this->getStyle('opacity'); if (isset($opacity) && is_numeric($opacity)) { $opacity = floatval($opacity); $rh->scaleOpacity($opacity); } // original (document fragment) width for unit parsing $ow = $rh->getWidth() / $scaleX; $p = array(); $np = count($this->points); for ($i = 0; $i < $np; $i++) { $point = $this->points[$i]; $p[] = ($offsetX + $point[0]) * $scaleX; $p[] = ($offsetY + $point[1]) * $scaleY; } $fill = $this->getComputedStyle('fill'); if (isset($fill) && $fill !== 'none') { $fillColor = SVG::parseColor($fill, true); $rh->fillPolygon($p, $np, $fillColor); } $stroke = $this->getComputedStyle('stroke'); if (isset($stroke) && $stroke !== 'none') { $strokeColor = SVG::parseColor($stroke, true); $rh->setStrokeWidth(SVG::convertUnit($this->getComputedStyle('stroke-width'), $ow) * $scaleX); $rh->drawPolyline($p, $np, $strokeColor); } $rh->pop(); }
public function execute(&$value, &$error) { // file upload check foreach ($value['error'] as $error_code) { if ($error_code) { $error = $this->getParameter('upload_error'); return false; } } $validation = sfConfig::get('app_images_validation'); // weight check foreach ($value['size'] as $file_size) { if ($file_size > $validation['weight']) { $error = $this->getParameter('weight_error'); return false; } } // type check // FIXME with symfony 1.0, the type is the one given by the browser // we prefer to use or own mime type checker (this is what is done in further // versions of symfony, using system file check) foreach ($value['tmp_name'] as $file) { $file_type = c2cTools::getMimeType($file); if (!in_array($file_type, $validation['mime_types'])) { $error = $this->getParameter('type_error'); return false; } } foreach ($value['tmp_name'] as $k => $filename) { if ($value['type'][$k] != 'image/svg+xml') { list($width, $height) = getimagesize($filename); } else { // are there any script? if (SVG::hasScript($filename)) { $error = $this->getParameter('svg_script_error'); return false; } // dimensions $dimensions = SVG::getSize($filename); if ($dimensions === false) { $error = $this->getParameter('svg_error'); return false; } else { list($width, $height) = $dimensions; } } // height/width check if ($width > $validation['max_size']['width'] || $height > $validation['max_size']['height']) { $error = $this->getParameter('max_dim_error'); return false; } if ($width < $validation['min_size']['width'] || $height < $validation['min_size']['height']) { $error = $this->getParameter('min_dim_error'); return false; } } return true; }
public function draw(SVGRenderingHelper $rh, $scaleX, $scaleY, $offsetX = 0, $offsetY = 0) { $rh->push(); $opacity = $this->getStyle('opacity'); if (isset($opacity) && is_numeric($opacity)) { $opacity = floatval($opacity); $rh->scaleOpacity($opacity); } // original (document fragment) width for unit parsing $ow = $rh->getWidth() / $scaleX; $x1 = ($offsetX + $this->x1) * $scaleX; $y1 = ($offsetY + $this->y1) * $scaleY; $x2 = ($offsetX + $this->x2) * $scaleX; $y2 = ($offsetY + $this->y2) * $scaleY; $stroke = $this->getComputedStyle('stroke'); if (isset($stroke) && $stroke !== 'none') { $strokeColor = SVG::parseColor($stroke, true); $rh->setStrokeWidth(SVG::convertUnit($this->getComputedStyle('stroke-width'), $ow) * $scaleX); $rh->drawLine($x1, $y1, $x2, $y2, $strokeColor); } $rh->pop(); }
public function execute(&$value, &$error) { // whether the image was sent via plupload or not $plupload = (bool) (!$this->getContext()->getRequest()->getParameter('noplupload', false)); // file upload check if ($value['error']) { // if plupload was used, most probably the resized image // was too big, so provide custom error message if ($plupload) { $error = $this->getParameter('upload_resize_error'); } else { $error = $this->getParameter('upload_error'); } return false; } $validation = sfConfig::get('app_images_validation'); if ($value['size'] > $validation['weight']) { // same as above (in this case, max_file_size from php.ini is bigger than $validation['weight']) if ($plupload) { $error = $this->getParameter('weight_resize_error'); } else { $error = $this->getParameter('weight_error'); } return false; } // type check // with symfony 1.0, the type is the one given by the browser // we prefer to use or own mime type checker (this is what is done in further // versions of symfony, using system file check) $mime_type = c2cTools::getMimeType($value['tmp_name']); if (!in_array($mime_type, $validation['mime_types'])) { $error = $this->getParameter('type_error'); return false; } if ($mime_type != 'image/svg+xml') { list($width, $height) = getimagesize($value['tmp_name']); } else { // are there any script? if (SVG::hasScript($value['tmp_name'])) { $error = $this->getParameter('svg_script_error'); return false; } // dimensions $dimensions = SVG::getSize($value['tmp_name']); if ($dimensions === false) { $error = $this->getParameter('svg_error'); return false; } else { list($width, $height) = $dimensions; } } // height/width check (max width not checked for SVG, it is automatically resized) if ($mime_type != 'image/svg+xml' && ($width > $validation['max_size']['width'] || $height > $validation['max_size']['height'])) { $error = $this->getParameter('max_dim_error'); return false; } if ($width < $validation['min_size']['width'] || $height < $validation['min_size']['height']) { $error = $this->getParameter('min_dim_error'); return false; } return true; }
/** * Executes edit action. */ public function executeEdit() { // populate objects for form display depending on what we are doing (creating, editing) $this->setEditFormInformation(); // All modules will use the same template $this->setTemplate('../../documents/templates/edit'); $document = $this->document; $module_name = $this->getModuleName(); $this->document_name = $document->get('name'); // Culture (lang) is automatically defined in Hydrate, // redefined in the model. if ($this->getRequest()->getMethod() == sfRequest::POST) { $lang = $this->getRequestParameter('lang'); $user_id = $this->getUser()->getId(); $is_minor = $this->getRequestParameter('rev_is_minor', false); $message = $this->getRequestParameter('rev_comment'); $document->setCulture($lang); $old_lon = $document->get('lon'); $old_lat = $document->get('lat'); $this->setDataFields($document); // upload potential GPX file to server and set WKT field // or upload a new version of an image $request = $this->getRequest(); if ($request->hasFiles()) { c2cTools::log('request has files'); if ($request->getFileName('image_new_version') && $module_name == 'images') { c2cTools::log('new image uploaded'); $base_path = sfConfig::get('sf_upload_dir') . DIRECTORY_SEPARATOR; $temp_dir = $base_path . sfConfig::get('app_images_temp_directory_name'); $upload_dir = $base_path . sfConfig::get('app_images_directory_name'); $filename = $request->getFiles(); $unique_filename = c2cTools::generateUniqueName(); $file_ext = Images::detectExtension($filename['image_new_version']['tmp_name']); // upload file in a temporary folder $new_location = $temp_dir . DIRECTORY_SEPARATOR . $unique_filename . $file_ext; sfLoader::loadHelpers(array('General')); $redir_route = '@document_by_id_lang_slug?module=' . $module_name . '&id=' . $this->document->get('id') . '&lang=' . $this->document->getCulture() . '&slug=' . get_slug($this->document); if (!$request->moveFile('image_new_version', $new_location)) { return $this->setErrorAndRedirect('Failed moving uploaded file', $redir_route); } if ($file_ext == '.svg') { if (!SVG::rasterize($temp_dir . DIRECTORY_SEPARATOR, $unique_filename, $file_ext)) { return $this->setErrorAndRedirect('Failed rasterizing svg file', $redir_route); } $document->set('has_svg', true); } else { $document->set('has_svg', false); } // generate thumbnails (ie. resized images: "BI"/"SI") Images::generateThumbnails($unique_filename, $file_ext, $temp_dir); // move to uploaded images directory if (!Images::moveAll($unique_filename . $file_ext, $temp_dir, $upload_dir)) { return $this->setErrorAndRedirect('image dir unavailable', $redir_route); } // update filename and image properties $document->set('filename', $unique_filename . $file_ext); $size = getimagesize($upload_dir . DIRECTORY_SEPARATOR . $unique_filename . $file_ext); if ($size) { $document->set('width', $size[0]); $document->set('height', $size[1]); } $document->set('file_size', filesize($upload_dir . DIRECTORY_SEPARATOR . $unique_filename . $file_ext)); // populate with new exif data, if any... $document->populateWithExifDataFrom($upload_dir . DIRECTORY_SEPARATOR . $unique_filename . $file_ext); } if ($request->getFileName('gps_data') && in_array($module_name, array('routes', 'outings'))) { // it is necessary to preserve both tests nested. if ($wkt = $this->getWktFromFileUpload($request)) { c2cTools::log('wkt extracted'); $document->set('geom_wkt', $wkt); // NB: these fields exist in both objects for which a file upload is possible (outings, routes) $_a = ParseGeo::getCumulatedHeightDiffFromWkt($wkt); if (!$document->get('height_diff_up')) { $document->set('height_diff_up', $_a['up']); c2cTools::log('height diff up set from wkt : ' . $_a['up']); } if (!$document->get('height_diff_down')) { $document->set('height_diff_down', $_a['down']); c2cTools::log('height diff down set from wkt : ' . $_a['down']); } $message = '[geodata] ' . (!$message ? "Edit with geometry upload" : $message); } else { $this->getRequest()->setError('gps_data', 'invalid gpx file'); return false; } } } if (count($this->document->getModified()) == 0 && count($this->document->getCurrentI18nObject()->getModified()) == 0) { // no change of the document was detected // => redirects to the document without saving anything $this->redirectToView(); return; } // we prevent here concurrent edition : // fake data so that second test always fails on summit creation (and when document is an archive) : $rev_when_edition_begun = 1; $current_rev = 0; // test if id exists (summit update) before checking concurrent edition // and if this is not an archive (editing an old document to reverse wrong changes) // (because only useful for document update) : if (($id = $this->getRequestParameter('id')) && !$this->getRequestParameter('editing_archive')) { $rev_when_edition_begun = $this->getRequestParameter('revision'); $current_rev = $document->getVersion(); } c2cTools::log("Document {$id} in {$lang} : rev when edition begun : {$rev_when_edition_begun} - current rev : {$current_rev}"); if ($rev_when_edition_begun < $current_rev) { c2cTools::log("Document {$id} in {$lang} has been concurrently saved. {$rev_when_edition_begun} < {$current_rev}"); // document has been saved by someone else during edition // we present datas entered in the same form $this->document = $document; // and we launch a preview with the document in its true current state: $this->concurrent_edition = true; // if the current_document variable is available in the edit template, we display the preview of it. } else { $message = !$message ? "Edit in {$lang}" : $message; // if document has a geometry, compute and create associations with ranges, depts, countries. // nb: association is performed upon document creation with initial geometry // OR when the centroid (lon, lat) has moved during an update. $needs_geom_association = isset($wkt) || $document->get('lon') != $old_lon && $document->get('lon') != null || $document->get('lat') != $old_lat && $document->get('lat') != null; // geom centroid has moved $document->doSaveWithMetadata($user_id, $is_minor, $message); $this->success = true; // means that child class can redirect to document view after other operations if needed (eg: associations). $this->document = $document; $id = $document->get('id'); if ($needs_geom_association) { c2cTools::log('executeEdit: needs_geom_association'); // we create new associations : // (and delete old associations before creating the new ones) // (and do not create outings-maps associations) $nb_created = gisQuery::createGeoAssociations($id, true, $module_name != 'outings'); c2cTools::log("created {$nb_created} geo associations"); // if summit or site coordinates have moved (hence $needs_geom_association = true), // refresh geo-associations of associated routes (from summits) and outings (from routes or sites) $this->refreshGeoAssociations($id); } // we clear views, histories, diffs of this doc + filter and list, in every language (content+interface): $this->clearCache($module_name, $id); // we clear views of the associated docs in every language (content+interface): // find all associated docs // 'users' module is excuded because a change of a user page have no visibility in associated docs, then it is not necessary to clear the cache of all associated outings if ($module_name != 'users') { $associated_docs = Association::findAllAssociatedDocs($id, array('id', 'module')); $ids = array(); foreach ($associated_docs as $doc) { $doc_id = $doc['id']; $doc_module = $doc['module']; // clear their view cache $this->clearCache($doc_module, $doc_id, false, 'view'); if ($module_name == 'outings' && in_array($doc_module, array('routes', 'sites')) || $module_name == 'routes' && in_array($doc_module, array('summits', 'parkings'))) { $ids[] = $doc_id; } } if ($module_name == 'outings') { $associated_docs = Association::findAllAssociatedDocs($ids, array('id', 'module'), array('sr', 'hr', 'pr', 'rr', 'pt', 'ht')); $ids = array(); foreach ($associated_docs as $doc) { $doc_id = $doc['id']; $doc_module = $doc['module']; // clear their view cache $this->clearCache($doc_module, $doc_id, false, 'view'); if (in_array($doc_module, array('summits', 'parkings', 'sites'))) { $ids[] = $doc_id; } } if (count($ids)) { $associated_docs = Association::findMainAssociatedDocs($ids, array('id', 'module'), array('ss', 'pp', 'tt')); foreach ($associated_docs as $doc) { // clear their view cache $this->clearCache($doc['module'], $doc['id'], false, 'view'); } } } elseif ($module_name == 'routes') { $associated_docs = Association::findMainAssociatedDocs($ids, array('id', 'module'), array('ss', 'pp')); foreach ($associated_docs as $doc) { // clear their view cache $this->clearCache($doc['module'], $doc['id'], false, 'view'); } } } // saves new document id in a "pseudo id" cookie to retrieve it if user resubmits original form if ($this->new_document && $this->pseudo_id) { $this->getResponse()->setCookie($this->pseudo_id, $id); } } // Go through simple heuristics to check for potential vandalism Vandalism::check($this->document); } else { // We display edit form. Retrieve nb comments $this->nb_comments = $this->new_document ? 0 : PunbbComm::retrieveNbComments($document->get('id') . '_' . $document->getCulture()); } // module specific actions $this->endEdit(); }
/** This function is used to validate an uploaded image. * It is quite similar to myImageValidator, except * that we cannot validate images one by one (when several ones * are uploaded at the same time). Thus, we have some custom * validation mechanism here */ public static function validate_image(&$value, &$error, $i) { // file upload check if ($value['error'][$i]) { $error = 'file failed to upload'; return false; } $validation = sfConfig::get('app_images_validation'); if ($value['size'][$i] > $validation['weight']) { $error = 'file is too big'; return false; } // type check // FIXME with symfony 1.0, the type is the one given by the browser // we prefer to use or own mime type checker (this is what is done in further // versions of symfony, using system file check) $mime_type = c2cTools::getMimeType($value['tmp_name'][$i]); if (!in_array($mime_type, $validation['mime_types'])) { $error = 'file has incorrect type'; return false; } if ($mime_type != 'image/svg+xml') { list($width, $height) = getimagesize($value['tmp_name'][$i]); } else { // are there any script? if (SVG::hasScript($value['tmp_name'][$i])) { $error = 'file cannot contain scripts'; return false; } // dimensions $dimensions = SVG::getSize($value['tmp_name'][$i]); if ($dimensions === false) { $error = 'file is malformed SVG'; return false; } else { list($width, $height) = $dimensions; } } // height/width check if ($width > $validation['max_size']['width'] || $height > $validation['max_size']['height']) { $error = 'file is too large'; return false; } if ($width < $validation['min_size']['width'] || $height < $validation['min_size']['height']) { $error = 'min_dim_error'; return false; } return true; }
public function draw(SVGRenderingHelper $rh, $scaleX, $scaleY, $offsetX = 0, $offsetY = 0) { $rh->push(); $opacity = $this->getStyle('opacity'); if (isset($opacity) && is_numeric($opacity)) { $opacity = floatval($opacity); $rh->scaleOpacity($opacity); } // original (document fragment) width for unit parsing $ow = $rh->getWidth() / $scaleX; // start of polygon construction $polys = array(); $currentPoly = null; $x = 0; $y = 0; $startX = null; $startY = null; $matches = array(); preg_match_all('/[MLHVCQAZ][^MLHVCQAZ]*/i', $this->d, $matches, PREG_SET_ORDER); foreach ($matches as $match) { $match = trim($match[0]); $command = substr($match, 0, 1); $args = preg_split('/[\\s,]+/', trim(substr($match, 1))); if ($command === 'M') { // moveto absolute foreach (array_chunk($args, 2) as $args) { if (count($args) < 2) { break 2; } $x = floatval($args[0]); $y = floatval($args[1]); $startX = $x; $startY = $y; if (!empty($currentPoly)) { $polys[] = $currentPoly; } $currentPoly = array(($offsetX + $x) * $scaleX, ($offsetY + $y) * $scaleY); } } else { if ($command === 'm') { // moveto relative foreach (array_chunk($args, 2) as $args) { if (count($args) < 2) { break 2; } $x += floatval($args[0]); $y += floatval($args[1]); $startX = $x; $startY = $y; if (!empty($currentPoly)) { $polys[] = $currentPoly; } $currentPoly = array(($offsetX + $x) * $scaleX, ($offsetY + $y) * $scaleY); } } else { if ($command === 'L') { // lineto absolute foreach (array_chunk($args, 2) as $args) { if (count($args) < 2) { break 2; } $x = floatval($args[0]); $y = floatval($args[1]); $currentPoly[] = ($offsetX + $x) * $scaleX; $currentPoly[] = ($offsetY + $y) * $scaleY; } } else { if ($command === 'l') { // lineto relative foreach (array_chunk($args, 2) as $args) { if (count($args) < 2) { break 2; } $x += floatval($args[0]); $y += floatval($args[1]); $currentPoly[] = ($offsetX + $x) * $scaleX; $currentPoly[] = ($offsetY + $y) * $scaleY; } } else { if ($command === 'H') { // lineto horizontal absolute if (empty($args)) { break; } foreach ($args as $arg) { $x = floatval($arg); $currentPoly[] = ($offsetX + $x) * $scaleX; $currentPoly[] = ($offsetY + $y) * $scaleY; } } else { if ($command === 'h') { // lineto horizontal relative if (empty($args)) { break; } foreach ($args as $arg) { $x += floatval($arg); $currentPoly[] = ($offsetX + $x) * $scaleX; $currentPoly[] = ($offsetY + $y) * $scaleY; } } else { if ($command === 'V') { // lineto vertical absolute if (empty($args)) { break; } foreach ($args as $arg) { $y = floatval($arg); $currentPoly[] = ($offsetX + $x) * $scaleX; $currentPoly[] = ($offsetY + $y) * $scaleY; } } else { if ($command === 'v') { // lineto vertical relative if (empty($args)) { break; } foreach ($args as $arg) { $y += floatval($arg); $currentPoly[] = ($offsetX + $x) * $scaleX; $currentPoly[] = ($offsetY + $y) * $scaleY; } } else { if ($command === 'Z' || $command === 'z') { // end if (!empty($args)) { break; } $x = $startX !== null ? $startX : 0; $y = $startY !== null ? $startY : 0; $currentPoly[] = ($offsetX + $x) * $scaleX; $currentPoly[] = ($offsetY + $y) * $scaleY; } else { if ($command === 'C') { // curveto cubic absolute foreach (array_chunk($args, 6) as $args) { if (count($args) < 6) { break 2; } // start point $p0x = ($offsetX + $x) * $scaleX; $p0y = ($offsetY + $y) * $scaleY; // first control point $p1x = ($offsetX + floatval($args[0])) * $scaleX; $p1y = ($offsetY + floatval($args[1])) * $scaleY; // second control point $p2x = ($offsetX + floatval($args[2])) * $scaleX; $p2y = ($offsetY + floatval($args[3])) * $scaleY; // final point $nx = floatval($args[4]); $ny = floatval($args[5]); $p3x = ($offsetX + $nx) * $scaleX; $p3y = ($offsetY + $ny) * $scaleY; $currentPoly = array_merge($currentPoly, SVGRenderingHelper::approximateCubicBezier(array($p0x, $p0y), array($p1x, $p1y), array($p2x, $p2y), array($p3x, $p3y))); $x = $nx; $y = $ny; } } else { if ($command === 'c') { // curveto cubic relative foreach (array_chunk($args, 6) as $args) { if (count($args) < 6) { break 2; } // start point $p0x = ($offsetX + $x) * $scaleX; $p0y = ($offsetY + $y) * $scaleY; // first control point $p1x = ($offsetX + $x + floatval($args[0])) * $scaleX; $p1y = ($offsetY + $y + floatval($args[1])) * $scaleY; // second control point $p2x = ($offsetX + $x + floatval($args[2])) * $scaleX; $p2y = ($offsetY + $y + floatval($args[3])) * $scaleY; // final point $nx = $x + floatval($args[4]); $ny = $y + floatval($args[5]); $p3x = ($offsetX + $nx) * $scaleX; $p3y = ($offsetY + $ny) * $scaleY; $currentPoly = array_merge($currentPoly, SVGRenderingHelper::approximateCubicBezier(array($p0x, $p0y), array($p1x, $p1y), array($p2x, $p2y), array($p3x, $p3y))); $x = $nx; $y = $ny; } } else { if ($command === 'Q') { // curveto quadratic absolute foreach (array_chunk($args, 4) as $args) { if (count($args) < 4) { break 2; } // start point $p0x = ($offsetX + $x) * $scaleX; $p0y = ($offsetY + $y) * $scaleY; // control point $p1x = ($offsetX + floatval($args[0])) * $scaleX; $p1y = ($offsetY + floatval($args[1])) * $scaleY; // final point $nx = floatval($args[2]); $ny = floatval($args[3]); $p2x = ($offsetX + $nx) * $scaleX; $p2y = ($offsetY + $ny) * $scaleY; $currentPoly = array_merge($currentPoly, SVGRenderingHelper::approximateQuadraticBezier(array($p0x, $p0y), array($p1x, $p1y), array($p2x, $p2y))); $x = $nx; $y = $ny; } } else { if ($command === 'q') { // curveto quadratic relative foreach (array_chunk($args, 4) as $args) { if (count($args) < 4) { break 2; } // start point $p0x = ($offsetX + $x) * $scaleX; $p0y = ($offsetY + $y) * $scaleY; // control point $p1x = ($offsetX + $x + floatval($args[0])) * $scaleX; $p1y = ($offsetY + $y + floatval($args[1])) * $scaleY; // final point $nx = $x + floatval($args[2]); $ny = $y + floatval($args[3]); $p2x = ($offsetX + $nx) * $scaleX; $p2y = ($offsetY + $ny) * $scaleY; $currentPoly = array_merge($currentPoly, SVGRenderingHelper::approximateQuadraticBezier(array($p0x, $p0y), array($p1x, $p1y), array($p2x, $p2y))); $x = $nx; $y = $ny; } } } } } } } } } } } } } } } if (!empty($currentPoly)) { $polys[] = $currentPoly; } // fill $fill = $this->getComputedStyle('fill'); if (isset($fill) && $fill !== 'none') { $fillColor = SVG::parseColor($fill, true); foreach ($polys as $poly) { $numpoints = count($poly) / 2; if ($numpoints >= 3) { $rh->fillPolygon($poly, $numpoints, $fillColor); } } } // outline $stroke = $this->getComputedStyle('stroke'); if (isset($stroke) && $stroke !== 'none') { $strokeColor = SVG::parseColor($stroke, true); $rh->setStrokeWidth(SVG::convertUnit($this->getComputedStyle('stroke-width'), $ow) * $scaleX); foreach ($polys as $poly) { $rh->drawPolyline($poly, count($poly) / 2, $strokeColor); } } $rh->pop(); }
private function handleImage($image_name, $tmp_name, $temp_dir, $index = 1) { // copy the image to the temp directory $filename = $tmp_name; $unique_filename = c2cTools::generateUniqueName(); $file_ext = Images::detectExtension($filename); $new_location = $temp_dir . $unique_filename . $file_ext; if (!move_uploaded_file($filename, $new_location)) { return array('error' => array('field' => 'image_file', 'msg' => 'Failed moving uploaded file')); } // svg if ($file_ext == '.svg') { if (!SVG::rasterize($temp_dir, $unique_filename, $file_ext)) { return array('error' => array('field' => 'image_file', 'msg' => 'Failed rasterizing svg file')); } } // if jpg, check if we need orientation changes if ($file_ext == '.jpg') { Images::correctOrientation($new_location); } // generate thumbnails Images::generateThumbnails($unique_filename, $file_ext, $temp_dir); // look iptc for a possible title (jpeg only) if ($file_ext == '.jpg') { $size = getimagesize($new_location, $info); if (isset($info['APP13'])) { $iptc = iptcparse($info['APP13']); if (isset($iptc['2#105'])) { $image_title = trim($iptc['2#105'][0]); } else { if (isset($iptc['2#120'])) { $image_title = trim($iptc['2#120'][0]); } } } } if (isset($image_title)) { $encoding = mb_detect_encoding($image_title, "UTF-8, ISO-8859-1, ISO-8859-15", true); if ($encoding !== false) { if ($encoding != 'UTF-8') { $image_title = mb_convert_encoding($image_title, 'UTF-8', $encoding); } else { $image_title = $image_title; } } // if encoding could not be detected, rather not try to put it as prefilled title } // we are also interested at this point on the exif date in order to reorder images on the client side if ($file_ext == '.jpg' && ($exif = exif_read_data($new_location))) { if (isset($exif['DateTimeOriginal'])) { $image_date = str_replace(' ', ':', $exif['DateTimeOriginal']); $image_date = explode(':', $image_date); $image_date = mktime($image_date[3], $image_date[4], $image_date[5], $image_date[1], $image_date[2], $image_date[0]); } } return array('image_filename' => $unique_filename . $file_ext, 'default_license' => $this->getDefaultImageLicense($this->getRequestParameter('document_id'), $this->getRequestParameter('mod')), 'image_number' => (intval($this->getRequestparameter('image_number')) + 1) * 1000 + $index, 'image_title' => isset($image_title) ? $image_title : null, 'image_datetime' => isset($image_date) && $image_date ? $image_date : null); }
<div class="row"> <div class="col-md-4 text-blue-grey" markdown="1"> # Leverage the power of Freedom in your app. #### Get started with one of [our guides](/api/getting-started), or jump straight into the [API documentation](/api/entities). </div> <div class="col-md-8"> <div class="breather-lg"></div> <?php echo SVG::create($path . "/images/svg/globe.svg", [600, 450], false, true); ?> </div> </div> <div class="breather-lg"></div> </div> </div> <div class="body-feature bg-blue-grey bg-300">