258 lines
7.2 KiB
JavaScript
258 lines
7.2 KiB
JavaScript
/**
|
|
* 登录场景 - 微信授权登录
|
|
*/
|
|
import BaseScene from './BaseScene';
|
|
|
|
export default class LoginScene extends BaseScene {
|
|
constructor(main, params = {}) {
|
|
super(main, params);
|
|
this.isLoading = false;
|
|
this.userInfoButton = null;
|
|
}
|
|
|
|
loadAssets() {
|
|
// 不加载外部图片,使用 Canvas 绘制
|
|
}
|
|
|
|
init() {
|
|
console.log('[LoginScene] 初始化登录场景');
|
|
// 创建微信授权按钮
|
|
this.createUserInfoButton();
|
|
}
|
|
|
|
// 创建微信用户信息授权按钮
|
|
createUserInfoButton() {
|
|
const { screenWidth, screenHeight } = this;
|
|
const btnWidth = 280;
|
|
const btnHeight = 50;
|
|
const btnX = (screenWidth - btnWidth) / 2;
|
|
const btnY = screenHeight * 0.55;
|
|
|
|
// 创建透明的用户信息按钮,覆盖在登录按钮上
|
|
this.userInfoButton = wx.createUserInfoButton({
|
|
type: 'text',
|
|
text: '',
|
|
style: {
|
|
left: btnX,
|
|
top: btnY,
|
|
width: btnWidth,
|
|
height: btnHeight,
|
|
backgroundColor: 'transparent',
|
|
borderColor: 'transparent',
|
|
borderWidth: 0,
|
|
borderRadius: 25,
|
|
color: 'transparent',
|
|
textAlign: 'center',
|
|
fontSize: 18,
|
|
lineHeight: 50
|
|
}
|
|
});
|
|
|
|
// 监听点击事件
|
|
this.userInfoButton.onTap(async (res) => {
|
|
console.log('[LoginScene] 用户信息授权回调:', res);
|
|
|
|
if (res.userInfo) {
|
|
// 用户同意授权,获取到了头像昵称
|
|
await this.doLoginWithUserInfo(res.userInfo);
|
|
} else {
|
|
// 未获取到用户信息,静默登录
|
|
console.log('[LoginScene] 未获取到用户信息,使用静默登录');
|
|
await this.doLoginWithUserInfo(null);
|
|
}
|
|
});
|
|
}
|
|
|
|
render(ctx) {
|
|
const { screenWidth, screenHeight } = this;
|
|
|
|
// 绘制背景渐变
|
|
const gradient = ctx.createLinearGradient(0, 0, 0, screenHeight);
|
|
gradient.addColorStop(0, '#1a1a2e');
|
|
gradient.addColorStop(0.5, '#16213e');
|
|
gradient.addColorStop(1, '#0f0f23');
|
|
ctx.fillStyle = gradient;
|
|
ctx.fillRect(0, 0, screenWidth, screenHeight);
|
|
|
|
// 绘制装饰性光效
|
|
this.renderGlow(ctx);
|
|
|
|
// 绘制Logo
|
|
this.renderLogo(ctx);
|
|
|
|
// 绘制应用名称
|
|
this.renderTitle(ctx);
|
|
|
|
// 绘制登录按钮
|
|
this.renderLoginButton(ctx);
|
|
|
|
// 绘制底部提示
|
|
this.renderFooter(ctx);
|
|
}
|
|
|
|
renderGlow(ctx) {
|
|
const { screenWidth, screenHeight } = this;
|
|
|
|
// 顶部光晕
|
|
const topGlow = ctx.createRadialGradient(
|
|
screenWidth / 2, -100, 0,
|
|
screenWidth / 2, -100, 400
|
|
);
|
|
topGlow.addColorStop(0, 'rgba(106, 90, 205, 0.3)');
|
|
topGlow.addColorStop(1, 'rgba(106, 90, 205, 0)');
|
|
ctx.fillStyle = topGlow;
|
|
ctx.fillRect(0, 0, screenWidth, 400);
|
|
}
|
|
|
|
renderLogo(ctx) {
|
|
const { screenWidth, screenHeight } = this;
|
|
const logoSize = 120;
|
|
const logoX = (screenWidth - logoSize) / 2;
|
|
const logoY = screenHeight * 0.2;
|
|
|
|
// 绘制Logo背景圆
|
|
ctx.beginPath();
|
|
ctx.arc(screenWidth / 2, logoY + logoSize / 2, logoSize / 2 + 10, 0, Math.PI * 2);
|
|
const logoGradient = ctx.createRadialGradient(
|
|
screenWidth / 2, logoY + logoSize / 2, 0,
|
|
screenWidth / 2, logoY + logoSize / 2, logoSize / 2 + 10
|
|
);
|
|
logoGradient.addColorStop(0, 'rgba(106, 90, 205, 0.4)');
|
|
logoGradient.addColorStop(1, 'rgba(106, 90, 205, 0.1)');
|
|
ctx.fillStyle = logoGradient;
|
|
ctx.fill();
|
|
|
|
// 绘制内圆
|
|
ctx.fillStyle = '#6a5acd';
|
|
ctx.beginPath();
|
|
ctx.arc(screenWidth / 2, logoY + logoSize / 2, logoSize / 2 - 10, 0, Math.PI * 2);
|
|
ctx.fill();
|
|
|
|
// 绘制书本图标
|
|
ctx.fillStyle = '#fff';
|
|
ctx.font = `${logoSize * 0.5}px sans-serif`;
|
|
ctx.textAlign = 'center';
|
|
ctx.textBaseline = 'middle';
|
|
ctx.fillText('📖', screenWidth / 2, logoY + logoSize / 2);
|
|
}
|
|
|
|
renderTitle(ctx) {
|
|
const { screenWidth, screenHeight } = this;
|
|
const titleY = screenHeight * 0.2 + 160;
|
|
|
|
// 应用名称
|
|
ctx.fillStyle = '#ffffff';
|
|
ctx.font = 'bold 32px sans-serif';
|
|
ctx.textAlign = 'center';
|
|
ctx.textBaseline = 'middle';
|
|
ctx.fillText('AI互动故事', screenWidth / 2, titleY);
|
|
|
|
// 副标题
|
|
ctx.fillStyle = 'rgba(255, 255, 255, 0.6)';
|
|
ctx.font = '16px sans-serif';
|
|
ctx.fillText('探索无限可能的剧情世界', screenWidth / 2, titleY + 40);
|
|
}
|
|
|
|
renderLoginButton(ctx) {
|
|
const { screenWidth, screenHeight } = this;
|
|
|
|
// 按钮位置和尺寸
|
|
const btnWidth = 280;
|
|
const btnHeight = 50;
|
|
const btnX = (screenWidth - btnWidth) / 2;
|
|
const btnY = screenHeight * 0.55;
|
|
|
|
// 绘制按钮背景
|
|
const btnGradient = ctx.createLinearGradient(btnX, btnY, btnX + btnWidth, btnY);
|
|
if (this.isLoading) {
|
|
btnGradient.addColorStop(0, '#666666');
|
|
btnGradient.addColorStop(1, '#888888');
|
|
} else {
|
|
btnGradient.addColorStop(0, '#07c160');
|
|
btnGradient.addColorStop(1, '#06ae56');
|
|
}
|
|
|
|
this.roundRect(ctx, btnX, btnY, btnWidth, btnHeight, 25);
|
|
ctx.fillStyle = btnGradient;
|
|
ctx.fill();
|
|
|
|
// 绘制按钮阴影效果
|
|
if (!this.isLoading) {
|
|
ctx.shadowColor = 'rgba(7, 193, 96, 0.4)';
|
|
ctx.shadowBlur = 20;
|
|
ctx.shadowOffsetY = 5;
|
|
this.roundRect(ctx, btnX, btnY, btnWidth, btnHeight, 25);
|
|
ctx.fill();
|
|
ctx.shadowColor = 'transparent';
|
|
ctx.shadowBlur = 0;
|
|
ctx.shadowOffsetY = 0;
|
|
}
|
|
|
|
// 绘制按钮文字
|
|
ctx.fillStyle = '#ffffff';
|
|
ctx.font = 'bold 18px sans-serif';
|
|
ctx.textAlign = 'center';
|
|
ctx.textBaseline = 'middle';
|
|
|
|
if (this.isLoading) {
|
|
ctx.fillText('登录中...', screenWidth / 2, btnY + btnHeight / 2);
|
|
} else {
|
|
ctx.fillText('微信一键登录', screenWidth / 2, btnY + btnHeight / 2);
|
|
}
|
|
}
|
|
|
|
renderFooter(ctx) {
|
|
const { screenWidth, screenHeight } = this;
|
|
const footerY = screenHeight - 60;
|
|
|
|
// 用户协议提示
|
|
ctx.fillStyle = 'rgba(255, 255, 255, 0.4)';
|
|
ctx.font = '12px sans-serif';
|
|
ctx.textAlign = 'center';
|
|
ctx.textBaseline = 'middle';
|
|
ctx.fillText('登录即表示同意《用户协议》和《隐私政策》', screenWidth / 2, footerY);
|
|
}
|
|
|
|
// 不再需要手动处理点击事件,由 userInfoButton 处理
|
|
onTouchEnd(e) {}
|
|
|
|
async doLoginWithUserInfo(userInfo) {
|
|
if (this.isLoading) return;
|
|
|
|
this.isLoading = true;
|
|
console.log('[LoginScene] 开始登录,用户信息:', userInfo);
|
|
|
|
try {
|
|
// 调用 UserManager 的登录方法,传入用户信息
|
|
await this.main.userManager.doLogin(userInfo);
|
|
|
|
console.log('[LoginScene] 登录成功,加载数据并进入首页');
|
|
|
|
// 隐藏授权按钮
|
|
if (this.userInfoButton) {
|
|
this.userInfoButton.hide();
|
|
}
|
|
|
|
// 登录成功,加载数据并进入首页
|
|
await this.main.loadAndEnterHome();
|
|
} catch (error) {
|
|
console.error('[LoginScene] 登录失败:', error);
|
|
this.isLoading = false;
|
|
|
|
wx.showToast({
|
|
title: error.message || '登录失败',
|
|
icon: 'none'
|
|
});
|
|
}
|
|
}
|
|
|
|
destroy() {
|
|
console.log('[LoginScene] 销毁登录场景');
|
|
// 销毁授权按钮
|
|
if (this.userInfoButton) {
|
|
this.userInfoButton.destroy();
|
|
this.userInfoButton = null;
|
|
}
|
|
}
|
|
}
|