Fastadmin 大转盘抽奖+后台管理员扫码核销+公众号发送1块红包

14 篇文章 0 订阅
7 篇文章 0 订阅

最近公司有需求搞个抽奖活动,看了好多文档,都是到差不差的,记录一下,将就看,肯定还有改进的地方
首先还是公众号授权信息,获得授权信息后,拿到openid,传给easywechat的获取单个用户信息方法,查询当前用户是否关注公众,若为关注,返回给前端,前端判断显示二维码还是大转盘,页面就不说了,展示效果自己画吧
大转盘的页面百度网盘 提取码:yoza
在这里插入图片描述
点击开始后判断当前活动时间是否结束,当前抽奖次数是否已经抽完毕等等提示
然后获取当前抽奖的活动奖品,获取中奖号

		//获取对应的概率率数组
			$rateArr = array_column($prmodel, 'probability');
			// 测试中将几率
//		foreach ($prmodel as $k => $v) {
//			$prmodel[$k]['中奖次数'] = 0;
//			$prmodel[$k]['概率'] = strval($v['probability']) . '%';
//			unset($prmodel[$k]['probability']);
//		}
//		for ($i = 0; $i < 10000; $i++) {
//			$result = $this->getRandPrize($rateArr);
//			$prmodel[$result]['中奖次数']++;
//		}
//				dd($prmodel);
			// 返回中奖号
			$result = $this->getRandPrize($rateArr);
			/**
	 * 返回转盘抽奖结果
	 * @param array $proArr 概率数组(值为概率)
	 * @return int|string 返回对应数组的下标
	 */
	private function getRandPrize($proArr)
	{
		$result = '';
		//概率数组的总概率精度
		$proSum = array_sum($proArr);
		//概率数组循环
		foreach ($proArr as $key => $proCur) {

			$randNum = mt_rand(1, $proSum);

			if ($randNum <= $proCur) {

				$result = $key;
				break;
			} else {
				$proSum -= $proCur;
			}
		}
		unset ($proArr);

		return $result;
	}

再根据当前返回的下标去获得对应的数组数据,如果奖品数量不为0,就减去当前奖品数量,再次查询当前奖品数量,若为0,将当前奖品的概率设置为0,并且把概率相加到免费的奖品上去。
如果不是免费的奖品,将生成二维码线下客服扫码核销,生成二维码用的扩展 phpqrcode,
二维码生成并且带logo

public function createQRcode($url,$qname,$filename)
	{

		Vendor('phpqrcode.phpqrcode');
		$value = $url;         //二维码内容
		$errorCorrectionLevel = 'H';  //容错级别
		$matrixPointSize = 6;      //生成图片大小
		$newqrcode = new \QRcode();
		// 判断是否有这个文件夹  没有的话就创建一个
		if(!is_dir("qrcode")){
			// 创建文件夹
			mkdir("qrcode");
		}
		//二维码图片保存路径
		$pathname = ROOT_PATH . '/public/'.$filename.'/';
		//生成二维码图片
		$qrfilename = $filename.'/'.$qname. time() . rand(10000, 9999999) . '.png';
		$newqrcode->png($value,$qrfilename , $errorCorrectionLevel, $matrixPointSize, 2);
		$logo = ROOT_PATH.'public/assets/img/logo.png'; //准备好的logo图片
		$QR = $qrfilename;      //已经生成的原始二维码图

		if (file_exists($logo)) {
			$QR = imagecreatefromstring(file_get_contents($QR));    //目标图象连接资源。
			$logo = imagecreatefromstring(file_get_contents($logo));  //源图象连接资源。
			$QR_width = imagesx($QR);      //二维码图片宽度
			$QR_height = imagesy($QR);     //二维码图片高度
			$logo_width = imagesx($logo);    //logo图片宽度
			$logo_height = imagesy($logo);   //logo图片高度
			$logo_qr_width = $QR_width / 4;   //组合之后logo的宽度(占二维码的1/5)
			$scale = $logo_width/$logo_qr_width;  //logo的宽度缩放比(本身宽度/组合后的宽度)
			$logo_qr_height = $logo_height/$scale; //组合之后logo的高度
			$from_width = ($QR_width - $logo_qr_width) / 2;  //组合之后logo左上角所在坐标点
			//重新组合图片并调整大小
			/*
			 * imagecopyresampled() 将一幅图像(源图象)中的一块正方形区域拷贝到另一个图像中
			 */
			imagecopyresampled($QR, $logo, $from_width, $from_width, 0, 0, $logo_qr_width,$logo_qr_height, $logo_width, $logo_height);
		}

		//输出图片
		imagepng($QR, $qrfilename);
		imagedestroy($QR);
		imagedestroy($logo);
		// 返回浏览地址
//		$qrappurl = $this->cdnurl("/".$filename,true);
		// 框架内置 cdnurl
		$qrappurl = cdnurl("/".$qrfilename, true);
		return $qrappurl;
	}
	/**
	 * 获取上传资源的CDN的地址
	 * @param string  $url    资源相对地址
	 * @param boolean $domain 是否显示域名 或者直接传入域名
	 * @return string
	 */
	function cdnurl($url, $domain = false)
	{
		$regex = "/^((?:[a-z]+:)?\/\/|data:image\/)(.*)/i";
		$cdnurl = \think\Config::get('upload.cdnurl');
		$url = preg_match($regex, $url) || ($cdnurl && stripos($url, $cdnurl) === 0) ? $url : $cdnurl . $url;
		if ($domain && !preg_match($regex, $url)) {
			$domain = is_bool($domain) ? request()->domain() : $domain;
			$url = $domain . $url;
		}
		return $url;
	}

生成后更新到当前中奖记录的二维码字段。
如果是中奖的红包1块,将直接发送红包1块到公众号,用户在公众号就能领取,也可以发送到余额,这里就只用到了发送红包,发送余额请参考 EasyWeChat 文档,红包发送需要到微信支付商户后台设置,每天每人领取的最多次数,每天每人可领取的最大金额,数据库也设置了红包的数量

/**
	 *订单号生成  18位
	 */
	public function CreateOrdernum()
	{
		$osn = date('Ymd') . substr(implode(NULL, array_map('ord', str_split(substr(uniqid(), 7, 13), 1))), 0, 18);//订单号生成
		return $osn;
	}


	/*
	 * 发送红包
	 * 现金红包发放后会以公众号消息的形式触达用户,不同情况下触达消息的形式会有差别,相关规则如下:
	 * 1.已关注公众号的用户,使用“防伪消息”触达;
	 * 2.未关注公众号的用户,使用“模板消息”触达。
	 * $lotteryname 活动名称
	 * $openid 用户openid
	 */
    public function  sendredpack($lotteryname,$openid){

	    $payment = Factory::payment($this->config);

	    $redpack = $payment->redpack;
	    $redpackData = [
		    'mch_billno'   => $this->CreateOrdernum(),// 商户订单号(每个订单号必须唯一。取值范围:0~9,a~z,A~Z)
		    'send_name'    => '红包名称', // 红包发送者名称
		    're_openid'    => $openid, // 接受红包的用户openid
		    'total_num'    => 1,  //固定为1,可不传,红包发放总人数
		    'total_amount' => 100,  //单位为分,不小于100,每次1块钱
		    'wishing'      => '恭喜您中奖啦', // 红包祝福语
		    'act_name'     => $lotteryname,// 活动名称
		    'remark'       => '测试备注',
		    'scene_id'     => 'PRODUCT_2', // 发放红包使用场景,红包金额大于200或者小于1元时必传 PRODUCT_2:抽奖
	    ];
	    // return_code 此字段是通信标识,非红包发放结果标识,红包发放是否成功需要查看result_code来判断
	    //
	    // sendNormal 普通个人红包
	    // sendGroup 裂变红包
	    $result = $redpack->sendNormal($redpackData);
//	    log::info('发送红包返回状态:' . print_r($result, true));
	    return $result;
    }

发送红包是查看 “result_code” => “SUCCESS” 是否,错误的话返回 “result_code” => “FAIL” ,成功返回以下

成功
array:11 [
  "return_code" => "SUCCESS"
  "return_msg" => "发放成功"
  "result_code" => "SUCCESS"
  "err_code" => "SUCCESS"
  "err_code_des" => "发放成功"
  "mch_billno" => "订单号"
  "mch_id" => "商户id"
  "wxappid" => "公众id"
  "re_openid" => "用户openid"
  "total_amount" => " 金额100"
  "send_listid" => "红包记录查询id"
]
失败
  "return_code" => "SUCCESS"
  "return_msg" => "每个红包的平均金额必须在1.00元到1.00元之间."
  "result_code" => "FAIL"
  "err_code" => "MONEY_LIMIT"
  "err_code_des" => "每个红包的平均金额必须在1.00元到1.00元之间."
  "mch_billno" => "订单号"
  "mch_id" => "商户id"
  "wxappid" => "公众id"
  "re_openid" => "用户openid"
  "total_amount" => "30" // 错误的金额

成功后生成红包发送记录,方便后续查看

前台客服扫码核销兑换奖品,微信扫一扫授权登录,授权回调判断是否为扫码客服,前台点击确认核销,核销当前奖品。
在我的奖品里面,点击兑换按钮,展示当前奖品的二维码,若状态不为可兑换奖品,直接展示结果,红包则展示已发送到公众号,以及发送红包时间。

大转盘的文字是没有换行的,只能一行展示,也可以换成图片,下面是换行

/**
				 * canvas处理文字超长自动换行
				 * @type {number}
				 */
				ctx.lineWidth=1;
				var lineWidth = 0;
				var canvasWidth = canvas.width;//计算canvas的宽度
				var initHeight=15;//绘制字体距离canvas顶部初始的高度
				var lastSubStrIndex= 0; //每次开始截取的字符串的索引

				lineWidth+=ctx.measureText(info[i]).width;
				if(lineWidth>(canvasWidth/4)){
					ctx.fillText(info[i].substring(lastSubStrIndex,4),-30,-125,60);//绘制截取部分
					initHeight+=20;//20为字体的高度
					lineWidth=0;
					lastSubStrIndex=i+5;
					if(i <= info[i].length-1){//绘制剩余部分
						ctx.fillText(info[i].substring(4,i+6),-30,-105,55);
					}
				}else{
					ctx.fillText(info[i],-30,-125,60);
					// ctx.fillText(info[i],80,-5,60);
				}

页面效果,进度条使用的layui的,后台计算值后返回给前台就行
在这里插入图片描述
右下角的奖品点击开始后,会更新数据,可以获取缓存来更新
奖品页面
在这里插入图片描述
兑换二维码
在这里插入图片描述
有待升级

  • 1
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
转盘抽奖是一种常见的游戏方式,通过转动转盘来抽取随机奖品或奖励。为了方便管理和控制抽奖过程,我们可以使用带后台的HTML来实现。 首先,我们需要设计一个大转盘抽奖的前端界面。这个界面包含转盘的样式和布局,还需要添加一些按钮或动画效果来实现转盘的旋转和停止。在前端界面中,我们可以使用HTML、CSS和JavaScript来实现。 接下来,我们需要搭建一个后台服务器来管理抽奖过程。后台可以使用HTML和JavaScript来实现,也可以使用其他的服务器端技术,如Node.js或PHP。后台需要实现以下功能: 1. 奖品设置:后台可以管理奖品的种类和数量,可以设置每个奖品在转盘上的位置。 2. 用户信息管理:后台可以记录用户的信息,如姓名、联系方式等。当用户参与抽奖时,后台可以保存用户的抽奖记录。 3. 抽奖逻辑:后台需要实现抽奖的逻辑,包括生成随机奖品、判断用户是否中奖以及记录用户的中奖信息等。 4. 数据统计:后台可以统计用户的抽奖次数、中奖情况等数据,以便后续的分析和优化。 在实际使用中,用户可以通过前端界面进行抽奖操作,前端界面会发送请求给后台服务器,后台服务器会根据设定的规则进行抽奖计算,并返回相应的结果给前端界面。前端界面会显示用户中奖的奖品或提示未中奖。 通过使用带后台的HTML来实现大转盘抽奖,我们可以方便地管理和控制抽奖过程,同时也可以提供更好的用户体验和数据分析能力,对于商家或活动举办方来说,这是一种非常实用和有效的抽奖方式。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

时间轴-小文同学

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值