PHP使用GD庫繪製表格(可根據數據自適應)

ps:真是代碼寫的久了什麼需求都會遇得上,木得辦法
需求是需要用圖片表格的樣式展示數據,先看效果圖:
在這裏插入圖片描述
就是一個表格,但是需要用圖片的方式進行展示,再次感嘆PHP的GD庫真是異常強大!!!
先說完成的功能,按照下面的數據列子可以很方便的組織出這類表格,自定義表頭信息以及根據數據需求自定義每一列的寬度和高度,代碼會自動讓數據居中顯示。

代碼

	/**
     * 生成表格
     */
    function create_table($params)
    {
        $base = [
            'border' => 10,//圖片外邊框
            'file_path' => $params['file_path'],//圖片保存路徑
            'title_height' => 25,//報表名稱高度
            'title_font_size' => 16,//報表名稱字體大小
            'font_ulr' => './MSYHMONO.ttf',//字體文件路徑
            'text_size' => 12,//正文字體大小
            'row_hight' => 30,//每行數據行高
        ];
    	
    	$save_path = $base['file_path'] . $params['file_name'];

    	//如果表說明部分不爲空,則增加表圖片的高度
        if(!empty($params['table_explain'])){
            $base['title_height'] =   $base['title_height'] * count($params['table_explain']);
        }
        
        //計算圖片總寬
        $w_sum = $base['border'];
        foreach ($params['field_width'] as $key => $value) {
        	//圖片總寬
            $w_sum += $value;
            //計算每一列的位置
            $base['column_x_arr'][$key] = $w_sum;
        }

        $base['img_width'] = $w_sum + $base['border'] * 2-$base['border'];//圖片寬度
        $base['img_height'] = ($params['row']+1) * $base['row_hight'] + $base['border'] * 2 + $base['title_height'];//圖片高度
        $border_top = $base['border'] + $base['title_height'];//表格頂部高度
        $border_bottom = $base['img_height'] - $base['border'];//表格底部高度

        $img = imagecreatetruecolor($base['img_width'], $base['img_height']);//創建指定尺寸圖片
        $bg_color = imagecolorallocate($img, 255,255,255);//設定圖片背景色
        $text_coler = imagecolorallocate($img, 0, 0, 0);//設定文字顏色
        $border_coler = imagecolorallocate($img, 0, 0, 0);//設定邊框顏色


        imagefill($img, 0, 0, $bg_color);//填充圖片背景色

        //先填充一個黑色的大塊背景
        imagefilledrectangle($img, $base['border'], $base['border'] + $base['title_height'], $base['img_width'] - $base['border'], $base['img_height'] - $base['border'], $border_coler);//畫矩形

        //再填充一個小兩個像素的 背景色區域,形成一個兩個像素的外邊框
        imagefilledrectangle($img, $base['border'] + 2, $base['border'] + $base['title_height'] + 2, $base['img_width'] - $base['border'] - 2, $base['img_height'] - $base['border'] - 2, $bg_color);//畫矩形
        //畫表格縱線 及 寫入表頭文字

        $sum = $base['border'];
        foreach($base['column_x_arr'] as $key => $x){

            imageline($img, $x, $border_top, $x, $border_bottom,$border_coler);//畫縱線
            
            $this_title_box = imagettfbbox($base['text_size'], 0, $base['font_ulr'], $params['table_header'][$key]);
            $title_x_len = $this_title_box[2] - $this_title_box[0];
            imagettftext($img, $base['text_size'], 0, $sum + (($x-$sum)/2 - $title_x_len/2), $border_top + ($base['row_hight']+$base['text_size'])/2, $text_coler, $base['font_ulr'], $params['table_header'][$key]);//寫入表頭文字
            $sum += $params['field_width'][$key];
        }

        //畫表格橫線
        foreach($params['data'] as $key => $item){
            $border_top += $base['row_hight'];
            //畫橫線
            imageline($img, $base['border'], $border_top, $base['img_width'] - $base['border'], $border_top, $border_coler);

            $this_first = imagettfbbox($base['text_size'], 0, $base['font_ulr'], $key);
            $first_len = $this_first[2] - $this_first[0];
           
            imagettftext($img, $base['text_size'], 0, $params['field_width'][0]/2 - $first_len/2+$base['border'], $border_top + ($base['row_hight']+$base['text_size'])/2, $text_coler, $base['font_ulr'], $key);//寫入序號
            $sub = 0;
            $sum = $params['field_width'][0]+$base['border'];
            foreach ($item as $value){
                $sub++;
                $this_title_box = imagettfbbox($base['text_size'], 0, $base['font_ulr'], $value);
                $title_x_len = $this_title_box[2] - $this_title_box[0];
                imagettftext($img, $base['text_size'], 0, $sum + (($base['column_x_arr'][$sub]-$sum)/2 - $title_x_len/2), $border_top + ($base['row_hight']+$base['text_size'])/2, $text_coler, $base['font_ulr'], $value);//寫入data數據
                $sum += $params['field_width'][$sub];
            }
        }
 
        //計算標題寫入起始位置
        $title_fout_box = imagettfbbox($base['title_font_size'], 0, $base['font_ulr'], $params['title']);//imagettfbbox() 返回一個含有 8 個單元的數組表示了文本外框的四個角:
        $title_fout_width = $title_fout_box[2] - $title_fout_box[0];//右下角 X 位置 - 左下角 X 位置 爲文字寬度
        $title_fout_height = $title_fout_box[1] - $title_fout_box[7];//左下角 Y 位置- 左上角 Y 位置 爲文字高度
        
       
 
        $save_path = $base['file_path'] . $params['file_name'];
        if(!is_dir($base['file_path']))//判斷存儲路徑是否存在,不存在則創建
        {
            mkdir($base['file_path'],0777,true);
        }


        //居中寫入標題
        imagettftext($img, $base['title_font_size'], 0, ($base['img_width'] - $title_fout_width)/2, 30, $text_coler, $base['font_ulr'], $params['title']);
        //設置圖片左上角信息
        $a_hight = 20;
        if(!empty($params['table_explain'])){
            foreach ($params['table_explain'] as $key => $value) {
                imagettftext($img, $base['text_size'], 0, 10, 20+$a_hight, $text_coler, $base['font_ulr'], $value);
                $a_hight += 20;
            }
        }
        imagepng($img,$save_path);//輸出圖片,輸出png使用imagepng方法,輸出gif使用imagegif方法
        echo '<img src="/'.$save_path.'"/>';
    }

這是生成圖片的方法,如果沒有特殊需求完全不需要動這個方法裏的代碼,按照下面的示例傳值即可。

示例:

//表格數據
	$data = [
		[
            'name' => '張三',
            'sexdesc' => '女',
            'type1' => '說明',
            'type2' => '2020-05-25 10:00~11:30',
            'type3' => '2020-05-25',
            'type4' => '2020-05-25',
            'type5' => '2020-05-25',
            'type6' => '2020-05-25',

	   	],

	];
	//循環制造數據
	for ($i=0; $i < 10; $i++) { 
		$data[] = [
            'name' => '張三',
            'sexdesc' => '女',
            'type1' => '說明',
            'type2' => '2020-05-25 10:00~11:30',
            'type3' => '2020-05-25',
            'type4' => '2020-05-25',
            'type5' => '2020-05-25',
            'type6' => '2020-05-25',

	   	];
	}
	//圖片左上角彙總說明數據,可爲空
	$table_explain = [
		0 => '[性別]:女100 男50 不詳2',
	    1 => '[類型]:說明8 說明16 ',
	    2 => '[類型]:說明8 說明16 ',
	];
	//表頭信息
	$table_header = [
        0   =>  '序號',
        1   =>  '表頭1',
        2   =>  '表頭2',
        3   =>  '表頭3',
        4   =>  '表頭4',
        5   =>  '表頭5',
        6   =>  '表頭6',
        7   =>  '表頭7',
        8   =>  '表頭8'

    ];
    //每個格子的寬度,可根據數據長度自定義
    $field_width = [
        0   =>  '60',
        1   =>  '80',
        2   =>  '60',
        3   =>  '80',
        4   =>  '220',
        5   =>  '300',
        6   =>  '300',
        7   =>  '100',
        8   =>  '120'
    ];
    //參數
    $params = [
        'row' => count($data),          //數據的行數
        'file_name' => '數據_'.date("Ymd" , strtotime("+1 day")).'.png',      //保存的文件名
        'title' => date("Y-m-d")." 數據說明",
        'table_time' => date("Y-m-d H:i:s"),
        'data' => $data,
        'table_explain'	=> $table_explain,
        'table_header'	=> $table_header,
        'field_width'	=> $field_width,
        'file_path' =>  "./public/".date("Y-m-d")."/"  //文件保存路徑
    ];
	//調用方法
	create_table($params);
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章