当前位置: 首页 > news >正文

千里共婵娟 | 结合微信公众号用JavaScript完整开发实现换中秋头像的功能

在这里插入图片描述

🏆作者简介,黑夜开发者,CSDN领军人物,全栈领域优质创作者✌,阿里云社区专家博主,2023年6月csdn上海赛道top4。
🏆数年电商行业从业经验,历任核心研发工程师,项目技术负责人。
🏆本文已收录于专栏:100个JavaScript的小应用,微信公众号开发。
🎉欢迎 👍点赞✍评论⭐收藏

文章目录

  • 🚀一、前言
  • 🚀二、开发流程概述
  • 🚀三、配置微信公众号
    • 🔎3.1 AppId和AppSecret获取
    • 🔎3.1 添加网页授权域名
    • 🔎3.3 白名单设置
  • 🚀四、功能开发
    • 🔎4.1 获取用户微信头像
      • 🍁4.1.1 引导用户进入授权页面
      • 🍁4.1.2 获取授权code并换取access_token
      • 🍁4.1.3 获取用户基本信息
    • 🔎4.2 JavaScript实现用户换头像
      • 🍁4.2.1 创建HTML结构(index.php)
      • 🍁4.2.2 拼接头像和相框
      • 🍁4.2.3 生成头像为一个图片
  • 🚀五、总结


🚀一、前言

中秋节是我国的重要传统节日,今年直接和国庆节凑到了一起,放一个8天的小长假,是不是很兴奋呢。为了增加节日气氛,许多人会更换自己的社交媒体头像,如微信头像。使用与中秋或者国庆主题相关的图片。本篇博文将介绍如何使用PHP通过微信公众号获取用户头像,并且将头像传递给JavaScript开发一个实现换中秋头像的功能。

在这里插入图片描述

通过本篇文章的阅读,您将获取如下的实战知识:

  1. 熟悉了解微信公众号的基本开发流程。
  2. 学习到微信公众号网页授权获取用户基本信息这个板块的开发。
  3. 基本掌握html,css等网页前端的组成与基本开发流程。
  4. Javascript, canvas用于图片合成,头像生成的场景使用。
  5. 学习到一部分PHP相关的后端知识

🚀二、开发流程概述

首先我们得通过微信公众号开发获取到用户的头像,然后我们需要准备一些素材。这个图片素材需要是镂空图 PNG,用来镶嵌在用的真实头像上面。接下来,我们需要创建一个HTML页面,并在其中引入一个JavaScript文件。我们将使用JavaScript来操作DOM元素和Canvas元素,实现换装功能。如果您熟悉HTMLJavaScript的基本知识那就更好了。

🚀三、配置微信公众号

🔎3.1 AppId和AppSecret获取

AppIdAppSecret得先获取到,请看下图,记得一定要保存好AppSecret
在这里插入图片描述

🔎3.1 添加网页授权域名

网页授权域名是必须要添加的,否则公众号是不回允许在没有通过的域名下面进行授权。如果你遇到了一些问题,可以排查一下是不是这个地方的配置。在公众号设置>功能设置里面添加,加域名就行。

在这里插入图片描述

这里可能要传文件验证,如果传了文件还是有问题,可以检查一下文件权限啥的,或者看看能不能手动访问。

🔎3.3 白名单设置

白名单主要是添加自己服务器所在的IP地址到公众号后台,这样只有指定的服务器才允许与公众号接口通信。如果白名单没有设置,获取access_token的时候可能会报如下错误。

{"errcode":40164,"errmsg":"invalid ip xxx ipv6 ::ffff:xxxx, not in whitelist rid: 6503251e-14033bf0-774d3d3e"}

在这里插入图片描述

在安全中心>IP白名单处进行设置,白名单设置了可能会有短暂的延时生效,如果当时不能访问,可以等会再试一下。

🚀四、功能开发

🔎4.1 获取用户微信头像

这个部分主要通过PHP进行开发,核心是如何与公众号进行API交互。

🍁4.1.1 引导用户进入授权页面

构建一个URL,用户点击后将跳转到微信授权页面,同时携带着您设置的回调URL。

$redirect_uri = urlencode('http://your-domain.com/callback.php'); // 回调URL,需要urlencode
$appid = 'Your Appid'; // 公众号AppID
$scope = 'snsapi_userinfo'; // snsapi_base或snsapi_userinfo
$state = 'STATE'; // 自定义参数,可不填
$auth_url = "https://open.weixin.qq.com/connect/oauth2/authorize?appid={$appid}&redirect_uri={$redirect_uri}&response_type=code&scope={$scope}&state={$state}#wechat_redirect";
header('Location: ' . $auth_url); // 跳转到授权页面

在到达callback.php之前,如果已经关注了公众号的用户,可以直接获取到用户头像,否则则会提示授权,用户同意之后才能获取头像,这便是网页授权获取用户头像的核心功能。授权的情况可以见下图真实案例。

在这里插入图片描述

🍁4.1.2 获取授权code并换取access_token

用户同意授权后,微信会重定向到您设置的回调URL,并携带一个code参数。在回调页面(callback.php)中获取到该code,并使用它来换取access_tokenopenid

$code = $_GET["code"]; // 授权code
$appid = 'Your Appid'; // 公众号AppID
$secret = 'Your App Secret'; // 公众号App Secret// 通过code换取access_token
$token_url = "https://api.weixin.qq.com/sns/oauth2/access_token?appid={$appid}&secret={$secret}&code={$code}&grant_type=authorization_code";
$token_data = json_decode(file_get_contents($token_url), true);$access_token = $token_data['access_token']; // 获取到的access_token
$openid = $token_data['openid']; // 用户的openid

🍁4.1.3 获取用户基本信息

使用获取到的access_tokenopenid,可以调用以下API来获取用户基本信息:

$userinfo_url = "https://api.weixin.qq.com/sns/userinfo?access_token={$access_token}&openid={$openid}&lang=zh_CN";
$userinfo_data = json_decode(file_get_contents($userinfo_url), true);$nickname = $userinfo_data['nickname']; // 用户昵称
$headimgurl = $userinfo_data['headimgurl']; // 用户头像链接
// 可以根据需要获取其他用户信息字段
header('Location: https://www.xxx.wang/index.html?avatar_url=' . $headimgurl

上面代码的最后一句是重点,将获取到的微信头像传递给index.html,后面javascript会用到。

🔎4.2 JavaScript实现用户换头像

🍁4.2.1 创建HTML结构(index.php)

在HTML文件中,我们可以使用<input type="file">元素来让用户选择要上传的头像文件。同时,我们还需要一个<canvas></canvas>元素来绘制新的头像。

<!DOCTYPE html>
<html>
<head><title>头像换装</title>
</head>
<body><h1>头像换装</h1><div id="avatar"><img src="./img/head0.png" alt="0" id="avatar_template" style="z-index: 1000;pointer-events: none;"><img src="" alt="" id="avatar_img" class="pinch-zoom"></div><p class="hide"><canvas style="width:500px;height:500px;" id="cvs"></canvas></p><div style="display: none;" class="avatar-final"><div class="finished-img"><img id="finishedImg" src=""/><br></div><p class="control"><a class="css_btn_create" id="download">生成</a></p></div><script src="main.js"></script><script>loadImage()</script>
</body>
</html>

这里我用photoshop制作这么一个相框图片,里面加载头像,就是上面的head0.png

在这里插入图片描述

🍁4.2.2 拼接头像和相框

其中avatar_template就是我们的头像相框,avatar_img就是我们的微信头像,通过下面的方式来讲头像放到img标签里面。并且将拼接好的图片放到finishedImg里面。

// 将url的图片加载到页面
function loadImage() {let imgUrl = getQueryString('avatar_url');// 通过路径解析处高清图像imgUrl = headImgHD(imgUrl);$('#avatar_img').attr('src', imgUrl);$('#avatar_img').attr('crossOrigin', 'anonymous');curImage = $('#avatar_template').attr('src');drawToCanvas(imgUrl, curImage, $('#finishedImg'));
}// 开始整合绘制图片到finishedImg里面
function drawToCanvas(img1, img2, showObj) {let cvs = document.getElementById('cvs');let showSize = 230;let size = 800;cvs.width = size;cvs.height = size;let ctx = cvs.getContext('2d');let image1 = new Image;image1.setAttribute('crossOrigin', 'anonymous');image1.src = img1;image1.onload = function () {let width = image1.width < image1.height ? size : size * (image1.width / image1.height);let height = image1.width > image1.height ? size : size * (image1.height / image1.width);let x = image1.width < image1.height ? 0 : (size * (image1.width / image1.height) - size) / 2;let y = image1.width > image1.height ? 0 : (size * (image1.height / image1.width) - size) / 2;document.getElementById('avatar_img').style.showSize = width + 'px';document.getElementById('avatar_img').style.showSize = height + 'px';document.getElementById('avatar_img').style.marginLeft = -x + 'px';document.getElementById('avatar_img').style.marginTop = -y + 'px';ctx.drawImage(image1, -x, -y, width, height);let image2 = new Image;image2.setAttribute('crossOrigin', 'anonymous');image2.src = img2;image2.onload = function () {ctx.drawImage(image2, 0, 0, size, size);let canvas = document.getElementById('cvs');//获取二维码中的图片地址let src_xp = canvas.toDataURL('image/jpeg');$(showObj).attr('src', src_xp)}}
}

🍁4.2.3 生成头像为一个图片

当用户完成头像换装后,我们可以提供一个按钮来让用户生成新的头像。这里,我们可以使用html2canvas方法将页面元素转化为一个整体的图片,并将其显示在页面中。这个时候我们可以长按图片保存,然后上传到我的头像就完成了换头像的功能。

$('#download').click(function (ev) {takeScreenShot();
});function takeScreenShot() {html2canvas(document.getElementById('avatar'), {allowTaint:false,dpi: 400,useCORS: true,onrendered: function(canvas) {document.body.appendChild(canvas);var canvas = $('canvas')[1];//获取二维码中的图片地址let src_xp = canvas.toDataURL('image/jpeg');console.log(src_xp);$('#finishedImg').attr('src', src_xp)$('.avatar-final').show();$('#avatar-control').hide();$(canvas).hide();},});
}

最后,一起来看看最终的头像效果。

在这里插入图片描述

🚀五、总结

本篇博文介绍了如何使用JavaScript开发一个实现换中秋头像功能的应用程序。我们通过与微信公众号头像打通,并使用Html进行页面绘制。最后,通过Canvas进行图片整合,并提供一个生成按钮让用户一键生成新的头像。

在这里插入图片描述

如果你想直接体验换头像的功能,可以关注下面公众号回复【换头像】。今天的内容就到这里,我们下次见。

相关文章:

千里共婵娟 | 结合微信公众号用JavaScript完整开发实现换中秋头像的功能

&#x1f3c6;作者简介&#xff0c;黑夜开发者&#xff0c;CSDN领军人物&#xff0c;全栈领域优质创作者✌&#xff0c;阿里云社区专家博主&#xff0c;2023年6月csdn上海赛道top4。 &#x1f3c6;数年电商行业从业经验&#xff0c;历任核心研发工程师&#xff0c;项目技术负责…...

pt26django教程

admin 后台数据库管理 django 提供了比较完善的后台管理数据库的接口&#xff0c;可供开发过程中调用和测试使用 django 会搜集所有已注册的模型类&#xff0c;为这些模型类提拱数据管理界面&#xff0c;供开发者使用 创建后台管理帐号: [rootvm mysite2]# python3 manage.…...

javabasic

计算机基础 一、学前知识 1. 计算机组成 2. 进制的概念 &#xff08;1&#xff09;二进制的存储 计算机不管是内存还是硬盘&#xff0c;都是以二进制的形式存储。如同一张巨大的表格&#xff0c;里面都是由0和1组成。 二进制&#xff1a;逢2进1 基数为2&#xff0c;数值部分…...

电子词典项目

目录 目录 头文件&#xff1a;dict.h: 源文件&#xff1a;dict.c: 服务器测试文件&#xff1a;serDict.c: 客户端测试文件&#xff1a;cliDict.c: 头文件&#xff1a;dict.h: #ifndef __DICT_H__ #define __DICT_H__ #include<myhead.h> #include<sqlite3.h>#de…...

SQL12 高级操作符练习(2)

描述 题目&#xff1a;现在运营想要找到学校为北大或GPA在3.7以上(不包括3.7)的用户进行调研&#xff0c;请你取出相关数据&#xff08;使用OR实现&#xff09; 示例&#xff1a;user_profile iddevice_idgenderageuniversitygpa12138male21北京大学3.423214male复旦大学4.03…...

python写代码过程中的坑230915

1.解释代码IndentationError: expected an indented block 这个错误通常是由于代码缩进错误导致的。 在Python中,代码块(如循环、条件语句、函数等)通常使用缩进来表示。因此,如果你在期望缩进的位置没有正确缩进代码,就会出现"IndentationError: expected an inden…...

SpringBoot课堂笔记20230913

本篇文章为SpringBoot学习笔记&#xff0c;方便自己再复习。 Maven&#xff1a;jar包管理工具 注解&#xff1a; Controller:处理http请求&#xff0c;返回的视图 RestController: 相当于ResponseBody和Controller一起用&#xff0c;返回的是json ResponseBody:返回响应内容 …...

3D数字孪生:从3D数据采集到3D内容分析

数字孪生&#xff08;Digital Twin&#xff09;是物理对象、流程或系统的虚拟复制品&#xff0c;用于监控、分析和优化现实世界的对应物。 这些数字孪生在制造、工程和城市规划等领域变得越来越重要&#xff0c;因为它们使我们能够在现实世界中实施改变之前模拟和测试不同的场景…...

【杂记】git管理工具的相关应用

这里记录一些用git管理工具进行开发的命令&#xff0c;便于自己查看&#xff0c;我认为下面两篇博客写的很详细&#xff0c;但是为了自己方便查看&#xff0c;所以自己写了一些命令供自己进一步理解。gitee相对git来说更方便一些&#xff08;毕竟国内的不用担心墙&#xff09;&…...

看好多人都在劝退学计算机,可是张雪峰又 推荐过计算机,所以计算机到底是什么样 的?

张雪峰高考四百多分&#xff0c;但是他现在就瞧不起400多分的学生。说难听点&#xff0c;六七百分的 热门专业随便报谁不会啊&#xff1f; 计算机专业全世界都是过剩的&#xff0c;今年桂林电子科技&#xff0c;以前还是华为的校招大学&#xff0c;今年 计算机2/3待业。这个世…...

leetcode 26.删除有序数组中的重复项

给你一个 升序排列 的数组 nums &#xff0c;请你 原地 删除重复出现的元素&#xff0c;使每个元素 只出现一次 &#xff0c;返回删除后数组的新长度。元素的 相对顺序 应该保持 一致 。然后返回 nums 中唯一元素的个数。 考虑 nums 的唯一元素的数量为 k &#xff0c;你需要做…...

jitsi音视频会议集成到自己的网页中

将jitsi视频会议集成到自己的web网站&#xff1a; 源码&#xff1a; <!DOCTYPE html> <html lang"en" xmlns:th"http://www.thymeleaf.org"> <head><meta charset"UTF-8"><meta name"viewport" content&…...

浅析Java责任链模式实现

一、概要 定义&#xff1a;责任链模式是一种行为设计模式&#xff0c; 允许你将请求沿着处理者链进行发送。收到请求后&#xff0c; 每个处理者均可对请求进行处理&#xff0c; 或将其传递给链上的下个处理者。 二、应用场景&#xff1a; 1.多条件流程判断&#xff1a;权限相关…...

SpringBoot雪花算法主键ID传到前端后精度丢失问题的解决

Java后端Long类型的范围 -263~263&#xff0c;即&#xff1a;-9223372036854775808~9223372036854775807&#xff0c;它是19位的。 这个数字可以通过方法获得&#xff1a;Long.MAX_VALUE、Long_MIN_VALUE。 前端JS的数字类型的范围 -253~253&#xff0c;即&#xff1a;-9007…...

vue使用elementUI的upload上传文件封装

这篇文章的目的 将文件上传的方法封装一下&#xff0c;供大家统一调用, 话不多说&#xff0c;直接上代码 upload 核心参数说明 action 上传的地址accept 接受上传的文件类型multiple 是否开启多文件上传模式limit 限制上传个数fileList 文件列表disabled 是否禁用 upload 核心方…...

cenos自动启动tomcat

首先创建一个脚本 关闭tomcat 等待2分钟 启动tomcat 并且把日志输出在 /usr/local/tomcat/tomcatchognqi.log #!/bin/bashexport JAVA_HOME/usr/local/jdk/jdk1.8.0_211 export JRE_HOME$JAVA_HOME/jre# 日志文件路径和文件名 LOG_FILE"/usr/local/tomcat/tomcatchognqi.…...

OSI模型与数据的封装

1、OSI模型 上层|| 七层模型 四层模型|| 应用层| 表示层 应用层 http/ftp/ssh/ftps| 会话层 -----------------------------------------------------------------------| 传输层 传输层 tcp/udp ------------------------------…...

【李沐深度学习笔记】数据操作

本课观看地址 数据操作p1 N维数组样例 N维数组是机器学习和神经网络的主要数据结构 1-d向量就是样本的各特征抽象成一个向量&#xff1b;2-d矩阵的每一行是一个样本&#xff0c;每一行都是一个样本的特征向量 3-d可以表示RGB图片&#xff0c;RGB图像是一个三维数组&#xff…...

【蓝桥杯选拔赛真题61】Scratch小猫照镜子 少儿编程scratch图形化编程 蓝桥杯选拔赛真题解析

目录 scratch小猫照镜子 一、题目要求 编程实现 二、案例分析 1、角色分析...

vue3将页面导出成PDF文件(完美解决图片、表格内容分割问题)

vue3将页面导出成PDF文件&#xff08;完美解决图片、表格内容分割问题&#xff09; 1、安装依赖2、在utils中创建htmlToPDF.js文件3、在vue中引入并使用 1、安装依赖 npm install --save html2canvas // 页面转图片 npm install jspdf --save // 图片转pdf2、在utils中创建h…...

基于算法竞赛的c++编程(28)结构体的进阶应用

结构体的嵌套与复杂数据组织 在C中&#xff0c;结构体可以嵌套使用&#xff0c;形成更复杂的数据结构。例如&#xff0c;可以通过嵌套结构体描述多层级数据关系&#xff1a; struct Address {string city;string street;int zipCode; };struct Employee {string name;int id;…...

C++_核心编程_多态案例二-制作饮品

#include <iostream> #include <string> using namespace std;/*制作饮品的大致流程为&#xff1a;煮水 - 冲泡 - 倒入杯中 - 加入辅料 利用多态技术实现本案例&#xff0c;提供抽象制作饮品基类&#xff0c;提供子类制作咖啡和茶叶*//*基类*/ class AbstractDr…...

IoT/HCIP实验-3/LiteOS操作系统内核实验(任务、内存、信号量、CMSIS..)

文章目录 概述HelloWorld 工程C/C配置编译器主配置Makefile脚本烧录器主配置运行结果程序调用栈 任务管理实验实验结果osal 系统适配层osal_task_create 其他实验实验源码内存管理实验互斥锁实验信号量实验 CMISIS接口实验还是得JlINKCMSIS 简介LiteOS->CMSIS任务间消息交互…...

docker 部署发现spring.profiles.active 问题

报错&#xff1a; org.springframework.boot.context.config.InvalidConfigDataPropertyException: Property spring.profiles.active imported from location class path resource [application-test.yml] is invalid in a profile specific resource [origin: class path re…...

Springboot社区养老保险系统小程序

一、前言 随着我国经济迅速发展&#xff0c;人们对手机的需求越来越大&#xff0c;各种手机软件也都在被广泛应用&#xff0c;但是对于手机进行数据信息管理&#xff0c;对于手机的各种软件也是备受用户的喜爱&#xff0c;社区养老保险系统小程序被用户普遍使用&#xff0c;为方…...

【网络安全】开源系统getshell漏洞挖掘

审计过程&#xff1a; 在入口文件admin/index.php中&#xff1a; 用户可以通过m,c,a等参数控制加载的文件和方法&#xff0c;在app/system/entrance.php中存在重点代码&#xff1a; 当M_TYPE system并且M_MODULE include时&#xff0c;会设置常量PATH_OWN_FILE为PATH_APP.M_T…...

【Android】Android 开发 ADB 常用指令

查看当前连接的设备 adb devices 连接设备 adb connect 设备IP 断开已连接的设备 adb disconnect 设备IP 安装应用 adb install 安装包的路径 卸载应用 adb uninstall 应用包名 查看已安装的应用包名 adb shell pm list packages 查看已安装的第三方应用包名 adb shell pm list…...

深度剖析 DeepSeek 开源模型部署与应用:策略、权衡与未来走向

在人工智能技术呈指数级发展的当下&#xff0c;大模型已然成为推动各行业变革的核心驱动力。DeepSeek 开源模型以其卓越的性能和灵活的开源特性&#xff0c;吸引了众多企业与开发者的目光。如何高效且合理地部署与运用 DeepSeek 模型&#xff0c;成为释放其巨大潜力的关键所在&…...

多元隐函数 偏导公式

我们来推导隐函数 z z ( x , y ) z z(x, y) zz(x,y) 的偏导公式&#xff0c;给定一个隐函数关系&#xff1a; F ( x , y , z ( x , y ) ) 0 F(x, y, z(x, y)) 0 F(x,y,z(x,y))0 &#x1f9e0; 目标&#xff1a; 求 ∂ z ∂ x \frac{\partial z}{\partial x} ∂x∂z​、 …...

CMS内容管理系统的设计与实现:多站点模式的实现

在一套内容管理系统中&#xff0c;其实有很多站点&#xff0c;比如企业门户网站&#xff0c;产品手册&#xff0c;知识帮助手册等&#xff0c;因此会需要多个站点&#xff0c;甚至PC、mobile、ipad各有一个站点。 每个站点关联的有站点所在目录及所属的域名。 一、站点表设计…...