Pass array to Excel - php

I am using (trying to use) PHPExcel to pass an array to excel, I have defined the headings and i want every array in the array to in a separate row.
However, this only puts the headings in the excel file and not the data from the array. What am i doing wrong?How can I get this to work?
Script:
<?php
$databasehost = "localhost";
$databasename = "dummydata";
$databasetable = "import1";
$databasetable2 = "data1";
$databaseusername ="dummydata";
$databasepassword = "dummydata";
$con = #mysql_connect($databasehost,$databaseusername,$databasepassword) or die(mysql_error());
#mysql_select_db($databasename) or die(mysql_error());
$query = mysql_query("SELECT * from $databasetable;");
$data = array();
$index = 0;
while($row = mysql_fetch_assoc($query))
{
$data[$index] = $row;
$index++;
}
foreach ($data as $key) {
$url = 'http://maps.googleapis.com/maps/api/geocode/json?latlng='.$key['latitude'].','.$key['longitude'].'&sensor=true';
$json = file_get_contents($url);
$dataReceived = json_decode($json, TRUE);
//echo '<pre>'; print_r($dataReceived['results']); echo '</pre>';
$compiled = array();
$index = 0;
foreach ($dataReceived['results'] as $value) {
$compiled[$index] = array(
'ref' => $key['id']);
foreach ($value['address_components'] as $value2)
{
$compiled[$index][$value2['types'][0]] = $value2['long_name'];
}
$index++;
}
$sortedData = array();
$index = 0;
foreach ($compiled as $value) {
//echo '<pre>'; print_r($value); echo '</pre>';
$sortedData[$index] = array(
'ref' => $value['ref'],
'lat' => $key['latitude'],
'long' => $key['longitude'],
'route' => $value['route'],
'locality' => $value['locality'],
'administrative_area_level_2' => $value['administrative_area_level_2'],
'administrative_area_level_1' => $value['administrative_area_level_1'],
'country' => $value['country'],
'postal_code_prefix' => $value['postal_code_prefix'],
'postal_town' => $value['postal_town'],
'postal_code' => $value['postal_code'],
'administrative_area_level_3' => $value['administrative_area_level_3'],
'street_number' => $value['street_number'],
'establishment' => $value['establishment'],
);
$index++;
}
echo '<pre>';print_r($sortedData);echo "</pre>";
/*$query = mysql_query("INSERT INTO $databasetable2
ref, lat, long, route, locality, administrative_area_level_2, administrative_area_level_1, country, postal_code_prefix, postal_town)
VALUES
()");*/
}
#mysql_close($con);
/**
* PHPExcel
*
* Copyright (C) 2006 - 2011 PHPExcel
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
* #category PHPExcel
* #package PHPExcel
* #copyright Copyright (c) 2006 - 2011 PHPExcel (http://www.codeplex.com/PHPExcel)
* #license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL
* #version ##VERSION##, ##DATE##
*/
/** Error reporting */
error_reporting(E_ALL);
ini_set('display_errors', '1');
date_default_timezone_set('Europe/London');
/** PHPExcel */
require_once 'Classes/PHPExcel.php';
// Create new PHPExcel object
//echo date('H:i:s') . " Create new PHPExcel object\n";
$objPHPExcel = new PHPExcel();
// Set properties
//echo date('H:i:s') . " Set properties\n";
$objPHPExcel->getProperties()->setCreator("Anon")
->setLastModifiedBy("Anon")
->setTitle("Crawler Data");
// Add some data
//echo date('H:i:s') . " Add some data\n";
$objPHPExcel->setActiveSheetIndex(0)
->setCellValue('A1', 'ref')
->setCellValue('B1', 'latitude')
->setCellValue('C1', 'longitude')
->setCellValue('D1', 'route')
->setCellValue('E1', 'locality')
->setCellValue('F1', 'administrative_area_level_2')
->setCellValue('G1', 'administrative_area_level_1')
->setCellValue('H1', 'country')
->setCellValue('I1', 'postal_code_prefix')
->setCellValue('J1', 'postal_town')
->setCellValue('K1', 'postal_code')
->setCellValue('L1', 'administrative_area_level_3')
->setCellValue('M1', 'street_number')
->setCellValue('N1', 'establishment');
//$objPHPExcel->getActiveSheet()->fromArray($sortedData, null, 'A2');
// Set active sheet index to the first sheet, so Excel opens this as the first sheet
$objPHPExcel->setActiveSheetIndex(0);
// Save Excel 2007 file
//echo date('H:i:s') . " Write to Excel2007 format\n";
//!!!!!!!!!!!!!!!!!!!-------- I Change 'Excel2007' to 'Excel5' ------!!!!!!!!!!!!!!!!!!!!!!!!
$objWriter = PHPExcel_IOFactory::createWriter($objPHPExcel, 'Excel5');
//!!!!!!!!!!!!!!!!!!!-------- I Change '.xlsx' to '.xls' ------!!!!!!!!!!!!!!!!!!!!!!!!
$objWriter->save(str_replace('.php', '.xls', __FILE__));
// Echo memory peak usage
//echo date('H:i:s') . " Peak memory usage: " . (memory_get_peak_usage(true) / 1024 / 1024) . " MB\r\n";
// Echo done
//echo date('H:i:s') . " Done writing file.\r\n";
?>
file now looks like:
<?php
require_once 'Classes/PHPExcel.php';
date_default_timezone_set('Europe/London');
$databasehost = "localhost";
$databasename = "ryansmur_crawler";
$databasetable = "import1";
$databasetable2 = "data1";
$databaseusername ="ryansmur_admin";
$databasepassword = "Penelope1";
$con = #mysql_connect($databasehost,$databaseusername,$databasepassword) or die(mysql_error());
#mysql_select_db($databasename) or die(mysql_error());
$query = mysql_query("SELECT * from $databasetable;");
$data = array();
$index = 0;
while($row = mysql_fetch_assoc($query))
{
$data[$index] = $row;
$index++;
}
$headers = array(
'ref', 'lat', 'long', 'route', 'locality', 'administrative_area_level_2',
'administrative_area_level_1', 'country', 'postal_code_prefix',
'postal_town', 'postal_code', 'administrative_area_level_3',
'street_number', 'establishment',
);
$addRowCreate = function(PHPExcel_Worksheet $sheet, $col = 'A', $row = NULL) {
return function(array $data) use ($sheet, $col, &$row) {
if ($row === NULL) {
$row = $sheet->getHighestRow() + 1;
}
$sheet->fromArray(array($data), NULL, "$col$row");
$row++;
};
};
$doc = new PHPExcel();
$doc->getProperties()->setCreator("Anon")
->setLastModifiedBy("Anon")
->setTitle("Crawler Data");
$sheet = $doc->setActiveSheetIndex(0);
$sheet->fromArray($headers);
$addRow = $addRowCreate($sheet);
foreach ($data as $key) {
$url = 'http://maps.googleapis.com/maps/api/geocode/json?latlng='.$key['latitude'].','.$key['longitude'].'&sensor=true';
$json = file_get_contents($url);
$dataReceived = json_decode($json, TRUE);
$compiled = array();
$index = 0;
foreach ($dataReceived['results'] as $value) {
$compiled[$index] = array(
'ref' => $key['id']);
foreach ($value['address_components'] as $value2)
{
$compiled[$index][$value2['types'][0]] = $value2['long_name'];
}
$index++;
}
$sortedData = array();
$index = 0;
foreach ($compiled as $value) {
$addRow(array(
'ref' => $value['ref'],
'lat' => $key['latitude'],
'long' => $key['longitude'],
'route' => $value['route'],
'locality' => $value['locality'],
'administrative_area_level_2' => $value['administrative_area_level_2'],
'administrative_area_level_1' => $value['administrative_area_level_1'],
'country' => $value['country'],
'postal_code_prefix' => $value['postal_code_prefix'],
'postal_town' => $value['postal_town'],
'postal_code' => $value['postal_code'],
'administrative_area_level_3' => $value['administrative_area_level_3'],
'street_number' => $value['street_number'],
'establishment' => $value['establishment'],
));
$index++;
}
}
#mysql_close($con);
$objWriter = PHPExcel_IOFactory::createWriter($objPHPExcel, 'Excel5');
$objWriter->save(str_replace('.php', '.xls', __FILE__));
echo date('H:i:s') . " Done writing file.\r\n";
?>

Just re-reading your code and it looks rather chaotic. I think it can be improved in many areas, however with the least changes I suggest you do the following:
Instead of first creating multiple arrays of rows you want to add, add a new row each time you have created it. For that you do not even need to name the keys. So before you iterate through the database results, first create the headers (I named it $headers):
$headers = array(
'ref', 'lat', 'long', 'route', 'locality', 'administrative_area_level_2',
'administrative_area_level_1', 'country', 'postal_code_prefix',
'postal_town', 'postal_code', 'administrative_area_level_3',
'street_number', 'establishment',
);
Also before the database iteration, create a helper-function:
$addRowCreate = function(PHPExcel_Worksheet $sheet, $col = 'A', $row = NULL) {
return function(array $data) use ($sheet, $col, &$row) {
if ($row === NULL) {
$row = $sheet->getHighestRow() + 1;
}
$sheet->fromArray(array($data), NULL, "$col$row");
$row++;
};
};
This $addRowCreate helper function will allow you to create a add-row-function later on, like in just a second. Also before the database iteration, create the excel document (memory) and set it's properties. Also add the headers in the first row:
$doc = new PHPExcel();
$doc->getProperties()->setCreator("Anon")
->setLastModifiedBy("Anon")
->setTitle("Crawler Data");
$sheet = $doc->setActiveSheetIndex(0);
$sheet->fromArray($headers);
The next step is to create the add-row-function, which is very easy thanks to the helper above:
$addRow = $addRowCreate($sheet);
You now can use one row after the other by calling it once per row array. For testing purposes, just add another row and save it to disk:
$addRow($headers);
$writer = PHPExcel_IOFactory::createWriter($doc, 'Excel5');
$writer->save(basename(__FILE__, '.php') . '.xls');
die('test finished.');
You should now have create the xls file with two rows. You can then remove the test again and inside your loops use the $addRow function:
$addRow(array(
'ref' => $value['ref'],
'lat' => $key['latitude'],
'long' => $key['longitude'],
'route' => $value['route'],
'locality' => $value['locality'],
'administrative_area_level_2' => $value['administrative_area_level_2'],
'administrative_area_level_1' => $value['administrative_area_level_1'],
'country' => $value['country'],
'postal_code_prefix' => $value['postal_code_prefix'],
'postal_town' => $value['postal_town'],
'postal_code' => $value['postal_code'],
'administrative_area_level_3' => $value['administrative_area_level_3'],
'street_number' => $value['street_number'],
'establishment' => $value['establishment'],
));
Technically you can remove the string-array-keys, however I've kept them in so that you can better find the place where you need to change your code as the array already exists there-in.
After you've put this to the work, you can safely remove all the not-any-more-needed temporary arrays and counters.
The full usage-example (test):
require_once 'Classes/PHPExcel.php'; /* PHPExcel <http://phpexcel.codeplex.com/> */
$headers = array(
'ref', 'lat', 'long', 'route', 'locality', 'administrative_area_level_2',
'administrative_area_level_1', 'country', 'postal_code_prefix',
'postal_town', 'postal_code', 'administrative_area_level_3',
'street_number', 'establishment',
);
$addRowCreate = function(PHPExcel_Worksheet $sheet, $col = 'A', $row = NULL) {
return function(array $data) use ($sheet, $col, &$row) {
if ($row === NULL) {
$row = $sheet->getHighestRow() + 1;
}
$sheet->fromArray(array($data), NULL, "$col$row");
$row++;
};
};
$doc = new PHPExcel();
$doc->getProperties()->setCreator("Anon")
->setLastModifiedBy("Anon")
->setTitle("Crawler Data");
$sheet = $doc->setActiveSheetIndex(0);
$sheet->fromArray($headers);
$addRow = $addRowCreate($sheet);
$addRow($headers);
$writer = PHPExcel_IOFactory::createWriter($doc, 'Excel5');
$writer->save(basename(__FILE__, '.php') . '.xls');
die('test finished.');
Old Answer:
However, this only puts the headings in the excel file and not the data from the array. What am i doing wrong?
You are actually only storing the headings into the file. You do not store any data.
How can I get this to work?
Bring the array in the right format and uncomment the following line in your code:
//$objPHPExcel->getActiveSheet()->fromArray($sortedData, null, 'A2');
Take care that $sortedData is the needed 2D array, see the examples in this dicsussion:
Array
(
[0] => Array
(
[0] => Relative CellA1
[1] => Relative CellB1
[2] => Relative CellC1
)
[1] => Array
(
[0] => Relative CellA2
[1] => Relative CellB2
[2] => Relative CellC2
)
)
Unless you don't get the array into that kind of 2D format, the function will not work in your favor.
Please let me know if you've got any more questions.

PHPExcel write data to the cell and you must define it position. Just like then you define headers. The principle is that you fill out the document line by line.
So I write example code to show the idea
$alphas = range('A', 'Z'); // A, B, C, D, E...
$sheet = $excel->getActiveSheet();
//headers
$sheet
->setCellValue($alphas[0].'1', 'Title1')
->setCellValue($alphas[1].'1', 'Title2')
->setCellValue($alphas[2].'1', 'Title3')
->setCellValue($alphas[3].'1', 'Title4')
;
$sheet->getColumnDimension($alphas[0])->setWidth(40);
$sheet->getColumnDimension($alphas[1])->setWidth(9);
$sheet->getColumnDimension($alphas[2])->setWidth(60);
$sheet->getColumnDimension($alphas[3])->setWidth(30);
$items = ...;// <--- your data
$row_num = 2; // start from 2 row
foreach($items as $item) {
$sheet->setCellValue($alphas[0].$row_num, $item['key1']);
$sheet->setCellValue($alphas[1].$row_num, $item['key2']);
$sheet->setCellValue($alphas[2].$row_num, $item['key3']);
$sheet->setCellValue($alphas[3].$row_num, $item['key4']);
$row_num++;
}

You can create a generic function to get excel content from any 2D arrays.
PHP array2xlsx function
/**
* This function returns xlsx content from an associative array.
*
* Warning: one cell = about 1k memory, so this function does not work
* if your array is too large.
*
* #param array $array
* #param string $title
* #param string $author
* #return string
*/
function array2xlsx(array &$array, $title = 'New Document', $author = null)
{
// Basic checks
if (count($array) == 0)
{
return null;
}
// Putting meta-data into a new excel file
$ex = new PHPExcel();
$ex->getProperties()->setLastModifiedBy($title);
$ex->getProperties()->setTitle($title);
$ex->getProperties()->setSubject($title);
$ex->getProperties()->setDescription($title);
$ex->getProperties()->setCreator($author);
// Select first page on the excel document
$ex->setActiveSheetIndex(0);
$sheet = $ex->getActiveSheet();
// Writes column titles on row 1 (assuming column names are array keys)
$column_names = array_keys(reset($array));
foreach ($column_names as $column_number => $column_name)
{
$azNumber = PHPExcel_Cell::stringFromColumnIndex($column_number);
$sheet->SetCellValue($azNumber . "1", $column_name);
}
// Writes document content
foreach ($array as $row_number => $row)
{
foreach (array_values($row) as $column_number => $cell_content)
{
// Converts column numbers to alphabetic numbering
$azNumber = PHPExcel_Cell::stringFromColumnIndex($column_number);
$sheet->SetCellValue($azNumber . ($row_number + 2), $cell_content);
}
}
// Creates file contents
$writer = new PHPExcel_Writer_Excel2007($ex);
ob_start();
$writer->save("php://output");
$content = ob_get_contents();
ob_end_clean();
return $content;
}
And send it directly to your user, by sending proper headers.
PHP download_send_header function
function download_send_headers($filename) {
header("Pragma: public");
header("Expires: 0");
header("Cache-Control: must-revalidate, post-check=0, pre-check=0");
header("Content-Type: application/force-download");
header("Content-Type: application/octet-stream");
header("Content-Type: application/download");
header("Content-Disposition: attachment;filename={$filename}");
header("Content-Transfer-Encoding: binary");
}
PHP Usage example
// We simulate your array
$array = array();
for ($i = 0; ($i < 50); $i++)
{
$array[$i] = array(
'ref' => "ref {$i}",
'lat' => "lat {$i}",
'long' => "long {$i}",
'route' => "route {$i}",
'locality' => "locality {$i}",
'administrative_area_level_2' => "administrative area level 2 {$i}",
'administrative_area_level_1' => "administrative area level 1 {$i}",
'country' => "country {$i}",
'postal_code_prefix' => "postal_code_prefix {$i}",
'postal_town' => "postal_town {$i}",
'postal_code' => "postal code {$i}",
'administrative_area_level_3' => "administrative area level 3 {$i}",
'street_number' => "street number {$i}",
'establishment' => "establishment {$i}",
);
}
// We send headers and excel content from your array
download_send_headers("my_test.xlsx");
echo array2xlsx($array);
Result

Related

Phpspreadsheet cells are not being formatted as specified

I'm trying to set a format other than "General" on cells, but they remain as "General".
This is a simplification of my code:
use PhpOffice\PhpSpreadsheet\Spreadsheet;
use PhpOffice\PhpSpreadsheet\IOFactory;
use PhpOffice\PhpSpreadsheet\Cell\DataType;
// Data sample
$data = [
['Pete', 1, 'peter#foo.com', 23, 600000000000],
['Carl', 2, 'carl#bar.com', 29, 600000000000],
];
// Format for each column
$column_types = [
'Name' => DataType::TYPE_STRING,
'Id' => DataType::TYPE_NUMERIC,
'Email' => DataType::TYPE_STRING,
'Age' => DataType::TYPE_NUMERIC,
'Commerce ID' => DataType::TYPE_NUMERIC,
];
$column_types = array_values($data);
$spreadsheet = new Spreadsheet();
$spreadsheet->setActiveSheetIndex(0);
$sheet = $spreadsheet->getActiveSheet();
foreach ($data as $row => $row_data) {
$i = 1;
$row++;
foreach ($row_data as $value) {
// VALUE IS SET, BUT NOT DATA TYPE!!
$sheet->getCellByColumnAndRow($i, $row)->setValueExplicit($value, $column_types[$i - 1]);
$i++;
}
}
$writer = IOFactory::createWriter($spreadsheet, 'Xlsx');
$writer->setPreCalculateFormulas(false);
$writer->save(PATH_TEMP . 'my_excel.xlsx');
Now when I open the resulting xlsx, all the cells will be "General", not Number, in case it was assigned DataType::TYPE_NUMERIC. And what it's worse, the last column, which is "600000000000", is converted to "6E+11", even though it's still a "General" cell.
Any ideas what should I do?
You have to set the number format of the cell style like this (simplified example):
$sheet->getCellByColumnAndRow(1, 1)
->setValueExplicit(6000000000000, DataType::TYPE_NUMERIC)
->getStyle()
->getNumberFormat()
->setFormatCode(\PhpOffice\PhpSpreadsheet\Style\NumberFormat::FORMAT_NUMBER);

PHP Excel performance is slow

I want to generate an excel sheet which contain some default fields and variable number of comment fields and data related to comment. I want to set specific width and wrap text for comment fields.Righ now I am using this code
$excelObj = new \PHPExcel();
$ews = $excelObj->getSheet(0);
$ews->setTitle('SurveyDetails');
$ews->fromArray($header, ' ', 'A1'); //Write the header from array
$ews->fromArray($content_arr, ' ', 'A2'); // Write the content from array
$header_style = array(
'font' => array('bold' => true,),
'alignment' => array('horizontal' => \PHPExcel_Style_Alignment::HORIZONTAL_CENTER, 'vertical' => \PHPExcel_Style_Alignment::VERTICAL_CENTER),
);
$content_style = array(
'alignment' => array('horizontal' => \PHPExcel_Style_Alignment::HORIZONTAL_CENTER, 'vertical' => \PHPExcel_Style_Alignment::VERTICAL_CENTER),
);
$start_end_columns = $excelObj->setActiveSheetIndex(0)->calculateWorksheetDimension();
preg_match_all('!\d+!', $start_end_columns, $matches);
$numbers = implode(':', $matches[0]);
$columns = explode(":", $numbers);
$header_end_column_no = $columns[1];
$header_start_end = str_replace($header_end_column_no, 1, $start_end_columns); // A1:G1
$ews->getStyle($header_start_end)->applyFromArray($header_style);
$start_end_columns = str_replace("A1", "A2", $start_end_columns); // Start column of content changed A1 to A2
$ews->getStyle($start_end_columns)->applyFromArray($content_style);
$cols = explode(":", $start_end_columns);
$endColmn = $cols[1];
$endColmn = preg_replace('/[0-9]+/', '', $endColmn);
$activeSheetObj = $excelObj->getActiveSheet();
//Set the autosize height for all the cells
$activeSheetObj->getDefaultRowDimension()->setRowHeight(-1);
$this->log(sprintf("Before set hyper link excel projectId : %s, surveyId : %s", $projectId, $survey_id), LogLevel::INFO);
//Set the hyperlink in the path field
$i = 2;
$count = count($content_arr);
foreach ($content_arr as $content) {
$activeSheetObj->getCell('F' . $i)->getHyperlink()->setUrl($content['path']);
$i++;
}
$activeSheetObj->getStyle('G'.'2:'.'G'.$count)->getAlignment()->setWrapText(true);
$this->log(sprintf("After setting hyper link projectId : %s, surveyId : %s", $projectId, $survey_id), LogLevel::INFO);
//Set specific width for the note and comment fields
$activeSheetObj->getColumnDimension('G')->setWidth(35);
$l = 0;
if (strcmp('G', $endColmn) != 0) {
for ($col = 'J'; $col != $endColmn; $col++) {
if ($l % 3 == 0) {
$activeSheetObj
->getColumnDimension($col)
->setWidth(35);
$activeSheetObj->getStyle($col.'2:'.$col.$count)->getAlignment()->setWrapText(true);
}
$l++;
}
$activeSheetObj->getColumnDimension($endColmn)->setWidth(35);
$activeSheetObj->getStyle($endColmn.'2:'.$endColmn.$count)->getAlignment()->setWrapText(true);
}
unset($content_arr);
$this->log(sprintf("After setting width projectId : %s, surveyId : %s", $projectId, $survey_id), LogLevel::INFO);
$writer = \PHPExcel_IOFactory::createWriter($excelObj, 'Excel2007');
//Save to perticular location
$keyname = "videos/Export/" . $projectId . "/" . $fileName;
$writer->save('/home/senchu/Documents/Infrass.xlsx');
But it takes about 3 seconds to complete the process on 10 columns and 400 rows. Is there any way to optimize this code so that to increase the performance. When I tried caching I didn't get much performance improvement.
Instead of iterating each row and setting hyper link like
$activeSheetObj->getCell('F' . $i)->getHyperlink()->setUrl($content['path']);
is there any method to set hyper link from array.so that we can avoid this much number of iterations.

Filling Excel sheet using PHPExcel

I am Trying to fill my Excel sheet with the data i filtered through the methods i have made. For now i am getting a sheet but i only have only one row filled not the other it's not getting the data i provide it though my object
I am trying my sheet something similar to this sheet .
i am trying to write code in this part of code :
public function export($Sets,$disp_filter)
{
$objPHPExcel = new PHPExcel();
$objPHPExcel->getProperties()->setTitle("Offic excel Test Document");
$styleArray = array(
'font' => array(
'bold' => true,
'color' => array('rgb' => 'FF0000'),
'size' => 10,
'name' => 'Verdana'
));
$objPHPExcel->getActiveSheet()->getStyle('A1')->applyFromArray($styleArray);
$excel_out = array($this->outputSampleName($Sets));
// var_dump($excel_out);
// exit;
$objPHPExcel->getActiveSheet()->SetCellValue('A1', 'Sample Size and Margin of Error');
$rowCount = 2;
foreach ($excel_out as $key=> $line)
{
$colCount = 'A';
$i=0;
// $line = array($Set['name']);
// $CT = $Set['crossTabs']['base'];
// $Moe = array($CT['sample']['moe']);
foreach($line as $col_value)
{
// var_dump($col_value);
// exit;
$objPHPExcel->getActiveSheet()->setCellValue($colCount.$rowCount, $col_value[$i])
->getStyle($colCount.$rowCount)->applyFromArray($styleArray);
$colCount++;
}
$rowCount++;
$i++;
}
return $objPHPExcel;
}
protected function outputSampleName($Sets)
{
foreach ($Sets as $Set)
{
$CT = $Set['crossTabs']['base'];
$line = array(
$Set['name'],
$CT['sample']['moe'] . '%'
);
$excel_out []= $line;
}
return $excel_out;
}
when i see by var_dump($excel_out)
i have this data structure :
**Please suggest me something how can i get those percentage values in my next row in optimized way.
for now i can only loop through the sample[name] which are (enthusiasts, hunter, new shooters etc. )from that array. **
thanks in advance

PHPExcel output numbers are wrong

I have this code:
$query = "SELECT ciudadh,corporacionh,r1,proxima,ultima FROM usuariox";
$headings = array('#', 'Estas son sus fichas hasta la fecha','fecha de ingreso');
if ($result = mysql_query($query) or die(mysql_error())) {
// Create a new PHPExcel object
$objPHPExcel = new PHPExcel();
$objPHPExcel->getActiveSheet()->setTitle('Asuntos Pendientes');
$rowNumber = 2;
$rowNumber2 = 2;
$col = 'A';
foreach($headings as $heading) {
$objPHPExcel->getActiveSheet()->setCellValue($col.$rowNumber,$heading);
$col++;
}
// Loop through the result set
$rowNumber = 3;
$newId = 1;
while ($row = mysql_fetch_row($result)) {
$col = 'B';
$objPHPExcel->getActiveSheet()->setCellValue("A$rowNumber", $newId++);
foreach($row as $cell) {
$objPHPExcel->getActiveSheet()->setCellValue($col.$rowNumber,$cell);
$col++;
}
$rowNumber++;
$rowNumber2++;
}
$styleArray = array(
'borders' => array(
'allborders' => array(
'style' => PHPExcel_Style_Border::BORDER_THIN,
'color' => array('argb' => 'FFB0c4dE'),
),
),
);
$styleArray2 = array(
'fill' => array(
'type' => PHPExcel_Style_Fill::FILL_SOLID,
'color' => array('argb' => 'FFB0c4dE'),
),
);
$objPHPExcel->getActiveSheet()->getStyle('A2:F2')->applyFromArray($styleArray);
$objPHPExcel->getActiveSheet()->getStyle('A1:F1')->applyFromArray($styleArray2);
$objPHPExcel->getActiveSheet()->getSheetView()->setZoomScale(80);
$objDrawing = new PHPExcel_Worksheet_Drawing();
$objDrawing->setName('Logo');
$objDrawing->setDescription('Logo');
$objDrawing->setPath('./images/headerexcel2.png');
$objDrawing->setWorksheet($objPHPExcel->getActiveSheet());
$objDrawing->setCoordinates('A1');
$objDrawing->setOffsetX(30);
// Freeze pane so that the heading line won't scroll
$objPHPExcel->getActiveSheet()->getColumnDimension('A')->setWidth(5);
$objPHPExcel->getActiveSheet()->getColumnDimension('B')->setWidth(50);
$objPHPExcel->getActiveSheet()->getDefaultRowDimension()->setRowHeight(30);
$objPHPExcel->getActiveSheet()->getRowDimension('1')->setRowHeight(50);
$objPHPExcel->getActiveSheet()->getRowDimension('2')->setRowHeight(15);
$objPHPExcel->getActiveSheet()->getHeaderFooter()->setOddHeader('&C&16');
$objPHPExcel->getDefaultStyle()->getFont()->setName('Arial');
$objPHPExcel->getDefaultStyle()->getFont()->setSize(14);
$objPHPExcel->getActiveSheet()->freezePane('A2');
// Save as an Excel BIFF (xls) file
$objWriter = PHPExcel_IOFactory::createWriter($objPHPExcel, 'Excel5');
header('Content-Type: application/vnd.ms-excel');
header('Content-Disposition: attachment;filename="asuntos-pendientes.xls"');
header('Cache-Control: max-age=0');
$objWriter->save('php://output');
exit();
}
echo 'a problem has occurred... no data retrieved from the database';
the code works but "r1" field (mysql) have numbers like this:
05001400300120110010000
but if a look the excel file instead the number Im getting this :
Write values like 05001400300120110010000 using setCellValueExplicit() which will (by default) treat it as a string value, and hence store the value with the leading zero and (because it is far larger than an Excel or a PHP integer value) it won't be cast to float and displayed in scientific format
Excel can't represent numbers this long if the cell type is set to General, it not a problem of PHPExcel. You have to set the cell type to Number.
You can try:
$PHPExcelObject->getActiveSheet()->getStyle($cell)->getNumberFormat()->setFormatCode('0');

PHP Excel export not recognised by office 2007

I have been using stack overflow for a good couple of years but only now made an account because I have never become so stuck that I needed to ask a question (not because I'm smart, because my code is simple!), anyway on to my question;
I am exporting a table in .xls format via PHP with information from a few tables in my MYSQL table. all the information and styling works perfectly. The only problem is that when it opens in office 2007 i get this error message:
"the file you are trying to open, 'export.xls', is a different format than specified by the file extension. Verify that the file is not corrupted and is from a trusted source before opening the file. Are you sure you want to view this file?"
So to sum up, all information is pulled from DB successful and all the styling works - I know this to be true because when I click 'yes' on the dialog box that pops up I see everything laid-out perfectly.
Below is the Excel exporter class:
/**
* Class for generating xml with multiple spreadsheets
* #author Marin Crnković
* #version 0.9
* #update_date 21.01.2009
*/
class excel_xml {
var $xml_data;
var $nl;
var $tab;
var $cols;
var $rows;
var $worksheets;
var $counters;
var $xml;
/**
* Constructor
*/
function excel_xml(){
$this->column_width = 150;
$this->debug = false;
$this->cols = array();
$this->row_array = array();
$this->rows = array();
$this->worksheets = array();
$this->counters = array();
$this->nl = "\n";
$this->tab = "\t";
}
/**
* Set debug
*/
function debug() {
$this->debug = true;
}
/**
* Generate xml
* #returns string
*/
function generate() {
// Create header
$xml = $this->create_header().$this->nl;
// Put all worksheets
$xml .= join('', $this->worksheets).$this->nl;
// Finish with a footer
$xml .= $this->create_footer();
$this->xml = $xml;
return $this->xml;
}
/**
* Create worksheet
* Uppon creating a worksheet, delete counters
* #param string $worksheet_name: name of the worksheet
*/
function create_worksheet($worksheet_name) {
$worksheet = '<Worksheet ss:Name="'.$worksheet_name.'">';
$worksheet .= $this->create_table();
$worksheet .= '<WorksheetOptions xmlns="urn:schemas-microsoft-com:office:excel">
<ProtectObjects>False</ProtectObjects>
<ProtectScenarios>False</ProtectScenarios>
</WorksheetOptions>
</Worksheet>';
// Unset the counters and rows so you can generate another worksheet table
$this->counters = array();
$this->row_array = array();
$this->rows = '';
// Add generated worksheet to the worksheets array
$this->worksheets[] = $worksheet;
}
/**
* Create table
* #returns string
*/
function create_table() {
// Create rows with the method that automaticaly sets counters for number of columns and rows
$rows = $this->create_rows();
// Table header
$table = '<Table ss:ExpandedColumnCount="'.$this->counters['cols'].'" ss:ExpandedRowCount="'.$this->counters['rows'].'" x:FullColumns="1" x:FullRows="1">'.$this->nl;
// Columns data (width mainly)
for($i = 1; $i <= $this->counters['cols']; $i++) {
$table .= '<Column ss:Index="'.$i.'" ss:Width="'.$this->column_width.'" />'.$this->nl;
}
// Insert all rows
$table .= join('', $rows);
// End table
$table .= '</Table>'.$this->nl;
return $table;
}
/**
* Add another row into the array
* #param mixed $array: array with row cells
* #param mixed $style: default null, if set, adds style to the array
*/
function add_row($array, $style = null) {
if(!is_array($array)) {
// Asume the delimiter is , or ;
$array = str_replace(',', ';', $array);
$array = explode(';', $array);
}
if(!is_null($style)) {
$style_array = array('attach_style' => $style);
$array = array_merge($array, $style_array);
}
$this->row_array[] = $array;
}
/**
* Create rows
* #returns array
*/
function create_rows() {
$row_array = $this->row_array;
if(!is_array($row_array)) return;
$cnt = 0;
$row_cell = array();
foreach($row_array as $row_data) {
$cnt++;
// See if there are styles attached
$style = null;
if($row_data['attach_style']) {
$style = $row_data['attach_style'];
unset($row_data['attach_style']);
}
// Store the counter of rows
$this->counters['rows'] = $cnt;
$cells = '';
$cell_cnt = 0;
foreach($row_data as $key => $cell_data) {
$cell_cnt++;
$cells .= $this->nl.$this->prepare_cell($cell_data, $style);
}
// Store the number of cells in row
$row_cell[$cnt][] = $cell_cnt;
$this->rows[] = '<Row>'.$cells.$this->nl.'</Row>'.$this->nl;
}
// Find out max cells in all rows
$max_cells = max($row_cell);
$this->counters['cols'] = $max_cells[0];
return $this->rows;
}
/**
* Prepare cell
* #param string $cell_data: string for a row cell
* #returns string
*/
function prepare_cell($cell_data, $style = null) {
$str = str_replace("\t", " ", $cell_data); // replace tabs with spaces
$str = str_replace("\r\n", "\n", $str); // replace windows-like new-lines with unix-like
$str = str_replace('"', '""', $str); // escape quotes so we support multiline cells now
preg_match('#\"\"#', $str) ? $str = '"'.$str.'"' : $str; // If there are double doublequotes, encapsulate str in doublequotes
// Formating: bold
if(!is_null($style)) {
$style = ' ss:StyleID="'.$style.'"';
} elseif (preg_match('/^\*([^\*]+)\*$/', $str, $out)) {
$style = ' ss:StyleID="bold"';
$str = $out[1];
}
if (preg_match('/\|([\d]+)$/', $str, $out)) {
$merge = ' ss:MergeAcross="'.$out[1].'"';
$str = str_replace($out[0], '', $str);
}
// Get type
$type = preg_match('/^([\d]+)$/', $str) ? 'Number' : 'String';
return '<Cell'.$style.$merge.'><Data ss:Type="'.$type.'">'.$str.'</Data></Cell>';
}
/**
* Create header
* #returns string
*/
function create_header() {
if (is_array($this->styles)) {
$styles = join('', $this->styles);
}
$header = <<<EOF
<?xml version="1.0"?>
<?mso-application progid="Excel.Sheet"?>
<Workbook xmlns="urn:schemas-microsoft-com:office:spreadsheet"
xmlns:o="urn:schemas-microsoft-com:office:office"
xmlns:x="urn:schemas-microsoft-com:office:excel"
xmlns:ss="urn:schemas-microsoft-com:office:spreadsheet"
xmlns:html="http://www.w3.org/TR/REC-html40">
<OfficeDocumentSettings xmlns="urn:schemas-microsoft-com:office:office">
<DownloadComponents/>
<LocationOfComponents HRef="file:///\\"/>
</OfficeDocumentSettings>
<ExcelWorkbook xmlns="urn:schemas-microsoft-com:office:excel">
<WindowHeight>12525</WindowHeight>
<WindowWidth>15195</WindowWidth>
<WindowTopX>480</WindowTopX>
<WindowTopY>120</WindowTopY>
<ActiveSheet>0</ActiveSheet>
<ProtectStructure>False</ProtectStructure>
<ProtectWindows>False</ProtectWindows>
</ExcelWorkbook>
<Styles>
<Style ss:ID="Default" ss:Name="Normal">
<Alignment ss:Vertical="Bottom"/>
<Borders/>
<Font/>
<Interior/>
<NumberFormat/>
<Protection/>
</Style>
<Style ss:ID="bold">
<Font ss:Bold="1" />
</Style>
$styles
</Styles>
EOF;
return $header;
}
/**
* Add style to the header
* #param string $style_id: id of the style the cells will reference to
* #param array $parameters: array with parameters
*/
function add_style($style_id, $parameters) {
foreach($parameters as $param => $data) {
switch($param) {
case 'size':
$font['ss:Size'] = $data;
break;
case 'font':
$font['ss:FontName'] = $data;
break;
case 'color':
case 'colour':
$font['ss:Color'] = $data;
break;
case 'bgcolor':
$interior['ss:Color'] = $data;
break;
case 'bold':
$font['ss:Bold'] = $data;
break;
case 'italic':
$font['ss:Italic'] = $data;
break;
case 'strike':
$font['ss:StrikeThrough'] = $data;
break;
}
}
if(is_array($interior)) {
foreach($interior as $param => $value) {
$interiors .= ' '.$param.'="'.$value.'"';
}
$interior = '<Interior ss:Pattern="Solid"'.$interiors.' />'.$this->nl;
}
if(is_array($font)) {
foreach($font as $param => $value) {
$fonts .= ' '.$param.'="'.$value.'"';
}
$font = '<Font'.$fonts.' />'.$this->nl;
}
$this->styles[] = '
<Style ss:ID="'.$style_id.'">
'.$interior.$font.'
</Style>';
}
/**
* Create footer
* #returns string
*/
function create_footer() {
return '</Workbook>';
}
/**
* Output as download
*/
function download($filename) {
if(!strlen($this->xml)) $this->generate();
header("Cache-Control: public, must-revalidate");
header("Pragma: no-cache");
header("Content-Length: " .strlen($this->xml) );
header("Content-Type: application/vnd.ms-excel");
if(!$this->debug){
header('Content-Disposition: attachment; filename="'.$filename.'"');
header("Content-Transfer-Encoding: binary");
} else {
header("Content-Type: text/plain");
}
print $this->xml;
exit;
}
}
And this is my implementation with sensitive information censored;
$excel = new excel_xml();
$header_style = array(
'bold' => 1,
'size' => '14',
'color' => '#FFFFFF',
'bgcolor' => '#4F81BD'
);
$excel->add_style('header', $header_style);
$header_style2 = array(
'bold' => 1,
'color' => '#FFFFFF',
'bgcolor' => '#92d050'
);
$excel->add_style('green', $header_style2);
$header_style3 = array(
'bold' => 1,
'color' => '#FFFFFF',
'bgcolor' => '#c00000'
);
$excel->add_style('error', $header_style3);
$header_style4 = array(
'bold' => 1,
'color' => '#FFFFFF',
'bgcolor' => '#e46d0a'
);
$excel->add_style('orange', $header_style4);
$header_style5 = array(
'bold' => 1,
'color' => '#FFFFFF',
'bgcolor' => '#c00000'
);
$excel->add_style('red', $header_style5);
/**
* Add row and attach the style "header" to it
*/
$excel->add_row(array(
'col1',
'col2',
'col3',
'col4',
'col5'
), 'header');
/**
* Add some rows, if you encapsulate the string inside asterisks,
* they will get bold using the predefined style "bold"
* If you append "|x" where x is a number, that cell will be
* merged with the x following cells
*/
$excel->add_row(array(
$Queried_Info_From_DB1,
$Queried_Info_From_DB2,
$Queried_Info_From_DB3,
$Queried_Info_From_DB4,
$Queried_Info_From_DB5
), 'red');
if(mysql_num_rows($result) == 0){
$excel->add_row(array(
'You have no info to display!|4'
), 'error');
}
/**
* Tell the object to create the worksheet.
* The passed string is the name of the worksheet
*/
$excel->create_worksheet('Your info');
/**
* If you invoke the generate method, you will get the
* XML returned or...
*/
$xml = $excel->generate();
/**
* ... you can pass the whole thing for download with
* the passed string as the filename
*/
$excel->download('Export');
You're writing a file that's spreadsheetML format, not BIFF (.xls) format, so MS Excel will complain at this discrepancy. Try saving it with a file extension of .xml (because that's what you're actually creating)

Categories