php 滑动图片验证生成
1.话不多说,直接干货,喜欢的希望大家一键三连
<?php namespace App\Model; class VerifyImage { //浮层坐标数组 protected $tailoringArray = []; //浮层图宽 protected $picW = 100; //浮层图高 protected $picH = 100; //浮层图圆半径 protected $r = 10; //截图小图路径 protected $tailoringSmallSavePath; //截图大图路径 protected $tailoringBigSavePath; //截图小图图片名称 protected $tailoringSmallName; //截图大图图片名称 protected $tailoringBigName; //图片后缀 protected $picSuffix = '.png'; //原图路径 protected $srcPic; //原图信息 protected $picInfo; //图片保存路径 protected $picSavePath; //资源图片路径 protected $resourcesPath; //初始化相关数据 public function init() { $this->resourcesPath = BASE_PATH . '/static/code/'; //背景图片存放目录 (Resources) $dir = BASE_PATH . '/static/images/code/' . date('YmdH'); //被处理图片 存放目录(裁剪小图,错位背景图) $this->tailoringBigSavePath = $dir . '/big/'; $this->tailoringSmallSavePath = $dir . '/small/'; $this->getRandomPng(); $this->tailoringSmallName = $this->tailoringSmallSavePath . md5(uniqid()) . $this->picSuffix; $this->tailoringBigName = $this->tailoringBigSavePath . md5(uniqid() . time()) . $this->picSuffix; //检查目录是否存在 if (!file_exists($this->tailoringBigSavePath)) { mkdir($this->tailoringBigSavePath, 0777, true); } if (!file_exists($this->tailoringSmallSavePath)) { mkdir($this->tailoringSmallSavePath, 0777, true); } //删除过时资源图片 $this->picSavePath = dirname($dir); //删除一小时之前图片 $this->deleteHourXSVerificationImage($this->picSavePath); } public function __construct() { $this->init(); // 获取原图的 宽高 $this->picInfo = $this->getPicWidthHeight($this->srcPic); $this->getTailoringImage(); } // 获取图片宽、高 public function getPicWidthHeight($pic_path) { $lim_size = getimagesize($pic_path); return array('w' => $lim_size[0], 'h' => $lim_size[1]); } //随机获取参照图片 private function getRandomPng() { $this->srcPic = $this->resourcesPath . $this->tailoringBigName . mt_rand(1, 4) . '.png'; echo $this->srcPic; if (!file_exists($this->srcPic)) { throw new \Exception('图片资源不存在!!!'); } else { return $this->srcPic; } } //获取浮层图片 public function getTailoringImage(){ $dr = $this->r*$this->r; //半径平方 $local_w = $this->r*2-5; //第一个圆中心点 $circular1_x = $local_w+($this->picW-($local_w)*2)/2; $circular1_y = $this->r; //第二个圆中心点 $circular2_x = $this->picH-$this->r; $circular2_y = $local_w+($this->picH-($local_w)*2)/2;; for($i=0;$i<$this->picH;$i++){ for($j=0;$j<$this->picW;$j++){ //根据公式(x-a)²+(y-b)² = r² 算出像素是否在圆内 $d1 = pow($j-$circular1_x,2)+pow($i-$circular1_y,2); $d2 = pow($j-$circular2_x,2)+pow($i-$circular2_y,2); if(($i>=$local_w && $j>=$local_w && $i<=$this->picH-$local_w && $j<=$this->picW-$local_w) || $d1<=$dr || $d2<=$dr){ $this->tailoringArray[$i][$j] = 1; //在拼图内为1 } else { $this->tailoringArray[$i][$j] = 0; //在拼图外为0 } } } } // 创建背景图和浮层图、浮层图x,y坐标 public function createImage(){ //原图 $srcFile = $this->srcPic; $src_w = $this->picInfo['w']; //原图宽 $src_h = $this->picInfo['h']; //原图高 $src_im = imagecreatefrompng($srcFile); $dst_im = imagecreatetruecolor($src_w,$src_h); //根据原图尺寸创建一个相同大小的真彩色位图 //给新图填充背景色 $black = imagecolorallocate($dst_im,0,0,0);//黑 imagefill($dst_im,0,0,$black); imagecopymerge($dst_im,$src_im,0,0,0,0,$src_w,$src_h,100);//原图图像写入新建真彩位图中 //生成透明底拼图画布 $jigsaw_im = imagecreatetruecolor($this->picW,$this->picH); //100*100拼图画布 imagealphablending($jigsaw_im,false); imagesavealpha($jigsaw_im, true); $jigsaw_bg = imagecolorallocatealpha($jigsaw_im,0,0,0,127); imagefill($jigsaw_im, 0, 0, $jigsaw_bg); //随机位置 $src_x = mt_rand(215,$src_w-$this->picW); //水印位于大图x坐标 $src_y= mt_rand(0,$src_h-35); //y坐标 $this->rgb_white = imagecolorallocatealpha($dst_im,127,127,127,60); //灰色水印 //循环轮廓抠图 for($i=0;$i<$this->picH;$i++){ for ($j=0;$j<$this->picW;$j++){ if($this->tailoringArray[$i][$j] == 1){ //如果在轮廓内,取原图像素颜色 $this->rgb = ImageColorAt($dst_im,$src_x+$j,$src_y+$i); imagesetpixel($jigsaw_im,$j,$i,$this->rgb); //在拼图画布上色 //在原图挖坑(打上灰色) imagesetpixel($dst_im,$src_x+$j,$src_y+$i,$this->rgb_white); } } } //保存图片 imagepng($dst_im,$this->tailoringBigName); imagepng($jigsaw_im,$this->tailoringSmallName); imagedestroy($src_im); imagedestroy($dst_im); imagedestroy($jigsaw_im); return ['tailoringBgImage'=>$this->tailoringBigName,'tailoringImage'=>$this->tailoringSmallName,'x'=>$src_x,'y'=>$src_y]; } // 删除一小时之前的 验证码图片 public function deleteHourXSVerificationImage($dir) { $op = dir($dir); $time = date("YmdH", strtotime("-1 hours")); $i = 0; while (false != ($item = $op->read()) && $i <= 10) { $i++; if ($item == '.' || $item == '..') { continue; } if (is_numeric($item) && $item <= $time || !is_numeric($item)) { if (is_dir($op->path . '/' . $item) && rmdir($op->path . '/' . $item) == false) { $this->deleteHourXSVerificationImage($op->path . '/' . $item); } else { echo $op->path . '/' . $item; unlink($op->path . '/' . $item); } } } } }