// index.js // 获取应用实例 let index = 0, // 当前点击图片的index items = [], // 图片数组信息 itemId = 1, // 图片id,用于识别点击图片 fliter = 'init', // 默认过滤类型(原图) shape = 'init'; // 默认形状(原图) const hCw = 1.62; // 图片宽高比 const canvasPre = 1; // 展示的canvas占mask的百分比 const maskCanvas = wx.createCanvasContext('maskCanvas', this); // 创建 canvas 的绘图上下文 CanvasContext 对象 const util = require('../../utils/util.js'); var urlPath = require('../../config.js'); Page({ /** * 页面的初始数据 */ data: { isLogin: false, //是否授权 funBox: true, //功能框 itemList: [], showBtn: false, //按钮 showBox: false, //弹框 // titlelist: ['脸谱', '背景', '按钮', '川剧', '人物', '文字', '装饰'], titlelist: [], titleIndex: '-1', allList: [ '../../img/background/1.png', ], allIndex: '-1', isOk: false, isNo: false, closeTime: null, titleVal:'', showTitle:false, times:0 }, chooseTitle(e) { let that = this; if (that.data.titleIndex != e.currentTarget.dataset.index) { that.setData({ allIndex: '-1' }) } this.setData({ titleIndex: e.currentTarget.dataset.index, showBtn: true }) this.getBottleWidgets(that.data.titlelist[that.data.titleIndex].id); }, chooseImg(e) { let that = this; that.setData({ allIndex: e.currentTarget.dataset.index, showBox: false, showBtn: false }) if (that.data.titleIndex == 0) { wx.getStorage({ //获取本地缓存 key: that.data.allList[that.data.allIndex].img, success: function(res) { console.log(res); that.setBackGroundImg({ url: res.data }); }, }) } else { wx.getStorage({ //获取本地缓存 key: that.data.allList[that.data.allIndex].img, success: function(res) { that.setDropItem({ url: res.data }); }, }) } }, titleInput(e){ this.setData({ titleVal:e.detail.value }) }, submit(){ if(this.data.titleVal==''){ wx.showToast({title:'请输入标题',icon:'none'}) } else { wx.showToast({title:'设置标题成功',icon:'none'}) this.setData({showTitle:false}) } }, onShow: function() { if (typeof this.getTabBar === 'function' && this.getTabBar()) { this.getTabBar().setData({ selected: 0 }) } }, /** * 生命周期函数--监听页面加载 */ onLoad: function(options) { items = this.data.itemList; wx.getSystemInfo({ // 获取系统信息 success: sysData => { this.sysData = sysData; // 设置画布宽高,this.sysData.windowWidth为屏幕的宽度 this.setData({ canvasWidth: this.sysData.windowWidth * canvasPre, // 如果觉得不清晰的话,可以把所有组件、宽高放大一倍 canvasHeight: this.sysData.windowWidth * canvasPre * hCw, backGroundWidth: this.sysData.windowWidth, backGroundHeight: this.sysData.screenHeight }) } }) this.setBackGroundImg({ url: '../../img/background/1.png' }); this.getBottleCategories(); }, // 上传图片 uploadImg() { let that = this; wx.chooseImage({ count: 1, sizeType: ['original', 'compressed'], sourceType: ['album', 'camera'], success(res) { // tempFilePath可以作为img标签的src属性显示图片 that.setDropItem({ url: res.tempFilePaths[0] }); } }) }, // 设置背景图片 setBackGroundImg(imgData) { let data = {}; // 存储图片信息 // 获取图片信息,网络图片需先配置download域名才能生效 wx.getImageInfo({ src: imgData.url, success: res => { // 初始化数据 let maxWidth = this.data.backGroundWidth, maxHeight = this.data.backGroundHeight; // 设置最大宽高 if (res.width > maxWidth || res.height > maxHeight) { // 原图宽或高大于最大值就执行 if (res.width / res.height > maxWidth / maxHeight) { // 判断比例使用最大值的宽或高作为基数计算 data.width = maxWidth; data.height = Math.round(maxWidth * (res.height / res.width)); } else { data.height = maxHeight; data.width = Math.round(maxHeight * (res.width / res.height)); } } data.image = imgData.url; // 显示地址 data.initImage = imgData.url; // 原始地址 // data.id = ++itemId; // id data.id = 2; // id data.top = 0; // top定位 data.left = 0; // left定位 // 圆心坐标 data.x = data.left + data.width / 2; data.y = data.top + data.height / 2; data.scale = 1; // scale缩放 data.rotate = 1; // 旋转角度 data.active = false; // 选中状态 data.angle = 0; items[0] = data; // 每增加一张图片数据增加一条信息 this.setData({ itemList: items }) } }) }, // 设置图片的信息 setDropItem(imgData) { let data = {}; // 存储图片信息 // 获取图片信息,网络图片需先配置download域名才能生效 wx.getImageInfo({ src: imgData.url, success: res => { // 初始化数据 let maxWidth = 150, maxHeight = 150; // 设置最大宽高 if (res.width > maxWidth || res.height > maxHeight) { // 原图宽或高大于最大值就执行 if (res.width / res.height > maxWidth / maxHeight) { // 判断比例使用最大值的宽或高作为基数计算 data.width = maxWidth; data.height = Math.round(maxWidth * (res.height / res.width)); } else { data.height = maxHeight; data.width = Math.round(maxHeight * (res.width / res.height)); } } data.image = imgData.url; // 显示地址 data.initImage = imgData.url; // 原始地址 data.id = ++itemId + 1; // id data.top = 10; // top定位 data.left = 10; // left定位 // 圆心坐标 data.x = data.left + data.width / 2; data.y = data.top + data.height / 2; data.scale = 1; // scale缩放 data.rotate = 1; // 旋转角度 data.active = false; // 选中状态 data.angle = 0; console.log(data, 123); items[items.length] = data; // 每增加一张图片数据增加一条信息 this.setData({ itemList: items }) } }) }, // 点击图片 WraptouchStart: function(e) { if (e.currentTarget.dataset.id != 2) { // 循环图片数组获取点击的图片信息 for (let i = 0; i < items.length; i++) { items[i].active = false; if (e.currentTarget.dataset.id == items[i].id) { index = i; items[index].active = true; } } this.setData({ itemList: items }) // 获取点击的坐标值 items[index].lx = e.touches[0].clientX; items[index].ly = e.touches[0].clientY; } this.setData({ showBox: false, funBox: false }) }, // 拖动图片 WraptouchMove(e) { if (e.currentTarget.dataset.id != 2) { items[index]._lx = e.touches[0].clientX; items[index]._ly = e.touches[0].clientY; items[index].left += items[index]._lx - items[index].lx; items[index].top += items[index]._ly - items[index].ly; items[index].x += items[index]._lx - items[index].lx; items[index].y += items[index]._ly - items[index].ly; items[index].lx = e.touches[0].clientX; items[index].ly = e.touches[0].clientY; this.setData({ itemList: items, showBtn: true, funBox: false }) } }, // 放开图片 WraptouchEnd() { this.synthesis(); // 调用合成图方法 clearTimeout(this.data.closeTime); this.data.closeTime = setTimeout(() => { this.setData({ showBtn: false, funBox: true }) }, 1000) }, // 点击伸缩图标 oTouchStart(e) { //找到点击的那个图片对象,并记录 for (let i = 0; i < items.length; i++) { items[i].active = false; if (e.currentTarget.dataset.id == items[i].id) { index = i; items[index].active = true; } } //获取作为移动前角度的坐标 items[index].tx = e.touches[0].clientX; items[index].ty = e.touches[0].clientY; //移动前的角度 items[index].anglePre = this.countDeg(items[index].x, items[index].y, items[index].tx, items[index].ty); //获取图片半径 items[index].r = this.getDistancs(items[index].x, items[index].y, items[index].left, items[index].top); }, oTouchMove: function(e) { //记录移动后的位置 items[index]._tx = e.touches[0].clientX; items[index]._ty = e.touches[0].clientY; //移动的点到圆心的距离 items[index].disPtoO = this.getDistancs(items[index].x, items[index].y, items[index]._tx, items[ index]._ty - 10) items[index].scale = items[index].disPtoO / items[index].r; //移动后位置的角度 items[index].angleNext = this.countDeg(items[index].x, items[index].y, items[index]._tx, items[ index]._ty) //角度差 items[index].new_rotate = items[index].angleNext - items[index].anglePre; //叠加的角度差 items[index].rotate += items[index].new_rotate; items[index].angle = items[index].rotate; //赋值 //用过移动后的坐标赋值为移动前坐标 items[index].tx = e.touches[0].clientX; items[index].ty = e.touches[0].clientY; items[index].anglePre = this.countDeg(items[index].x, items[index].y, items[index].tx, items[index] .ty) //赋值setData渲染 this.setData({ itemList: items }) }, // 计算坐标点到圆心的距离 getDistancs(cx, cy, pointer_x, pointer_y) { this.setData({ showBtn: true, funBox: false }) var ox = pointer_x - cx; var oy = pointer_y - cy; return Math.sqrt( ox * ox + oy * oy ); }, /* *参数cx和cy为图片圆心坐标 *参数pointer_x和pointer_y为手点击的坐标 *返回值为手点击的坐标到圆心的角度 */ countDeg: function(cx, cy, pointer_x, pointer_y) { var ox = pointer_x - cx; var oy = pointer_y - cy; var to = Math.abs(ox / oy); var angle = Math.atan(to) / (2 * Math.PI) * 360; if (ox < 0 && oy < 0) //相对在左上角,第四象限,js中坐标系是从左上角开始的,这里的象限是正常坐标系 { angle = -angle; } else if (ox <= 0 && oy >= 0) //左下角,3象限 { angle = -(180 - angle) } else if (ox > 0 && oy < 0) //右上角,1象限 { angle = angle; } else if (ox > 0 && oy > 0) //右下角,2象限 { angle = 180 - angle; } return angle; }, // 删除 deleteItem: function(e) { let newList = []; for (let i = 0; i < items.length; i++) { if (e.currentTarget.dataset.id != items[i].id) { newList.push(items[i]) } } if (newList.length > 1) { //大于0背景图可被删除,大于1背景图不能被删除 newList[newList.length - 1].active = true; // 剩下图片组最后一个选中 } items = newList; this.setData({ itemList: items }) }, // 打开遮罩层 openMask() { this.synthesis(); this.setData({ showCanvas: true, showTitle:true }) }, downLoadImg(netUrl, storageKeyUrl) { wx.getImageInfo({ src: netUrl, //请求的网络图片路径 success: function(res) { //请求成功后将会生成一个本地路径即res.path,然后将该路径缓存到storageKeyUrl关键字中 wx.setStorage({ key: storageKeyUrl, data: res.path, }); } }) }, synthesis() { // 合成图片 maskCanvas.save(); maskCanvas.beginPath(); // 画背景色(白色) maskCanvas.setFillStyle('#fff'); maskCanvas.fillRect(0, 0, this.data.canvasWidth, this.data.backGroundHeight); items.forEach((currentValue, index) => { maskCanvas.save(); maskCanvas.translate(0, 0); maskCanvas.beginPath(); maskCanvas.translate(currentValue.x, currentValue.y); // 圆心坐标 maskCanvas.rotate(currentValue.angle * Math.PI / 180); maskCanvas.translate(-(currentValue.width * currentValue.scale / 2), -(currentValue.height * currentValue.scale / 2)) maskCanvas.drawImage(currentValue.image, 0, 0, currentValue.width * currentValue.scale, currentValue.height * currentValue.scale); maskCanvas.restore(); }) // reserve 参数为 false,则在本次调用绘制之前 native 层会先清空画布再继续绘制 maskCanvas.draw(false, (e) => { wx.canvasToTempFilePath({ canvasId: 'maskCanvas', success: res => { this.setData({ canvasTemImg: res.tempFilePath }) } }, this); }) }, // 关闭遮罩层 disappearCanvas() { this.setData({ showCanvas: false }) }, // 保存图片到系统相册 saveImg: function() { if (wx.getStorageSync('token')) { wx.saveImageToPhotosAlbum({ filePath: this.data.canvasTemImg, success: res => { wx.showToast({ title: '保存成功', icon: "success" }) this.saveImgEv(this.data.canvasTemImg); }, fail: res => { wx.showModal({ title: '提示', content: '保存失败,请确保相册权限已打开', success: (e) => { if (e.confirm) { wx.openSetting({ success: settingdata => { if (settingdata.authSetting['scope.writePhotosAlbum']) { console.log('获取权限成功,给出再次点击图片保存到相册的提示。') } else { console.log('获取权限失败,给出不给权限就无法正常使用的提示') } }, fail: error => { console.log(error) } }) } } }) } }) } else { this.setData({ isLogin: true }) } }, // 保存图片接口 saveImgEv(imgSrc) { wx.uploadFile({ url: urlPath.composeBottle, filePath: imgSrc, name: 'image', formData: { 'name': this.data.titleVal }, header: { "Content-Type": "multipart/form-data", 'token': wx.getStorageSync('token') }, success: (data)=> { if(data.statusCode==200){ wx.showToast({ title:'保存成功', icon:'none' }) this.setData({ showCanvas:false }) } }, fail: function(data) { console.log(data); } }) }, // 分享图片 shareImg() { if (wx.getStorageSync('token')) { if(this.data.times==0){ wx.showToast({ title:'正在调起分享', duration:5000 }) this.setData({ times:this.data.times++ }) wx.uploadFile({ url: urlPath.composeBottle, filePath: this.data.canvasTemImg, name: 'image', formData: { 'name': this.data.titleVal }, header: { "Content-Type": "multipart/form-data", 'Content-Type': 'application/json', 'token': wx.getStorageSync('token') }, success: (res)=> { let newRes = JSON.parse(res.data); if(newRes.code==0){ wx.downloadFile({ url: 'https://fenggu.scdxtc.cn' + newRes.data.src, success: (res) => { wx.showShareImageMenu({ path: res.tempFilePath, success:(res)=>{ this.shareEv(newRes.data.id); } }) } }) } }, fail: function(data) { console.log(data); } }) } } else { this.setData({ isLogin: true }) } }, // 分享事件 shareEv(id) { wx.request({ url: urlPath.publishMyBottle, data: {id: id}, header: {'token': wx.getStorageSync('token')}, method: 'post', success: (res) => { if (res.data.code == 0) { wx.showToast({title: '分享作品成功'}) } } }); }, // 关闭授权 chooseBtn(e) { let loginIndex = e.currentTarget.dataset.index; this.setData({ isOk: false, isNo: false }) loginIndex == 1 ? this.setData({ isOk: true }) : this.setData({ isNo: true }) }, // 确认授权 shouq(e) { wx.getUserProfile({ //获取用户昵称 desc: '用于完善会员资料', success: (res) => { this.setData({ userInfo: res.userInfo, isLogin: false }) wx.showToast({ title: '授权成功', icon: 'none' }) this.setData({ isOk: false }) wx.login({ //调用授权登录 success: res => { wx.request({ url: urlPath.getopenid, method: 'post', data: { code: res.code, wx_name: this.data.userInfo.nickName, avater: this.data.userInfo.avatarUrl, }, success(res) { console.log(res, 1234); if (res.data.code == 0) { wx.setStorageSync('token', res.data.data .token); wx.setStorageSync('openid', res.data.data .openid); wx.setStorageSync('user', res.data.data .user); } } }); } }) }, fail: (res) => { wx.showToast({ title: '授权失败', icon: 'none' }) this.setData({ isOk: false }) } }) }, getBottleCategories() { wx.request({ url: urlPath.getBottleCategories, success: (res) => { if (res.data.code == 0) { if (res.data.data.length) { this.setData({ titlelist: res.data.data }) } } } }); }, getBottleWidgets(id) { wx.request({ url: urlPath.getBottleWidgets, method: 'post', data: { category_id: id, size: 60 }, success: (res) => { if (res.data.code == 0) { if (res.data.data.length) { let newArr = []; res.data.data.forEach(item => { let url = 'https://fenggu.scdxtc.cn' + item.img; this.downLoadImg(url, 'https://fenggu.scdxtc.cn' + item.img); let obj = { id: item.id, name: item.name, img: 'https://fenggu.scdxtc.cn' + item.img } newArr.push(obj) }) this.setData({ allList: newArr, showBox: true }) } else { wx.showToast({ title:'无内容', icon:'none' }) this.setData({ showBox: false }) } } } }); }, checkWorkEv() { wx.navigateTo({ url: '/pages/works/works' }) } })