@ -1,4 +1,19 @@
|
|||||||
使用说明
|
# 功能介绍
|
||||||
========
|
|
||||||
|
|
||||||
使用代码前,请先修改 `app.js` 里面的域名配置。
|
- 学员可以在点击右下角”加入课堂”选择课程加入,教员可以在“加入课堂中”新建课程
|
||||||
|
|
||||||
|
- 长按相应课程可以退出学习
|
||||||
|
|
||||||
|
- 进入课堂界面会显示在位,头像为彩色,若退出课堂界面则会显示灰色头像
|
||||||
|
|
||||||
|
- 教员在课堂界面中可以直观地看到学员在位情况,可以选择学员让其起立回答问题,并且对学员可以进行加分、减分操作
|
||||||
|
|
||||||
|
- 学员可以收到教员让其起立提问、回答的提示,还可以点击“我要提问、回答”
|
||||||
|
|
||||||
|
- 在课堂界面右下角进入“更多”可以查看本课堂的课程文件资源
|
||||||
|
|
||||||
|
- 教员可以在课程的设置界面中更新课程的名称,还可以将学员移除本课程的学习
|
||||||
|
|
||||||
|
## 其他
|
||||||
|
|
||||||
|
- 用户可以在设置中更改姓名、用户名
|
@ -1,28 +1,38 @@
|
|||||||
{
|
{
|
||||||
"pages": [
|
"pages": [
|
||||||
|
|
||||||
"pages/classes/classes",
|
"pages/classes/classes",
|
||||||
"pages/changeuser/changeuser",
|
"pages/changeuser/changeuser",
|
||||||
"pages/index/index",
|
|
||||||
"pages/config/config",
|
|
||||||
"pages/https/https",
|
|
||||||
"pages/session/session",
|
|
||||||
"pages/websocket/websocket",
|
|
||||||
"pages/game/game",
|
|
||||||
"pages/shouquan/shouquan",
|
|
||||||
"pages/outside/outside",
|
|
||||||
"pages/setting/setting",
|
"pages/setting/setting",
|
||||||
"pages/user/user",
|
"pages/user/user",
|
||||||
"pages/addclass/addclass",
|
"pages/addclass/addclass",
|
||||||
"pages/classdetail/classdetail",
|
"pages/classdetail/classdetail",
|
||||||
"pages/classroom/classroom",
|
"pages/classroom/classroom",
|
||||||
"pages/classsetting/classsetting"
|
"pages/classsetting/classsetting",
|
||||||
|
"pages/about/about",
|
||||||
|
"pages/createclass/createclass"
|
||||||
],
|
],
|
||||||
"window": {
|
"window": {
|
||||||
"backgroundTextStyle": "light",
|
"backgroundTextStyle": "light",
|
||||||
"navigationBarBackgroundColor": "#fff",
|
"navigationBarBackgroundColor": "#f2f2f2",
|
||||||
"navigationBarTitleText": " ",
|
"navigationBarTitleText": "积分教室",
|
||||||
"navigationBarTextStyle": "black"
|
"navigationBarTextStyle": "black"
|
||||||
},
|
},
|
||||||
|
"tabBar": {
|
||||||
|
"selectedColor": "#00C7B7",
|
||||||
|
"list": [
|
||||||
|
{
|
||||||
|
"pagePath": "pages/classes/classes",
|
||||||
|
"text": "学习",
|
||||||
|
"iconPath": "images/tabbar-icon/tabbar_contact_default.png",
|
||||||
|
"selectedIconPath": "images/tabbar-icon/tabbar_contact_pressed.png"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"pagePath": "pages/setting/setting",
|
||||||
|
"iconPath": "images/tabbar-icon/tabbar_settings_default.png",
|
||||||
|
"selectedIconPath": "images/tabbar-icon/tabbar_settings_pressed.png",
|
||||||
|
"text": "设置"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
"sitemapLocation": "sitemap.json"
|
"sitemapLocation": "sitemap.json"
|
||||||
}
|
}
|
Before Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 40 KiB |
Before Width: | Height: | Size: 73 KiB |
After Width: | Height: | Size: 10 KiB |
Before Width: | Height: | Size: 1018 B |
After Width: | Height: | Size: 21 KiB |
After Width: | Height: | Size: 19 KiB |
After Width: | Height: | Size: 15 KiB |
After Width: | Height: | Size: 416 B |
After Width: | Height: | Size: 222 B |
After Width: | Height: | Size: 943 B |
After Width: | Height: | Size: 773 B |
After Width: | Height: | Size: 1.2 KiB |
After Width: | Height: | Size: 1.1 KiB |
After Width: | Height: | Size: 719 B |
After Width: | Height: | Size: 604 B |
Before Width: | Height: | Size: 28 KiB |
@ -1,17 +1,6 @@
|
|||||||
// pages/shouquan.js
|
// pages/about/about.js
|
||||||
Page({
|
Page({
|
||||||
|
|
||||||
bindGetUserInfo: function (e) {
|
|
||||||
var that = this;
|
|
||||||
//此处授权得到userInfo
|
|
||||||
console.log(e.detail.userInfo);
|
|
||||||
//接下来写业务代码
|
|
||||||
|
|
||||||
//最后,记得返回刚才的页面
|
|
||||||
wx.navigateBack({
|
|
||||||
delta: 1
|
|
||||||
})
|
|
||||||
},
|
|
||||||
/**
|
/**
|
||||||
* 页面的初始数据
|
* 页面的初始数据
|
||||||
*/
|
*/
|
@ -0,0 +1,24 @@
|
|||||||
|
<view class="container">
|
||||||
|
<text>
|
||||||
|
# 功能介绍
|
||||||
|
|
||||||
|
- 学员可以在点击右下角”加入课堂”选择课程加入,教员可以在“加入课堂中”新建课程
|
||||||
|
|
||||||
|
- 长按相应课程可以退出学习
|
||||||
|
|
||||||
|
- 进入课堂界面会显示在位,头像为彩色,若退出课堂界面则会显示灰色头像
|
||||||
|
|
||||||
|
- 教员在课堂界面中可以直观地看到学员在位情况,可以选择学员让其起立回答问题,并且对学员可以进行加分、减分操作
|
||||||
|
|
||||||
|
- 学员可以收到教员让其起立提问、回答的提示,还可以点击“我要提问、回答”
|
||||||
|
|
||||||
|
- 在课堂界面右下角进入“更多”可以查看本课堂的课程文件资源
|
||||||
|
|
||||||
|
- 教员可以在课程的设置界面中更新课程的名称,还可以将学员移除本课程的学习
|
||||||
|
|
||||||
|
## 其他
|
||||||
|
|
||||||
|
- 用户可以在设置中更改姓名、用户名
|
||||||
|
|
||||||
|
</text>
|
||||||
|
</view>
|
@ -0,0 +1 @@
|
|||||||
|
/* pages/about/about.wxss */
|
@ -1,24 +0,0 @@
|
|||||||
const app = getApp();
|
|
||||||
const config = app.config;
|
|
||||||
const lab = require('../../lib/lab');
|
|
||||||
|
|
||||||
const done = config.host != '<请配置访问域名>';
|
|
||||||
|
|
||||||
|
|
||||||
Page({
|
|
||||||
data: {
|
|
||||||
done,
|
|
||||||
status: done ? 'success' : 'waiting',
|
|
||||||
host: config.host,
|
|
||||||
hintLine1: done ? '域名已配置' : '请修改小程序源码 app.js',
|
|
||||||
hintLine2: done ? '小程序实验将使用下面域名进行' : '配置小程序使用的服务器域名'
|
|
||||||
},
|
|
||||||
goBack() {
|
|
||||||
wx.navigateBack();
|
|
||||||
},
|
|
||||||
onShow() {
|
|
||||||
if (done) {
|
|
||||||
lab.finish('config');
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
@ -1 +0,0 @@
|
|||||||
{}
|
|
@ -1,13 +0,0 @@
|
|||||||
<view class="lab https">
|
|
||||||
<view class="status">
|
|
||||||
<icon type="{{status}}" size="70" />
|
|
||||||
</view>
|
|
||||||
<view class="hint">
|
|
||||||
<view class="line">{{hintLine1}}</view>
|
|
||||||
<view class="line">{{hintLine2}}</view>
|
|
||||||
</view>
|
|
||||||
<view class="hint">
|
|
||||||
<view class="line">{{host}}</view>
|
|
||||||
</view>
|
|
||||||
<view class="command"></view>
|
|
||||||
</view>
|
|
@ -1 +0,0 @@
|
|||||||
/* pages/config/config.wxss */
|
|
@ -0,0 +1,108 @@
|
|||||||
|
// pages/createclass/createclass.js
|
||||||
|
const AV = require("../../lib/av-live-query-weapp-min")
|
||||||
|
const Presence = require("../../model/presence")
|
||||||
|
const Class = require("../../model/class")
|
||||||
|
|
||||||
|
|
||||||
|
Page({
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 页面的初始数据
|
||||||
|
*/
|
||||||
|
data: {
|
||||||
|
new_classname: '',
|
||||||
|
new_class_teacher_username: '',
|
||||||
|
},
|
||||||
|
updateName: function ({ detail: { value } }) {
|
||||||
|
this.setData({ new_classname: value });
|
||||||
|
},
|
||||||
|
create_class: function (event) {
|
||||||
|
let { new_classname } = this.data;
|
||||||
|
new_classname = new_classname.trim();
|
||||||
|
if (new_classname == "") {
|
||||||
|
wx.showToast({
|
||||||
|
title: "课程名称不能为空",
|
||||||
|
icon: "none"
|
||||||
|
})
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
class_ = new Class({
|
||||||
|
name: new_classname,
|
||||||
|
teacher: AV.User.current()
|
||||||
|
})
|
||||||
|
wx.showLoading({
|
||||||
|
title: '请稍候',
|
||||||
|
})
|
||||||
|
class_.save().then(() => {
|
||||||
|
wx.hideLoading();
|
||||||
|
wx.showToast({
|
||||||
|
title: '创建成功,可在首页课程列表以教师身份进入课堂',
|
||||||
|
icon: "none",
|
||||||
|
duration: 4000
|
||||||
|
});
|
||||||
|
this.setData({ new_classname: "" });
|
||||||
|
},
|
||||||
|
() => {
|
||||||
|
wx.hideLoading();
|
||||||
|
wx.showToast({
|
||||||
|
title: '操作失败',
|
||||||
|
icon: "none"
|
||||||
|
});
|
||||||
|
});
|
||||||
|
},
|
||||||
|
/**
|
||||||
|
* 生命周期函数--监听页面加载
|
||||||
|
*/
|
||||||
|
onLoad: function (options) {
|
||||||
|
this.setData({ new_class_teacher_username: AV.User.current().get("username") });
|
||||||
|
},
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 生命周期函数--监听页面初次渲染完成
|
||||||
|
*/
|
||||||
|
onReady: function () {
|
||||||
|
|
||||||
|
},
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 生命周期函数--监听页面显示
|
||||||
|
*/
|
||||||
|
onShow: function () {
|
||||||
|
|
||||||
|
},
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 生命周期函数--监听页面隐藏
|
||||||
|
*/
|
||||||
|
onHide: function () {
|
||||||
|
|
||||||
|
},
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 生命周期函数--监听页面卸载
|
||||||
|
*/
|
||||||
|
onUnload: function () {
|
||||||
|
|
||||||
|
},
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 页面相关事件处理函数--监听用户下拉动作
|
||||||
|
*/
|
||||||
|
onPullDownRefresh: function () {
|
||||||
|
|
||||||
|
},
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 页面上拉触底事件的处理函数
|
||||||
|
*/
|
||||||
|
onReachBottom: function () {
|
||||||
|
|
||||||
|
},
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 用户点击右上角分享
|
||||||
|
*/
|
||||||
|
onShareAppMessage: function () {
|
||||||
|
|
||||||
|
}
|
||||||
|
})
|
@ -0,0 +1,13 @@
|
|||||||
|
<!--pages/createclass/createclass.wxml-->
|
||||||
|
<view class="container">
|
||||||
|
<text>创建我的课程</text>
|
||||||
|
<view class="flex-wrap input-wrap">
|
||||||
|
<text class="label">课程名称:</text>
|
||||||
|
<input value="{{new_classname}}" bindinput="updateName" id="name" class="info-input"/>
|
||||||
|
</view>
|
||||||
|
<view class="flex-wrap input-wrap">
|
||||||
|
<text class="label">教师用户名:</text>
|
||||||
|
<input value="{{new_class_teacher_username}}" id="teacher_name" class="info-input disabled" disabled="true"/>
|
||||||
|
</view>
|
||||||
|
<button bindtap="create_class">创建新课程</button>
|
||||||
|
</view>
|
@ -0,0 +1,30 @@
|
|||||||
|
|
||||||
|
.input-wrap {
|
||||||
|
background: #fff;
|
||||||
|
border-bottom: 1px solid #eee;
|
||||||
|
margin: 0 -12px;
|
||||||
|
padding: 0 12px;
|
||||||
|
height: 46px;
|
||||||
|
line-height: 46px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.info-input {
|
||||||
|
font-size: 18px;
|
||||||
|
line-height: 100%;
|
||||||
|
height: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
.disabled{
|
||||||
|
color: #999;
|
||||||
|
}
|
||||||
|
|
||||||
|
.label {
|
||||||
|
color: #999;
|
||||||
|
display: inline;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
button{
|
||||||
|
margin: 4px 26px;
|
||||||
|
font-size: 16px;
|
||||||
|
}
|
@ -1,253 +0,0 @@
|
|||||||
"use strict";
|
|
||||||
|
|
||||||
require('../../lib/regenerator-runtime');
|
|
||||||
|
|
||||||
const regeneratorRuntime = global.regeneratorRuntime;
|
|
||||||
|
|
||||||
// 引入 co 和 promisify 帮助我们进行异步处理
|
|
||||||
const co = require('../../lib/co');
|
|
||||||
const promisify = require('../../lib/promisify');
|
|
||||||
|
|
||||||
// 引入 Wafer 客户端 SDK 支持会话
|
|
||||||
const wafer = require('../../vendors/wafer-client-sdk/index');
|
|
||||||
|
|
||||||
// 简单的小程序 WebSocket 信道封装
|
|
||||||
const Tunnel = require('../../lib/tunnel');
|
|
||||||
|
|
||||||
// 登录接口转成返回 Promise 形式
|
|
||||||
const login = promisify(wafer.login);
|
|
||||||
|
|
||||||
// 获得小程序实例
|
|
||||||
const app = getApp();
|
|
||||||
|
|
||||||
// 用于记录实验成功
|
|
||||||
const lab = require('../../lib/lab');
|
|
||||||
|
|
||||||
// 设置会话登录地址
|
|
||||||
wafer.setLoginUrl(`https://${app.config.host}/login`);
|
|
||||||
|
|
||||||
// 文案
|
|
||||||
const WIN_TEXTS = ['很棒', '秒杀', '赢了', 'Winner', '胜利', '不要大意', '无敌啊'];
|
|
||||||
const LOSE_TEXTS = ['失误', '卧槽', '不可能', 'Loser', '行不行啊', '加油', '大侠再来'];
|
|
||||||
const EQ_TEXTS = ['平局', '平分秋色', '对方学你', '照镜子', '半斤八两', '换一个', '一样的'];
|
|
||||||
const pickText = texts => texts[Math.floor(texts.length * Math.random())];
|
|
||||||
|
|
||||||
// 定义页面
|
|
||||||
Page({
|
|
||||||
data: {
|
|
||||||
// 是否已经和服务器连接
|
|
||||||
connected: false,
|
|
||||||
|
|
||||||
// 游戏是否进行中
|
|
||||||
playing: false,
|
|
||||||
|
|
||||||
// 当前需要展示的游戏信息
|
|
||||||
gameInfo: "",
|
|
||||||
|
|
||||||
// 开始游戏按钮文本
|
|
||||||
startButtonText: "开始",
|
|
||||||
|
|
||||||
//「我」的信息,包括昵称、头像、分数、选择
|
|
||||||
myName: "",
|
|
||||||
myAvatar: null,
|
|
||||||
myScore: 0,
|
|
||||||
myStreak: 0,
|
|
||||||
myChoice: Math.floor(Math.random() * 10000) % 3 + 1,
|
|
||||||
|
|
||||||
//「你」的信息
|
|
||||||
youHere: false,
|
|
||||||
yourName: "",
|
|
||||||
yourAvatar: null,
|
|
||||||
yourScore: 0,
|
|
||||||
yourStreak: 0,
|
|
||||||
yourChoice: 1,
|
|
||||||
yourMove: 0,
|
|
||||||
|
|
||||||
// 取得胜利的是谁
|
|
||||||
win: null
|
|
||||||
},
|
|
||||||
|
|
||||||
// 页面显示后,开始连接
|
|
||||||
onShow: function() {
|
|
||||||
this.begin();
|
|
||||||
},
|
|
||||||
|
|
||||||
// 进行登录和链接,完成后开始启动游戏服务
|
|
||||||
begin: co.wrap(function *() {
|
|
||||||
try {
|
|
||||||
this.setData({ gameInfo: "正在登陆" });
|
|
||||||
yield login();
|
|
||||||
|
|
||||||
this.setData({ gameInfo: "正在连接"});
|
|
||||||
yield this.connect();
|
|
||||||
} catch (error) {
|
|
||||||
console.error('error on login or connect: ', error);
|
|
||||||
}
|
|
||||||
this.serve();
|
|
||||||
}),
|
|
||||||
|
|
||||||
// 链接到服务器后进行身份识别
|
|
||||||
connect: co.wrap(function *() {
|
|
||||||
|
|
||||||
const tunnel = this.tunnel = new Tunnel();
|
|
||||||
try {
|
|
||||||
yield tunnel.connect(`wss://${app.config.host}/game`, wafer.buildSessionHeader());
|
|
||||||
} catch (connectError) {
|
|
||||||
console.error({ connectError });
|
|
||||||
this.setData({ gameInfo: "连接错误" });
|
|
||||||
throw connectError;
|
|
||||||
}
|
|
||||||
tunnel.on('close', () => {
|
|
||||||
this.setData({
|
|
||||||
connected: false,
|
|
||||||
gameInfo: "连接已中断"
|
|
||||||
});
|
|
||||||
});
|
|
||||||
this.setData({
|
|
||||||
gameInfo: "准备",
|
|
||||||
connected: true,
|
|
||||||
gameState: 'connected'
|
|
||||||
});
|
|
||||||
return new Promise((resolve, reject) => {
|
|
||||||
// 10 秒后超时
|
|
||||||
const timeout = setTimeout(() => reject, 10000);
|
|
||||||
tunnel.on('id', ({ uname, uid, uavatar }) => {
|
|
||||||
this.uid = uid;
|
|
||||||
this.setData({
|
|
||||||
myName: uname,
|
|
||||||
myAvatar: uavatar
|
|
||||||
});
|
|
||||||
resolve(tunnel);
|
|
||||||
clearTimeout(timeout);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
}),
|
|
||||||
|
|
||||||
// 开始进行游戏服务
|
|
||||||
serve: co.wrap(function *() {
|
|
||||||
const tunnel = this.tunnel;
|
|
||||||
|
|
||||||
// 游戏开始,初始化对方信息,启动计时器
|
|
||||||
tunnel.on('start', packet => {
|
|
||||||
const you = packet.players.filter(user => user.uid !== this.uid).pop();
|
|
||||||
|
|
||||||
this.setData({
|
|
||||||
playing: false,
|
|
||||||
done: false,
|
|
||||||
finding: true,
|
|
||||||
gameInfo: '正在寻找玩伴...'
|
|
||||||
});
|
|
||||||
setTimeout(() => {
|
|
||||||
this.setData({
|
|
||||||
youHere: true,
|
|
||||||
yourName: you.uname,
|
|
||||||
yourAvatar: you.uavatar,
|
|
||||||
finding: false,
|
|
||||||
playing: true,
|
|
||||||
gameInfo: "准备"
|
|
||||||
});
|
|
||||||
}, 10);
|
|
||||||
|
|
||||||
let gameTime = packet.gameTime;
|
|
||||||
clearInterval(this.countdownId);
|
|
||||||
this.countdownId = setInterval(() => {
|
|
||||||
if (gameTime > 0) {
|
|
||||||
this.setData({ gameInfo: --gameTime });
|
|
||||||
} else {
|
|
||||||
clearInterval(this.countdownId);
|
|
||||||
}
|
|
||||||
}, 1000);
|
|
||||||
|
|
||||||
this.tunnel.emit('choice', { choice: this.data.myChoice });
|
|
||||||
});
|
|
||||||
|
|
||||||
// 对方有动静的时候,触发提醒
|
|
||||||
let movementTimer = 0;
|
|
||||||
const movementTimeout = 300;
|
|
||||||
tunnel.on('movement', packet => {
|
|
||||||
const lastMove = this.lastMove;
|
|
||||||
|
|
||||||
this.setData({ yourMove: lastMove == 1 ? 2 : 1 });
|
|
||||||
|
|
||||||
clearTimeout(movementTimer);
|
|
||||||
movementTimer = setTimeout(() => {
|
|
||||||
this.lastMove = this.data.yourMove;
|
|
||||||
this.setData({ yourMove: 0 });
|
|
||||||
}, 300);
|
|
||||||
});
|
|
||||||
|
|
||||||
// 服务器通知结果
|
|
||||||
tunnel.on('result', packet => {
|
|
||||||
|
|
||||||
// 清除计时器
|
|
||||||
clearInterval(this.countdownId);
|
|
||||||
|
|
||||||
// 双方结果
|
|
||||||
const myResult = packet.result.find(x => x.uid == this.uid);
|
|
||||||
const yourResult = packet.result.find(x => x.uid != this.uid);
|
|
||||||
|
|
||||||
// 本局结果
|
|
||||||
let gameInfo, win = 'nobody';
|
|
||||||
|
|
||||||
if (myResult.roundScore == 0 && yourResult.roundScore == 0) {
|
|
||||||
gameInfo = pickText(EQ_TEXTS);
|
|
||||||
}
|
|
||||||
else if (myResult.roundScore > 0) {
|
|
||||||
gameInfo = pickText(WIN_TEXTS);
|
|
||||||
win = 'me';
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
gameInfo = pickText(LOSE_TEXTS);
|
|
||||||
win = 'you'
|
|
||||||
}
|
|
||||||
|
|
||||||
// 更新到视图
|
|
||||||
this.setData({
|
|
||||||
gameInfo,
|
|
||||||
myScore: myResult.totalScore,
|
|
||||||
myStreak: myResult.winStreak,
|
|
||||||
yourChoice: yourResult.choice,
|
|
||||||
yourScore: yourResult.totalScore,
|
|
||||||
yourStreak: yourResult.winStreak,
|
|
||||||
gameState: 'finish',
|
|
||||||
win,
|
|
||||||
startButtonText: win == 'you' ? "不服" : "再来",
|
|
||||||
done: true
|
|
||||||
});
|
|
||||||
|
|
||||||
lab.finish('game');
|
|
||||||
setTimeout(() => this.setData({ playing: false }), 1000);
|
|
||||||
});
|
|
||||||
}),
|
|
||||||
|
|
||||||
requestComputer() {
|
|
||||||
if (this.tunnel) {
|
|
||||||
this.tunnel.emit('requestComputer');
|
|
||||||
}
|
|
||||||
},
|
|
||||||
|
|
||||||
// 点击开始游戏按钮,发送加入游戏请求
|
|
||||||
startGame: co.wrap(function *() {
|
|
||||||
if (this.data.playing) return;
|
|
||||||
if (!this.data.connected) return;
|
|
||||||
|
|
||||||
this.setData({
|
|
||||||
playing: false,
|
|
||||||
done: false,
|
|
||||||
finding: true,
|
|
||||||
gameInfo: '正在寻找玩伴...'
|
|
||||||
});
|
|
||||||
this.tunnel.emit('join');
|
|
||||||
}),
|
|
||||||
|
|
||||||
// 点击手势,更新选择是石头、剪刀还是布
|
|
||||||
switchChoice(e) {
|
|
||||||
if (!this.data.playing) return;
|
|
||||||
let myChoice = this.data.myChoice + 1;
|
|
||||||
if (myChoice == 4) {
|
|
||||||
myChoice = 1;
|
|
||||||
}
|
|
||||||
this.setData({ myChoice });
|
|
||||||
this.tunnel.emit('choice', { choice: myChoice });
|
|
||||||
}
|
|
||||||
});
|
|
@ -1 +0,0 @@
|
|||||||
{}
|
|
@ -1,33 +0,0 @@
|
|||||||
<view class="root {{connected && 'connected'}} {{finding && 'finding'}} {{playing && 'playing'}} {{done && 'done'}}">
|
|
||||||
<view class="my-side">
|
|
||||||
<image class="avatar" src="{{myAvatar}}" mode="aspectFill" />
|
|
||||||
|
|
||||||
<image class="hand {{win == 'me' && 'win'}}" src="../../images/{{myChoice}}.png" bindtap="switchChoice"></image>
|
|
||||||
|
|
||||||
<text class="score">
|
|
||||||
{{myName}}
|
|
||||||
得分 {{myScore}}
|
|
||||||
</text>
|
|
||||||
<text class="streak">
|
|
||||||
连胜 {{myStreak}}
|
|
||||||
</text>
|
|
||||||
</view>
|
|
||||||
<view class="your-side {{youHere && 'here'}} {{yourMove && 'move-' + yourMove}}">
|
|
||||||
<image class="avatar" src="{{yourAvatar}}" mode="aspectFill" />
|
|
||||||
|
|
||||||
<image class="hand {{win == 'you' && 'win'}}" src="../../images/{{yourChoice}}.png"></image>
|
|
||||||
|
|
||||||
<text class="score">
|
|
||||||
{{yourName}}
|
|
||||||
得分 {{yourScore}}
|
|
||||||
</text>
|
|
||||||
<text class="streak">
|
|
||||||
连胜 {{yourStreak}}
|
|
||||||
</text>
|
|
||||||
</view>
|
|
||||||
|
|
||||||
<view class="game-info">{{gameInfo}}</view>
|
|
||||||
|
|
||||||
<button class="start-game" type="primary" bindtap="startGame">{{startButtonText}}</button>
|
|
||||||
<button class="request-computer" bindtap="requestComputer">跟机器人玩</button>
|
|
||||||
</view>
|
|
@ -1,191 +0,0 @@
|
|||||||
.root {
|
|
||||||
overflow: hidden;
|
|
||||||
position: absolute;
|
|
||||||
top: 0;
|
|
||||||
right: 0;
|
|
||||||
bottom: 0;
|
|
||||||
left: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.my-side {
|
|
||||||
width: 1500rpx;
|
|
||||||
height: 1500rpx;
|
|
||||||
position: absolute;
|
|
||||||
bottom: -1125rpx;
|
|
||||||
left: -375rpx;
|
|
||||||
border-radius: 100%;
|
|
||||||
background: lightskyblue;
|
|
||||||
overflow: visible;
|
|
||||||
}
|
|
||||||
|
|
||||||
.your-side {
|
|
||||||
width: 1500rpx;
|
|
||||||
height: 1500rpx;
|
|
||||||
position: absolute;
|
|
||||||
top: -1500rpx;
|
|
||||||
left: -375rpx;
|
|
||||||
border-radius: 100%;
|
|
||||||
background: lightpink;
|
|
||||||
overflow: visible;
|
|
||||||
transition: top ease 0.6s;
|
|
||||||
}
|
|
||||||
|
|
||||||
.your-side.here {
|
|
||||||
top: -1125rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.avatar {
|
|
||||||
position: absolute;
|
|
||||||
width: 172rpx;
|
|
||||||
height: 172rpx;
|
|
||||||
border-radius: 100%;
|
|
||||||
border: 8rpx solid white;
|
|
||||||
background-color: #f0f0f0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.hand {
|
|
||||||
position: absolute;
|
|
||||||
width: 187rpx;
|
|
||||||
height: 187rpx;
|
|
||||||
border-radius: 100%;
|
|
||||||
overflow: visible;
|
|
||||||
}
|
|
||||||
|
|
||||||
.score, .streak {
|
|
||||||
position: absolute;
|
|
||||||
color: #334567;
|
|
||||||
width: 225rpx;
|
|
||||||
overflow: hidden;
|
|
||||||
white-space: nowrap;
|
|
||||||
text-overflow: ellipsis;
|
|
||||||
}
|
|
||||||
|
|
||||||
.streak {
|
|
||||||
text-align: right;
|
|
||||||
}
|
|
||||||
|
|
||||||
.my-side .avatar {
|
|
||||||
left: 656.25rpx;
|
|
||||||
top: -93.75rpx;
|
|
||||||
transition: top ease .2s;
|
|
||||||
}
|
|
||||||
|
|
||||||
.my-side .hand {
|
|
||||||
left: 656.25rpx;
|
|
||||||
top: 150rpx;
|
|
||||||
transition: top ease .2s;
|
|
||||||
}
|
|
||||||
|
|
||||||
.root.playing .my-side .hand:active {
|
|
||||||
transform: scale(1.3);
|
|
||||||
}
|
|
||||||
|
|
||||||
.root.done .my-side .avatar {
|
|
||||||
top: 168.75rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.root.done .my-side .hand {
|
|
||||||
top: -112.5rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.my-side .score {
|
|
||||||
left: 412.5rpx;
|
|
||||||
bottom: 1162.5rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.my-side .streak {
|
|
||||||
right: 412.5rpx;
|
|
||||||
bottom: 1162.5rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.your-side .avatar {
|
|
||||||
left: 656.25rpx;
|
|
||||||
bottom: -93.75rpx;
|
|
||||||
transition: all ease .2s;
|
|
||||||
opacity: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.your-side.here .avatar {
|
|
||||||
opacity: 1;
|
|
||||||
}
|
|
||||||
.your-side.move-1 .avatar {
|
|
||||||
transform: rotate(15deg);
|
|
||||||
}
|
|
||||||
.your-side.move-2 .avatar {
|
|
||||||
transform: rotate(-15deg);
|
|
||||||
}
|
|
||||||
|
|
||||||
.your-side .hand {
|
|
||||||
left: 656.25rpx;
|
|
||||||
bottom: 150rpx;
|
|
||||||
opacity: 0;
|
|
||||||
transition: bottom ease .2s;
|
|
||||||
transform: rotate(180deg);
|
|
||||||
}
|
|
||||||
|
|
||||||
.root.done .your-side .avatar {
|
|
||||||
bottom: 168.75rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.root.done .your-side .hand {
|
|
||||||
bottom: -93.75rpx;
|
|
||||||
opacity: 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
.your-side .score {
|
|
||||||
left: 412.5rpx;
|
|
||||||
top: 1106.25rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.your-side .streak {
|
|
||||||
right: 412.5rpx;
|
|
||||||
top: 1106.25rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
.start-game, .request-computer {
|
|
||||||
position: absolute;
|
|
||||||
width: 200rpx;
|
|
||||||
height: 80rpx;
|
|
||||||
line-height: 80rpx;
|
|
||||||
margin-left: -100rpx;
|
|
||||||
bottom: 500rpx;
|
|
||||||
left: 50%;
|
|
||||||
display: none;
|
|
||||||
}
|
|
||||||
|
|
||||||
.request-computer {
|
|
||||||
width: 300rpx;
|
|
||||||
margin-left: -150rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.root.finding .request-computer {
|
|
||||||
display: block;
|
|
||||||
}
|
|
||||||
|
|
||||||
.root.connected .start-game {
|
|
||||||
display: block;
|
|
||||||
}
|
|
||||||
|
|
||||||
.root.connected.playing .start-game,
|
|
||||||
.root.finding .start-game {
|
|
||||||
display: none;
|
|
||||||
}
|
|
||||||
|
|
||||||
.game-info {
|
|
||||||
font-size: 75rpx;
|
|
||||||
position: absolute;
|
|
||||||
width: 750rpx;
|
|
||||||
height: 112.5rpx;
|
|
||||||
line-height: 112.5rpx;
|
|
||||||
margin-top: -56.25rpx;
|
|
||||||
bottom: 600rpx;
|
|
||||||
left: 0;
|
|
||||||
text-align: center;
|
|
||||||
opacity: 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
.root.connected.root.playing .game-info,
|
|
||||||
.root.connected.root.done .game-info {
|
|
||||||
opacity: 1;
|
|
||||||
}
|
|
@ -1,54 +0,0 @@
|
|||||||
const app = getApp();
|
|
||||||
const config = app.config;
|
|
||||||
const lab = require('../../lib/lab');
|
|
||||||
|
|
||||||
Page({
|
|
||||||
data: {
|
|
||||||
status: 'waiting',
|
|
||||||
url: 'https://' + config.host + '/hello',
|
|
||||||
requesting: false,
|
|
||||||
hintLine1: '完成服务器开发,',
|
|
||||||
hintLine2: '使得下面的地址可以访问'
|
|
||||||
},
|
|
||||||
request() {
|
|
||||||
this.setData({
|
|
||||||
requesting: true,
|
|
||||||
status: 'waiting',
|
|
||||||
hintLine1: '正在发送',
|
|
||||||
hintLine2: '...'
|
|
||||||
});
|
|
||||||
wx.request({
|
|
||||||
url: this.data.url,
|
|
||||||
method: 'GET',
|
|
||||||
success: (res) => {
|
|
||||||
if (+res.statusCode == 200) {
|
|
||||||
this.setData({
|
|
||||||
status: 'success',
|
|
||||||
hintLine1: '服务器响应成功',
|
|
||||||
hintLine2: '返回:' + res.data
|
|
||||||
});
|
|
||||||
lab.finish('https');
|
|
||||||
} else {
|
|
||||||
this.setData({
|
|
||||||
status: 'warn',
|
|
||||||
hintLine1: '响应错误',
|
|
||||||
hintLine2: '响应码:' + res.statusCode
|
|
||||||
});
|
|
||||||
}
|
|
||||||
},
|
|
||||||
fail: (res) => {
|
|
||||||
console.log(res);
|
|
||||||
this.setData({
|
|
||||||
status: 'warn',
|
|
||||||
hintLine1: '请求失败',
|
|
||||||
hintLine2: res.errMsg
|
|
||||||
});
|
|
||||||
},
|
|
||||||
complete: () => {
|
|
||||||
this.setData({
|
|
||||||
requesting: false
|
|
||||||
});
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
});
|
|
@ -1 +0,0 @@
|
|||||||
{}
|
|
@ -1,15 +0,0 @@
|
|||||||
<view class="lab https">
|
|
||||||
<view class="status">
|
|
||||||
<icon type="{{status}}" size="70" />
|
|
||||||
</view>
|
|
||||||
<view class="hint">
|
|
||||||
<view class="line">{{hintLine1}}</view>
|
|
||||||
<view class="line">{{hintLine2}}</view>
|
|
||||||
</view>
|
|
||||||
<view class="hint">
|
|
||||||
<view class="line">{{url}}</view>
|
|
||||||
</view>
|
|
||||||
<view class="command">
|
|
||||||
<button wx:if="{{status != 'success'}}" type="primary" bindtap="request" disabled="{{requesting}}">发送请求</button>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
@ -1 +0,0 @@
|
|||||||
/* pages/https/https.wxss */
|
|
@ -1,3 +0,0 @@
|
|||||||
{
|
|
||||||
"navigationBarTitleText": "积分教室"
|
|
||||||
}
|
|
@ -1,11 +0,0 @@
|
|||||||
<view class="index">
|
|
||||||
<view class="nav">
|
|
||||||
<navigator wx:for="{{labs}}" wx:key="{{lab.id}}" wx:for-item="lab" url="/pages/{{lab.id}}/{{lab.id}}">
|
|
||||||
<icon type="{{ done[lab.id] ? 'success' : 'waiting_circle' }}" size="24"></icon>
|
|
||||||
<text>{{lab.title}}</text>
|
|
||||||
</navigator>
|
|
||||||
</view>
|
|
||||||
<view class="clear">
|
|
||||||
<button bindtap="clear">清空任务状态</button>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
@ -1,41 +0,0 @@
|
|||||||
/* pages/index/index.wxss */
|
|
||||||
.index {
|
|
||||||
font-family: 'PingFang SC';
|
|
||||||
}
|
|
||||||
|
|
||||||
.nav {
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
padding: 0 50rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.nav navigator {
|
|
||||||
padding: 30rpx 0;
|
|
||||||
border-bottom: 1rpx solid #EEE;
|
|
||||||
position: relative;
|
|
||||||
}
|
|
||||||
|
|
||||||
.nav navigator:after {
|
|
||||||
content: '>';
|
|
||||||
display: block;
|
|
||||||
position: absolute;
|
|
||||||
right: 3rpx;
|
|
||||||
top: 50%;
|
|
||||||
height: 40rpx;
|
|
||||||
line-height: 40rpx;
|
|
||||||
margin-top: -20rpx;
|
|
||||||
color: #999;
|
|
||||||
}
|
|
||||||
|
|
||||||
.nav navigator icon,
|
|
||||||
.nav navigator text {
|
|
||||||
vertical-align: middle;
|
|
||||||
}
|
|
||||||
|
|
||||||
.nav navigator icon {
|
|
||||||
margin-right: 25rpx;
|
|
||||||
}
|
|
||||||
|
|
||||||
.clear {
|
|
||||||
margin: 100rpx 50rpx;
|
|
||||||
}
|
|
@ -1,74 +0,0 @@
|
|||||||
// pages/outside/outside.js
|
|
||||||
Page({
|
|
||||||
|
|
||||||
/**
|
|
||||||
* 页面的初始数据
|
|
||||||
*/
|
|
||||||
data: {
|
|
||||||
name: 'Hello World',
|
|
||||||
src: '/images/weixin.jpg'
|
|
||||||
},
|
|
||||||
getMyInfo: function (e) {
|
|
||||||
console.log(e.detail.userInfo)
|
|
||||||
let info = e.detail.userInfo;
|
|
||||||
this.setData({
|
|
||||||
name: info.nickName,//更新名称
|
|
||||||
src: info.avatarUrl//更新图片来源
|
|
||||||
})
|
|
||||||
},
|
|
||||||
/**
|
|
||||||
* 生命周期函数--监听页面加载
|
|
||||||
*/
|
|
||||||
onLoad: function (options) {
|
|
||||||
|
|
||||||
},
|
|
||||||
|
|
||||||
/**
|
|
||||||
* 生命周期函数--监听页面初次渲染完成
|
|
||||||
*/
|
|
||||||
onReady: function () {
|
|
||||||
|
|
||||||
},
|
|
||||||
|
|
||||||
/**
|
|
||||||
* 生命周期函数--监听页面显示
|
|
||||||
*/
|
|
||||||
onShow: function () {
|
|
||||||
|
|
||||||
},
|
|
||||||
|
|
||||||
/**
|
|
||||||
* 生命周期函数--监听页面隐藏
|
|
||||||
*/
|
|
||||||
onHide: function () {
|
|
||||||
|
|
||||||
},
|
|
||||||
|
|
||||||
/**
|
|
||||||
* 生命周期函数--监听页面卸载
|
|
||||||
*/
|
|
||||||
onUnload: function () {
|
|
||||||
|
|
||||||
},
|
|
||||||
|
|
||||||
/**
|
|
||||||
* 页面相关事件处理函数--监听用户下拉动作
|
|
||||||
*/
|
|
||||||
onPullDownRefresh: function () {
|
|
||||||
|
|
||||||
},
|
|
||||||
|
|
||||||
/**
|
|
||||||
* 页面上拉触底事件的处理函数
|
|
||||||
*/
|
|
||||||
onReachBottom: function () {
|
|
||||||
|
|
||||||
},
|
|
||||||
|
|
||||||
/**
|
|
||||||
* 用户点击右上角分享
|
|
||||||
*/
|
|
||||||
onShareAppMessage: function () {
|
|
||||||
|
|
||||||
}
|
|
||||||
})
|
|
@ -1,7 +0,0 @@
|
|||||||
<view class='container'>
|
|
||||||
<image src='{{src}}' class='abc'></image>
|
|
||||||
<text>{{name}}</text>
|
|
||||||
<button open-type='getUserInfo' bindgetuserinfo='getMyInfo'>点击登录积分教室</button>
|
|
||||||
<!-- open-type='getUserInfo 表示激活获取微信用户信息功能' -->
|
|
||||||
<!-- bindgetuserinfo='getMyInfo' 表示获得的数据将传递给自定义函数getMyInfo,可以自己取-->
|
|
||||||
</view>
|
|
@ -1,67 +0,0 @@
|
|||||||
const app = getApp();
|
|
||||||
const config = app.config;
|
|
||||||
const wafer = require('../../vendors/wafer-client-sdk/index');
|
|
||||||
const lab = require('../../lib/lab');
|
|
||||||
|
|
||||||
wafer.setLoginUrl(`https://` + config.host + '/login');
|
|
||||||
|
|
||||||
Page({
|
|
||||||
data: {
|
|
||||||
status: 'waiting',
|
|
||||||
url: 'https://' + config.host + '/me',
|
|
||||||
requesting: false,
|
|
||||||
hintLine1: '完成服务器开发,',
|
|
||||||
hintLine2: '让服务器可以识别小程序会话'
|
|
||||||
},
|
|
||||||
request() {
|
|
||||||
this.setData({
|
|
||||||
requesting: true,
|
|
||||||
status: 'waiting',
|
|
||||||
hintLine1: '正在发送',
|
|
||||||
hintLine2: '...'
|
|
||||||
});
|
|
||||||
wafer.request({
|
|
||||||
login: true,
|
|
||||||
url: this.data.url,
|
|
||||||
method: 'GET',
|
|
||||||
success: (res) => {
|
|
||||||
if (+res.statusCode == 200) {
|
|
||||||
if (res.data.openId) {
|
|
||||||
this.setData({
|
|
||||||
status: 'success',
|
|
||||||
hintLine1: '成功获取会话',
|
|
||||||
hintLine2: res.data.nickName,
|
|
||||||
avatarUrl: res.data.avatarUrl
|
|
||||||
});
|
|
||||||
lab.finish('session');
|
|
||||||
} else {
|
|
||||||
this.setData({
|
|
||||||
status: 'warn',
|
|
||||||
hintLine1: '会话获取失败',
|
|
||||||
hintLine2: '未获取到 openId'
|
|
||||||
});
|
|
||||||
console.error('会话获取失败', res.data);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
this.setData({
|
|
||||||
status: 'warn',
|
|
||||||
hintLine1: '响应错误',
|
|
||||||
hintLine2: '响应码:' + res.statusCode
|
|
||||||
});
|
|
||||||
}
|
|
||||||
},
|
|
||||||
fail: (error) => {
|
|
||||||
this.setData({
|
|
||||||
status: 'warn',
|
|
||||||
hintLine1: '获取失败',
|
|
||||||
hintLine2: error.message
|
|
||||||
});
|
|
||||||
},
|
|
||||||
complete: () => {
|
|
||||||
this.setData({
|
|
||||||
requesting: false
|
|
||||||
});
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
});
|
|
@ -1 +0,0 @@
|
|||||||
{}
|
|
@ -1,16 +0,0 @@
|
|||||||
<view class="lab https">
|
|
||||||
<view class="status">
|
|
||||||
<icon wx:if="{{status != 'success'}}" type="{{status}}" size="70" />
|
|
||||||
<image wx:if="{{status == 'success'}}" src="{{avatarUrl}}" mode="aspectFill" />
|
|
||||||
</view>
|
|
||||||
<view class="hint">
|
|
||||||
<view class="line">{{hintLine1}}</view>
|
|
||||||
<view class="line">{{hintLine2}}</view>
|
|
||||||
</view>
|
|
||||||
<view class="hint">
|
|
||||||
<view class="line">{{url}}</view>
|
|
||||||
</view>
|
|
||||||
<view class="command">
|
|
||||||
<button wx:if="{{status != 'success'}}" type="primary" bindtap="request" disabled="{{requesting}}">获取会话</button>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
@ -1 +0,0 @@
|
|||||||
/* pages/session/session.wxss */
|
|
@ -1,4 +1,20 @@
|
|||||||
|
const AV = require("../../lib/av-live-query-weapp-min")
|
||||||
Page({
|
Page({
|
||||||
|
data:{
|
||||||
|
current_user: null
|
||||||
|
},
|
||||||
|
enter_usersetting: function(event){
|
||||||
|
wx.navigateTo({
|
||||||
|
url: '../user/user'
|
||||||
|
})
|
||||||
|
},
|
||||||
|
enter_changeuser: function(event){
|
||||||
|
console.log(event);
|
||||||
|
wx.navigateTo({
|
||||||
|
url: '../changeuser/changeuser'
|
||||||
|
})
|
||||||
|
},
|
||||||
|
onShow: function(){
|
||||||
|
this.setData({current_user: AV.User.current().toJSON()})
|
||||||
|
}
|
||||||
})
|
})
|
@ -1,4 +1,13 @@
|
|||||||
<view class="form-wrap">
|
<view class="form-wrap">
|
||||||
<navigator url="../user/user" class="navigator user">登陆信息修改</navigator>
|
<view class="user-view">
|
||||||
<navigator url="../changeuser/changeuser" class="navigator user">更换登陆用户</navigator>
|
<image src="../../images/avatar.png" class="user" mode="aspectFit"></image>
|
||||||
|
<text class="user" bindtap="enter_usersetting">{{current_user.name}} | {{current_user.username}}</text>
|
||||||
|
</view>
|
||||||
|
<view class="nav-list">
|
||||||
|
<navigator url="../user/user" class="nav user" bindlongpress="enter_changeuser">登陆信息修改</navigator>
|
||||||
|
<navigator hidden="{{true}}" url="../changeuser/changeuser" class="nav user">更换登陆用户</navigator>
|
||||||
|
<navigator url="../addclass/addclass" class="nav addclass">加入课程</navigator>
|
||||||
|
<navigator url="../createclass/createclass" class="nav createclass">创建课程</navigator>
|
||||||
|
<navigator url="../about/about" class="nav about">关于</navigator>
|
||||||
|
</view>
|
||||||
</view>
|
</view>
|
@ -1,7 +1,27 @@
|
|||||||
.navigator {
|
.nav {
|
||||||
background: white;
|
background: white;
|
||||||
border-bottom: 1px solid #eee;
|
border-bottom: 1px solid #eee;
|
||||||
padding: 0 12px;
|
padding: 0 12px;
|
||||||
height: 46px;
|
height: 46px;
|
||||||
line-height: 46px;
|
line-height: 46px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.user-view{
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
}
|
||||||
|
|
||||||
|
.user{
|
||||||
|
align-self: center;
|
||||||
|
}
|
||||||
|
text.user{
|
||||||
|
font-size: 16px;
|
||||||
|
margin-top: 5px;
|
||||||
|
margin-bottom: 8px;
|
||||||
|
}
|
||||||
|
|
||||||
|
image.user{
|
||||||
|
margin-top: 10rpx;
|
||||||
|
height: 120rpx;
|
||||||
|
width: 120rpx;
|
||||||
|
}
|
||||||
|
@ -1,5 +0,0 @@
|
|||||||
<view class="lab https">
|
|
||||||
<view class="command">
|
|
||||||
<button open-type="getUserInfo" bindgetuserinfo="bindGetUserInfo">授权登录</button>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
@ -1,109 +0,0 @@
|
|||||||
const app = getApp();
|
|
||||||
const config = app.config;
|
|
||||||
const wafer = require('../../vendors/wafer-client-sdk/index');
|
|
||||||
const lab = require('../../lib/lab');
|
|
||||||
|
|
||||||
Page({
|
|
||||||
data: {
|
|
||||||
status: 'waiting',
|
|
||||||
url: 'wss://' + config.host + '/ws',
|
|
||||||
connecting: false,
|
|
||||||
hintLine1: '完成服务器开发,',
|
|
||||||
hintLine2: '让服务器支持 WebSocket 连接'
|
|
||||||
},
|
|
||||||
|
|
||||||
/**
|
|
||||||
* WebSocket 是否已经连接
|
|
||||||
*/
|
|
||||||
socketOpen: false,
|
|
||||||
|
|
||||||
/**
|
|
||||||
* 开始连接 WebSocket
|
|
||||||
*/
|
|
||||||
connect() {
|
|
||||||
this.setData({
|
|
||||||
status: 'waiting',
|
|
||||||
connecting: true,
|
|
||||||
hintLine1: '正在连接',
|
|
||||||
hintLine2: '...'
|
|
||||||
});
|
|
||||||
this.listen();
|
|
||||||
wafer.setLoginUrl(`https://${config.host}/login`);
|
|
||||||
wafer.login({
|
|
||||||
success: () => {
|
|
||||||
const header = wafer.buildSessionHeader();
|
|
||||||
const query = Object.keys(header).map(key => `${key}=${encodeURIComponent(header[key])}`).join('&');
|
|
||||||
wx.connectSocket({
|
|
||||||
// 小程序 wx.connectSocket() API header 参数无效,把会话信息附加在 URL 上
|
|
||||||
url: `${this.data.url}?${query}`,
|
|
||||||
header
|
|
||||||
});
|
|
||||||
},
|
|
||||||
fail: (err) => {
|
|
||||||
this.setData({
|
|
||||||
status: 'warn',
|
|
||||||
connecting: false,
|
|
||||||
hintLine1: '登录失败',
|
|
||||||
hintLine2: err.message || err
|
|
||||||
});
|
|
||||||
}
|
|
||||||
});
|
|
||||||
},
|
|
||||||
|
|
||||||
/**
|
|
||||||
* 监听 WebSocket 事件
|
|
||||||
*/
|
|
||||||
listen() {
|
|
||||||
wx.onSocketOpen(() => {
|
|
||||||
this.socketOpen = true;
|
|
||||||
this.setData({
|
|
||||||
status: 'success',
|
|
||||||
connecting: false,
|
|
||||||
hintLine1: '连接成功',
|
|
||||||
hintLine2: '现在可以通过 WebSocket 发送接收消息了'
|
|
||||||
});
|
|
||||||
console.info('WebSocket 已连接');
|
|
||||||
});
|
|
||||||
wx.onSocketMessage((message) => {
|
|
||||||
this.setData({
|
|
||||||
hintLine2: message.data
|
|
||||||
});
|
|
||||||
lab.finish('websocket');
|
|
||||||
});
|
|
||||||
wx.onSocketClose(() => {
|
|
||||||
this.setData({
|
|
||||||
status: 'waiting',
|
|
||||||
hintLine1: 'WebSocket 已关闭'
|
|
||||||
});
|
|
||||||
console.info('WebSocket 已关闭');
|
|
||||||
});
|
|
||||||
wx.onSocketError(() => {
|
|
||||||
setTimeout(() => {
|
|
||||||
this.setData({
|
|
||||||
status: 'warn',
|
|
||||||
connecting: false,
|
|
||||||
hintLine1: '发生错误',
|
|
||||||
hintLine2: 'WebSocket 连接建立失败'
|
|
||||||
});
|
|
||||||
});
|
|
||||||
console.error('WebSocket 错误');
|
|
||||||
});
|
|
||||||
},
|
|
||||||
|
|
||||||
/**
|
|
||||||
* 发送一个包含当前时间信息的消息
|
|
||||||
*/
|
|
||||||
send() {
|
|
||||||
wx.sendSocketMessage({
|
|
||||||
data: new Date().toTimeString().split(' ').shift() + '.' + (new Date().getMilliseconds())
|
|
||||||
});
|
|
||||||
},
|
|
||||||
|
|
||||||
/**
|
|
||||||
* 关闭 WebSocket 连接
|
|
||||||
*/
|
|
||||||
close() {
|
|
||||||
this.socketOpen = false;
|
|
||||||
wx.closeSocket();
|
|
||||||
}
|
|
||||||
});
|
|
@ -1 +0,0 @@
|
|||||||
{}
|
|
@ -1,17 +0,0 @@
|
|||||||
<view class="lab https">
|
|
||||||
<view class="status">
|
|
||||||
<icon type="{{status}}" size="70" />
|
|
||||||
</view>
|
|
||||||
<view class="hint">
|
|
||||||
<view class="line">{{hintLine1}}</view>
|
|
||||||
<view class="line">{{hintLine2}}</view>
|
|
||||||
</view>
|
|
||||||
<view class="hint">
|
|
||||||
<view class="line">{{url}}</view>
|
|
||||||
</view>
|
|
||||||
<view class="command">
|
|
||||||
<button type="primary" bindtap="connect" disabled="{{connecting || status == 'success'}}">连接</button>
|
|
||||||
<button bindtap="send" disabled="{{ status != 'success' }}">发送消息</button>
|
|
||||||
<button bindtap="close" disabled="{{ status != 'success' }}">断开</button>
|
|
||||||
</view>
|
|
||||||
</view>
|
|
@ -1 +0,0 @@
|
|||||||
/* pages/websocket/websocket.wxss */
|
|
@ -1,42 +0,0 @@
|
|||||||
{
|
|
||||||
"name": "wafer-client-sdk",
|
|
||||||
"description": "QCloud 微信小程序客户端 SDK",
|
|
||||||
"main": "index.js",
|
|
||||||
"authors": [
|
|
||||||
"Tencent Cloud"
|
|
||||||
],
|
|
||||||
"license": "MIT",
|
|
||||||
"keywords": [
|
|
||||||
"qcloud",
|
|
||||||
"weapp",
|
|
||||||
"wechat",
|
|
||||||
"sdk",
|
|
||||||
"client",
|
|
||||||
"auth",
|
|
||||||
"websocket"
|
|
||||||
],
|
|
||||||
"homepage": "https://github.com/tencentyun/wafer-client-sdk",
|
|
||||||
"ignore": [
|
|
||||||
"**/.*",
|
|
||||||
"node_modules",
|
|
||||||
"bower_components",
|
|
||||||
"test",
|
|
||||||
"tests",
|
|
||||||
"typings.json",
|
|
||||||
"jsconfig.json",
|
|
||||||
"package.json",
|
|
||||||
".npmignore",
|
|
||||||
".travis.yml",
|
|
||||||
".gitignore"
|
|
||||||
],
|
|
||||||
"version": "0.8.4",
|
|
||||||
"_release": "0.8.4",
|
|
||||||
"_resolution": {
|
|
||||||
"type": "version",
|
|
||||||
"tag": "v0.8.4",
|
|
||||||
"commit": "3f605d1aa5bd0206bb9368586f4acb104f5f8ae5"
|
|
||||||
},
|
|
||||||
"_source": "https://github.com/tencentyun/wafer-client-sdk.git",
|
|
||||||
"_target": "^0.8.3",
|
|
||||||
"_originalSource": "wafer-client-sdk"
|
|
||||||
}
|
|
@ -1,24 +0,0 @@
|
|||||||
LICENSE - "MIT License"
|
|
||||||
|
|
||||||
Copyright (c) 2016 by Tencent Cloud
|
|
||||||
|
|
||||||
Permission is hereby granted, free of charge, to any person
|
|
||||||
obtaining a copy of this software and associated documentation
|
|
||||||
files (the "Software"), to deal in the Software without
|
|
||||||
restriction, including without limitation the rights to use,
|
|
||||||
copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
||||||
copies of the Software, and to permit persons to whom the
|
|
||||||
Software is furnished to do so, subject to the following
|
|
||||||
conditions:
|
|
||||||
|
|
||||||
The above copyright notice and this permission notice shall be
|
|
||||||
included in all copies or substantial portions of the Software.
|
|
||||||
|
|
||||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
|
||||||
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
|
|
||||||
OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
|
||||||
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
|
||||||
HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
|
||||||
WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
|
||||||
FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
|
||||||
OTHER DEALINGS IN THE SOFTWARE.
|
|
@ -1,32 +0,0 @@
|
|||||||
{
|
|
||||||
"name": "wafer-client-sdk",
|
|
||||||
"description": "QCloud 微信小程序客户端 SDK",
|
|
||||||
"main": "index.js",
|
|
||||||
"authors": [
|
|
||||||
"Tencent Cloud"
|
|
||||||
],
|
|
||||||
"license": "MIT",
|
|
||||||
"keywords": [
|
|
||||||
"qcloud",
|
|
||||||
"weapp",
|
|
||||||
"wechat",
|
|
||||||
"sdk",
|
|
||||||
"client",
|
|
||||||
"auth",
|
|
||||||
"websocket"
|
|
||||||
],
|
|
||||||
"homepage": "",
|
|
||||||
"ignore": [
|
|
||||||
"**/.*",
|
|
||||||
"node_modules",
|
|
||||||
"bower_components",
|
|
||||||
"test",
|
|
||||||
"tests",
|
|
||||||
"typings.json",
|
|
||||||
"jsconfig.json",
|
|
||||||
"package.json",
|
|
||||||
".npmignore",
|
|
||||||
".travis.yml",
|
|
||||||
".gitignore"
|
|
||||||
]
|
|
||||||
}
|
|
@ -1,26 +0,0 @@
|
|||||||
var constants = require('./lib/constants');
|
|
||||||
var login = require('./lib/login');
|
|
||||||
var Session = require('./lib/session');
|
|
||||||
var request = require('./lib/request');
|
|
||||||
var Tunnel = require('./lib/tunnel');
|
|
||||||
|
|
||||||
var exports = module.exports = {
|
|
||||||
login: login.login,
|
|
||||||
setLoginUrl: login.setLoginUrl,
|
|
||||||
LoginError: login.LoginError,
|
|
||||||
|
|
||||||
clearSession: Session.clear,
|
|
||||||
|
|
||||||
request: request.request,
|
|
||||||
buildSessionHeader: request.buildSessionHeader,
|
|
||||||
RequestError: request.RequestError,
|
|
||||||
|
|
||||||
Tunnel: Tunnel,
|
|
||||||
};
|
|
||||||
|
|
||||||
// 导出错误类型码
|
|
||||||
Object.keys(constants).forEach(function (key) {
|
|
||||||
if (key.indexOf('ERR_') === 0) {
|
|
||||||
exports[key] = constants[key];
|
|
||||||
}
|
|
||||||
});
|
|
@ -1,20 +0,0 @@
|
|||||||
module.exports = {
|
|
||||||
WX_HEADER_CODE: 'X-WX-Code',
|
|
||||||
WX_HEADER_ENCRYPTED_DATA: 'X-WX-Encrypted-Data',
|
|
||||||
WX_HEADER_IV: 'X-WX-IV',
|
|
||||||
WX_HEADER_ID: 'X-WX-Id',
|
|
||||||
WX_HEADER_SKEY: 'X-WX-Skey',
|
|
||||||
|
|
||||||
WX_SESSION_MAGIC_ID: 'F2C224D4-2BCE-4C64-AF9F-A6D872000D1A',
|
|
||||||
|
|
||||||
ERR_INVALID_PARAMS: 'ERR_INVALID_PARAMS',
|
|
||||||
|
|
||||||
ERR_WX_LOGIN_FAILED: 'ERR_WX_LOGIN_FAILED',
|
|
||||||
ERR_WX_GET_USER_INFO: 'ERR_WX_GET_USER_INFO',
|
|
||||||
ERR_LOGIN_TIMEOUT: 'ERR_LOGIN_TIMEOUT',
|
|
||||||
ERR_LOGIN_FAILED: 'ERR_LOGIN_FAILED',
|
|
||||||
ERR_LOGIN_SESSION_NOT_RECEIVED: 'ERR_LOGIN_MISSING_SESSION',
|
|
||||||
|
|
||||||
ERR_INVALID_SESSION: 'ERR_INVALID_SESSION',
|
|
||||||
ERR_CHECK_LOGIN_FAILED: 'ERR_CHECK_LOGIN_FAILED',
|
|
||||||
};
|
|
@ -1,18 +0,0 @@
|
|||||||
var constants = require('./constants');
|
|
||||||
var SESSION_KEY = 'weapp_session_' + constants.WX_SESSION_MAGIC_ID;
|
|
||||||
|
|
||||||
var Session = {
|
|
||||||
get: function () {
|
|
||||||
return wx.getStorageSync(SESSION_KEY) || null;
|
|
||||||
},
|
|
||||||
|
|
||||||
set: function (session) {
|
|
||||||
wx.setStorageSync(SESSION_KEY, session);
|
|
||||||
},
|
|
||||||
|
|
||||||
clear: function () {
|
|
||||||
wx.removeStorageSync(SESSION_KEY);
|
|
||||||
},
|
|
||||||
};
|
|
||||||
|
|
||||||
module.exports = Session;
|
|
@ -1,18 +0,0 @@
|
|||||||
|
|
||||||
/**
|
|
||||||
* 拓展对象
|
|
||||||
*/
|
|
||||||
exports.extend = function extend(target) {
|
|
||||||
var sources = Array.prototype.slice.call(arguments, 1);
|
|
||||||
|
|
||||||
for (var i = 0; i < sources.length; i += 1) {
|
|
||||||
var source = sources[i];
|
|
||||||
for (var key in source) {
|
|
||||||
if (source.hasOwnProperty(key)) {
|
|
||||||
target[key] = source[key];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return target;
|
|
||||||
};
|
|
@ -1,32 +0,0 @@
|
|||||||
/* istanbul ignore next */
|
|
||||||
const noop = () => void(0);
|
|
||||||
|
|
||||||
let onOpen, onClose, onMessage, onError;
|
|
||||||
|
|
||||||
/* istanbul ignore next */
|
|
||||||
function listen(listener) {
|
|
||||||
if (listener) {
|
|
||||||
onOpen = listener.onOpen;
|
|
||||||
onClose = listener.onClose;
|
|
||||||
onMessage = listener.onMessage;
|
|
||||||
onError = listener.onError;
|
|
||||||
} else {
|
|
||||||
onOpen = noop;
|
|
||||||
onClose = noop;
|
|
||||||
onMessage = noop;
|
|
||||||
onError = noop;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* istanbul ignore next */
|
|
||||||
function bind() {
|
|
||||||
wx.onSocketOpen(result => onOpen(result));
|
|
||||||
wx.onSocketClose(result => onClose(result));
|
|
||||||
wx.onSocketMessage(result => onMessage(result));
|
|
||||||
wx.onSocketError(error => onError(error));
|
|
||||||
}
|
|
||||||
|
|
||||||
listen(null);
|
|
||||||
bind();
|
|
||||||
|
|
||||||
module.exports = { listen };
|
|
@ -1,15 +0,0 @@
|
|||||||
# 后台数据交互部分日志
|
|
||||||
|
|
||||||
## 已完成-登录微信公众平台,前往 设置 > 开发设置 > 服务器配置 > 「修改」 链接,增加下述域名为白名单中的域名
|
|
||||||
request合法域名
|
|
||||||
fqcxn98z.api.lncldglobal.com
|
|
||||||
fqcxn98z.engine.lncldglobal.com
|
|
||||||
fqcxn98z.rtm.lncldglobal.com
|
|
||||||
fqcxn98z.push.lncldglobal.com
|
|
||||||
app-router.leancloud.cn
|
|
||||||
socket合法域名
|
|
||||||
us-w1-backend2.leancloud.cn
|
|
||||||
us-w1-backend3.leancloud.cn
|
|
||||||
us-w1-backend4.leancloud.cn
|
|
||||||
us-w1-backend5.leancloud.cn
|
|
||||||
us-w1-backend6.leancloud.cn
|
|