PHP核心编程-图像操作
一 图像操作环境:
1. 开启GD2图像处理并检测
在php.ini开启GD库
2. 画布坐标系说明
二. 图像基本操作(步骤)
1. 创建图像
创建画布(图像资源)
创建的方法:
方法一: 创建真彩色图像
方法二: 基于现有图像创建
2. 绘制图像
如:将字符或汉字写入图像,缩略图,水印图像…..
3. 输出图像
生成的图像在哪个地方显示.
两个地方
1.通过浏览器来显示
Header(‘content-type:image/jpeg’); //设置让浏览器显示图像
Imagejpeg(图像资源); //将图像资源输出
2.图像以文件的形式在操作系统中显示.
Imagejpeg(图像资源,’文件名.jpg’);
如: Imagejpeg(图像资源,’1.jpg’)
4. 销毁图像
将图像资源销毁,目的释放内存.
Imagedestroy(图像资源); //当前页面有多少图像资源就销毁多少.
方法一:创建图片资源生成验证码:
<?php
// 第一步:创建图像资源 // 方法一:创建真彩色图像
// imagecreatetruecolor(width, height); 单位是像素
$image = imagecreatetruecolor(100, 30);
// 分配颜色
// imagecolorallocate(图像资源, red, green, blue);RGB,取值0~255
$bgcolor = imagecolorallocate($image,mt_rand(0,255),mt_rand(0,255),mt_rand(0,255));
// imagesx($image); //获取画布的宽度
// imagesy($image); //获取画布的高度 // 填充背景
// imagefill(图像资源,x,y,用什么颜色填充背景); x,y是填充的坐标
imagefill($image,0,0,$bgcolor);
// 第二步:图像绘制
/*
绘制图像(建议)的操作方法
1.首先将核心的函数(形参)写出来,然后在个形参前加$符号
2.在调用函数之前,对个形参从左到右一个一个进行设置
*/ // 在图片中写入字符串
// font 字符串的大小 , x,y 写入时的坐标 string 写入的字符串 color 文字颜色
$font = 5; //1~5 // 验证码开始
$str = 'qwertyuiopasdfghjklzxcvbnmQWERTYUIOPASDFGHJKLZXCVBNM1234567890';
$string = substr(str_shuffle($str),0,5); //打乱字符 截取5个字符
// 验证码结束 // $string = 'helloworld'; //注意:不支持汉字
/*
字符水平坐标
字符水平坐标 = (画布宽度-所有字符的宽度和)/2
字符水平坐标 = (300-所有字符的宽度和)/2
字符水平坐标 = (300-一个字符宽度 * 字符个数)/2
字符水平坐标 = (300-imagefontwidth($font) * 字符个数)/2
字符水平坐标 = (300-imagefontwidth($font) * strlen($string))/2
*/
$x = ( imagesx($image)-imagefontwidth($font) * strlen($string))/2;
/*字符的垂直方向
(画布的高度 - 一个字符的高度)/2
(200-一个字符的高度)/2 */
$y = ( imagesy($image)-imagefontheight($font))/2;
$color = imagecolorallocate($image,mt_rand(0,255),mt_rand(0,255),mt_rand(0,255));
imagestring($image, $font, $x, $y, $string, $color);
// mt_rand(min,max); 产生随机数
// 加入干扰线
for ($i=0; $i <15 ; $i++) {
$linecolor = imagecolorallocate($image,mt_rand(0,255),mt_rand(0,255),mt_rand(0,255));
imageline($image,mt_rand(0,100),mt_rand(0,100),mt_rand(0,100),mt_rand(0,50),$linecolor);
}
// 加入干扰像素点 for ($i=0; $i <100 ; $i++) {
$pixcolor = imagecolorallocate($image,mt_rand(0,255),mt_rand(0,255),mt_rand(0,255));
imagesetpixel($image, mt_rand(0,50), mt_rand(0,50), $pixcolor);
} /*// 画圆,弧
$cx = 100;
$cy = 100; $width = 150;
$height = 150; $start = 0;
$end = 360;
$color = imagecolorallocate($image,0,255,255);
// cx,cy 圆形的坐标, width,height 长轴,短轴 start,end 弧的开始和结束的角度,默认开始的是3点钟方向,顺序是顺时针 color线的颜色
imagearc($image, $cx, $cy,$width, $height, $start, $end, $color);*/ /*//画矩形
// x1,y1 左上角坐标 X2,y2 右下角坐标
// imagerectangle(image, x1, y1, x2, y2, color);
$x1 = 20;
$y1 = 20; $x2 = 150;
$y2 = 150;
$color = imagecolorallocate($image,0,0,255);
imagerectangle($image, $x1, $y1, $x2, $y2, $color);*/ /*// 画一条直线
$x1 = 0;
$y1 = 0; $x2 = 100;
$y2 = 100;
$color = imagecolorallocate($image,0,255,0); //红线 // 调用函数
// imageline(图像资源,x1,y1,x2,y2,线的颜色);
imageline($image,$x1,$y1,$x2,$y2,$color);
*/ // 方法二:基于现有的图像 // 第三步:输出图像
// 1.通过浏览器来显示
// header('content-type:image/jpeg');
header('content-type:image/png');
// imagejpeg(图像资源);
imagejpeg($image); // 2.生成单独文件
// imagejpeg($image,'1.jpg');
// 第四步:销毁图像
// imagedestroy(图像资源);
imagedestroy($image);
方法二: 基于现有的图像生成的验证码:
<?php
// 第一步:创建图像资源 // 方法二:基于现有的图像
$filename = './sucai/code.png';
$image = imagecreatefrompng($filename); // 第二步:图像绘制
// 将TTF文字字符写入图像
// size 字符大小 angle旋转的角度 x,y写入的坐标 color字符颜色 fontfile字体路径 text准备写入的字符
$size = 20;
$angle = 0;
$x = 12;
$y = 25;
$color = imagecolorallocate($image,mt_rand(0,255),mt_rand(0,255),mt_rand(0,255));
$fontfile = './sucai/Candarai.ttf';
// 验证码开始
$str = 'qwertyuiopasdfghjklzxcvbnmQWERTYUIOPASDFGHJKLZXCVBNM1234567890';
$text = substr(str_shuffle($str),0,5); //打乱字符 截取5个字符
// 验证码结束
// $text = '中国江南皮鞋厂专属水印';
imagettftext($image, $size, $angle, $x, $y, $color, $fontfile, $text); // 第三步:输出图像
// 1.通过浏览器来显示
// header('content-type:image/jpeg');
header('content-type:image/png');
// imagejpeg(图像资源);
imagejpeg($image); // 2.生成单独文件
// imagejpeg($image,'1.jpg');
// 第四步:销毁图像
// imagedestroy(图像资源);
imagedestroy($image);
五.创建方法:
注意:
1. 方法一: 创建一个真彩色图像
创建一个真彩色图像 (空画布)
为真彩色图像: 分配颜色
为真彩色图像: 填充颜色
注意:
(1) 实例:输出字符串图像,让文本居于图像的正中
(2)实例:随机验证码,随机验证码居中
(3) 实例:加入干扰元素,点与线
2. 方法二: 创建图像(基于现有图像)
Imagecreatefromjpeg(图像路径);
Imagecreatefrompng(图像路径);
Imagecreatefromgif(图像路径);
通过: getimagesize()获取图像信息:
取得图像的宽度和高度
取得字体的宽度和高度
(1) 在图像上写入TTF字体的文本(支持汉字)
imagettftext(image, size, angle, x, y, color, fontfile, text);
1.size //字符大小,没有限制
2.angle //旋转的角度
3.x,y 写入坐标
4.color //字符颜色
5.fontfile //字体的路径
6.text //准备写入的字符
2) 实例:TTF字体的文本
(2) 实例:基于现有图像生成TTF验证码
(3)实例:将验证码植入到表单中
验证码code.php
<?php
session_start();
// 第一步:创建图像资源 // 方法二:基于现有的图像
$filename = './sucai/code.png';
$image = imagecreatefrompng($filename); // 第二步:图像绘制
// 将TTF文字字符写入图像
// size 字符大小 angle旋转的角度 x,y写入的坐标 color字符颜色 fontfile字体路径 text准备写入的字符
$size = 20;
$angle = 0;
$x = 12;
$y = 25;
$color = imagecolorallocate($image,mt_rand(0,255),mt_rand(0,255),mt_rand(0,255));
$fontfile = './sucai/Candarai.ttf';
// 验证码开始
$str = 'qwertyuiopasdfghjklzxcvbnmQWERTYUIOPASDFGHJKLZXCVBNM1234567890';
$text = substr(str_shuffle($str),0,5); //打乱字符 截取5个字符 // 将验证码写入session
$_SESSION['checkcode'] = $text; // 验证码结束
// $text = '中国江南皮鞋厂专属水印';
imagettftext($image, $size, $angle, $x, $y, $color, $fontfile, $text);
// 第三步:输出图像
// 1.通过浏览器来显示
// header('content-type:image/jpeg');
header('content-type:image/png');
// imagejpeg(图像资源);
imagejpeg($image); // 2.生成单独文件
// imagejpeg($image,'1.jpg');
// 第四步:销毁图像
// imagedestroy(图像资源);
imagedestroy($image);
(4)通过session对验证码,进行验证
(5)实例:制作图像文字水印效果
(6)实例:上传图片并加入水印文字
1.上传页面: index.php
2.处理页面:upload.php
续上面的代码
(7)实例:生成缩略图
imagecopyresampled(dst_image, src_image, dst_x, dst_y, src_x, src_y, dst_w, dst_h, src_w, src_h)
输出目标图像:缩略图
说明:
Dst_image //目标图像资源
Src_image//源图像资源
Dst_x,dst_y //目标图像取样坐标
Src_x,src_y //源图像的取样坐标
//以上四个坐标都使用0. 等比缩小.
Dst_w,dst_h //目标图像的宽和高
Src_w,src_h //源图像的宽和高
<?php
// 第一步:创建图像资源 // 方法二:基于现有的图像
$src_file = './sucai/1.jpg';
$src_image = imagecreatefromjpeg($filename); //imagesx($src_image); //获取画布宽度
//imagesy($src_image); //获取画布高度 // getimagesize($src_image);
// list 可以取得数组对应下标的值
list($src_w,$src_h)= getimagesize($src_file);
$per = 0.5;
// 目标宽高
$dst_w = $per * $src_w;
$dst_h = $per * $src_h; $dst_image = imagecreatetruecolor($dst_w,$dst_h);
// 第二步:图像绘制
//缩略图,将大图等比缩小图
imagecopyresampled($dst_image, $src_image, 0, 0, 0, 0, $dst_w, $dst_h, $src_w, $src_h) ;
// imagecopyresized(dst_image, src_image, dst_x, dst_y, src_x, src_y, dst_w, dst_h, src_w, src_h); // 第三步:输出图像
// 1.通过浏览器来显示
// header('content-type:image/jpeg');
header('content-type:image/jpeg');
// imagejpeg(图像资源);
imagejpeg($dst_image); // 2.生成单独文件
// imagejpeg($image,'1.jpg');
// 第四步:销毁图像
// imagedestroy(图像资源);
imagedestroy($dst_image);
imagedestroy($src_image);
(8)实例:制作图像图片水印效果
imagecopymerge(dst_im, src_im, dst_x, dst_y, src_x, src_y, src_w, src_h, pct)
输出目标图像,源图像一般设置为logo小图.
说明:
dst_im //大图资源
Src_im //小图资源logo
src_x,src_y //小图的左角坐标
dst_x ,dst_y //小图左上角这个点在大图中的坐标
src_w,src_h //小图的宽与高
pct //小图的透明度0-100
<?php
//第一步: 创建图像
//方法二: 基于现有的图像
$dst_file = './sucai/1.jpg'; //大图
$src_file = './sucai/logo.gif'; //小图 //目标资源,大图
$dst_im = imagecreatefromjpeg($dst_file);
//源资源logo
$src_im = imagecreatefromgif($src_file); //获取源logo的宽与高
list($src_w, $src_h ) = getimagesize($src_file);
list($dst_w, $dst_h ) = getimagesize($dst_file); // imagesx($src_image); //获取画布的宽度
// imagesy($src_image); //获取画布的高度
//list — 把数组中的值赋给一些变量
/*echo "<pre>";
print_r(getimagesize($src_file));
echo "</pre>";
echo "<hr>";
die;*/
//list($src_w,$src_h) = getimagesize($src_file);
$dst_x = ($dst_w - $src_w)/2;
$dst_y = ($dst_h - $src_h)/2; $src_x = 0;
$src_y = 0;
$pct = 50; //0-100
imagecopymerge($dst_im, $src_im, $dst_x, $dst_y, $src_x, $src_y, $src_w, $src_h, $pct); //第三步: 输出图像
header('content-type:image/jpeg');
//imagejpeg(图像资源);
imagejpeg($dst_im); //第四步: 销毁图像
//imagedestroy(图像资源);
imagedestroy($dst_im);
imagedestroy($src_im); ?>
PHP核心编程-图像操作的更多相关文章
- PHP核心编程--目录操作(包含文件操作)
一.目录操作 1. 创建目录 创建目录mkdir(目录名称) //返回值为布尔 一次性创建主目录及其子目录 判断是不是一个目录is_dir //返回true,false 判断目录或文件是否存 ...
- 使用同步或异步的方式完成 I/O 访问和操作(Windows核心编程)
0x01 Windows 中对文件的底层操作 Windows 为了方便开发人员操作 I/O 设备(这些设备包括套接字.管道.文件.串口.目录等),对这些设备的差异进行了隐藏,所以开发人员在使用这些设备 ...
- CreateThread 线程操作与 _beginthreadex 线程安全(Windows核心编程)
0x01 线程的创建 线程不同于进程,Windows 中的进程是拥有 '惰性' 的,本身并不执行任何代码,而执行代码的任务转交给主线程,列如使用 CreateProcess 创建一个进程打开 Cmd ...
- Qt on Android 核心编程
Qt on Android 核心编程(最好看的Qt编程书!CSDN博主foruok倾力奉献!) 安晓辉 著 ISBN 978-7-121-24457-5 2015年1月出版 定价:65.00元 4 ...
- windows核心编程 - 线程同步机制
线程同步机制 常用的线程同步机制有很多种,主要分为用户模式和内核对象两类:其中 用户模式包括:原子操作.关键代码段 内核对象包括:时间内核对象(Event).等待定时器内核对象(WaitableTim ...
- windows核心编程---第九章 同步设备IO与异步设备IO之同步IO
同步设备IO 所谓同步IO是指线程在发起IO请求后会被挂起,IO完成后继续执行. 异步IO是指:线程发起IO请求后并不会挂起而是继续执行.IO完毕后会得到设备的通知.而IO完成端口就是实现这种通知的很 ...
- windows核心编程---第八章 使用内核对象进行线程同步
使用内核对象进行线程同步. 前面我们介绍了用户模式下线程同步的几种方式.在用户模式下进行线程同步的最大好处就是速度非常快.因此当需要使用线程同步时用户模式下的线程同步是首选. 但是用户模式下的线程同步 ...
- windows核心编程---第二章 字符和字符串处理
使用vc编程时项目-->属性-->常规栏下我们可以设置项目字符集合,它可以是ANSI(多字节)字符集,也可以是unicode字符集.一般情况下说Unicode都是指UTF-16.也 ...
- Python核心编程-描述符
python中,什么描述符.描述符就是实现了"__get__"."__set__"或"__delete__" 方法中至少一个的对象.什么是非 ...
随机推荐
- leetcode 238 & leetcode 152 & leetcode 228
lc238 Product of Array Except Self 遍历两次数组 用一个res[] 记录答案 1) 第一次,从左往右遍历 res[i] 记录0~i-1的乘积 2) 第二次,从右往左遍 ...
- 深入浅出 Java Concurrency (10): 锁机制 part 5 闭锁 (CountDownLatch)[转]
此小节介绍几个与锁有关的有用工具. 闭锁(Latch) 闭锁(Latch):一种同步方法,可以延迟线程的进度直到线程到达某个终点状态.通俗的讲就是,一个闭锁相当于一扇大门,在大门打开之前所有线程都被阻 ...
- jeecmsv8 shiro 分析
源代码注释可见 https://github.com/chenbo19867758/jeecmsV8-BoBo.git 1.后台登录页面 /jeeadmin/jeecms/login.do 1 w ...
- mysql大数据表优化
1.应尽量避免在 where 子句中使用!=或<>操作符,否则将引擎放弃使用索引而进行全表扫描. 2.对查询进行优化,应尽量避免全表扫描,首先应考虑在 where 及 order by 涉 ...
- Redis源码解析:14Redis服务器与客户端间的交互
Redis服务器是典型的一对多服务器程序,通过使用由IO多路复用技术实现的文件事件处理器,Redis服务器使用单线程单进程的方式来处理命令请求,并与多个客户端进行网络通信. Redis客户端与服务器之 ...
- LUOGU P1937 [USACO10MAR]仓配置Barn Allocation
传送门 解题思路 扫了一眼觉得是贪心+线段树,结果贪心的时候刚开始按区间长度排的序..这还有82分,后来叉了自己,换成按右端点排序过了. 代码 #include<iostream> #in ...
- Hackerrank--Team Formation
题目链接 For an upcoming programming contest, Roy is forming some teams from the n students of his unive ...
- 适配器模式--在NBA我需要翻译
适配器模式:将一个类的接口转换成客户希望的另外一个接口.Adapter模式使得原本由于接口不兼容而不能一起工作的那些类可以一起工作. 在软件开发中,也就是系统的数据和行为都正确,但接口不符时,我们应 ...
- 项目中的那些事---Java反射的应用
最近工作中遇到一个这样的问题: 为某个项目中的所有接口做一个测试工具,使用java Swing技术,该项目有不同的版本,不是所有版本中的接口都是相同的,而我做的工具需要兼容所有版本. 于是就引入了这样 ...
- 再问你Java内存模型的时候别再给我讲堆栈方法区
在介绍Java内存模型之前,先来看一下到底什么是计算机内存模型,然后再来看Java内存模型在计算机内存模型的基础上做了哪些事情.要说计算机的内存模型,就要说一下一段古老的历史,看一下为什么要有内存模型 ...