<template>
	<view class="checkin-publish-page">
		<!-- 内容区域 -->
		<scroll-view class="content-scroll" scroll-y>
			<!-- 上传照片卡片 -->
			<view class="card">
				<view class="card-header">
					<text class="card-title">上传照片</text>
					<text class="photo-count">{{ selectedImages.length }}/6</text>
				</view>
				<view class="photo-grid">
					<view 
						class="photo-item" 
						v-for="(image, index) in selectedImages" 
						:key="index"
					>
						<image class="photo-image" :src="image" mode="aspectFill"></image>
						<view class="photo-delete" @click="removeImage(index)">
							<text class="delete-icon">×</text>
						</view>
					</view>
					<view 
						class="photo-add-btn" 
						v-if="selectedImages.length < 6"
						@click="chooseImage"
					>
						<text class="add-icon">+</text>
						<text class="add-text">添加照片</text>
					</view>
				</view>
				<view class="photo-tip">
					<!-- <text class="tip-icon">📷</text> -->
					<text class="tip-text">拍摄清晰的照片能帮您更准确地识别食物营养成分</text>
				</view>
			</view>

			<!-- 选择餐次卡片 -->
			<view class="card">
				<view class="card-header">
					<text class="card-title">选择餐次</text>
				</view>
				<view class="meal-type-list">
					<view 
						class="meal-type-item" 
						v-for="(meal, index) in mealTypes" 
						:key="index"
						:class="{ active: selectedMealType === meal.value }"
						@click="selectMealType(meal.value)"
					>
						<text>{{ meal.label }}</text>
					</view>
				</view>
			</view>

			<!-- 备注说明卡片 -->
			<view class="card">
				<view class="card-header">
					<text class="card-title">一句话说明（可选）</text>
				</view>
				<textarea 
					class="remark-input" 
					v-model="remark"
					placeholder="记录今天的饮食感受、烹饪方法、食材用量等..."
					maxlength="500"
					@input="onRemarkInput"
				></textarea>
				<view class="remark-footer">
					<text class="char-count">{{ remark.length }}/500</text>
					<view class="voice-btn" :class="{ recording: isRecording }" @click="handleVoiceRemark">
						<text class="voice-icon">{{ isRecording ? '⏹️' : '🎤' }}</text>
						<text class="voice-text">{{ isRecording ? `停止录音 (${recordDuration}s)` : '语音录入' }}</text>
					</view>
				</view>
			</view>

			<!-- 生成AI营养分析视频卡片 -->
			<view class="card">
				<view class="card-header">
					<view class="ai-header-left">
						<text class="ai-icon">🎬</text>
						<text class="card-title">生成打卡视频分享到社区</text>
					</view>
					<switch 
						class="ai-switch" 
						:checked="enableAIVideo"
						@change="toggleAIVideo"
						color="#ff6b35"
					/>
				</view>
				<view class="ai-features" v-if="enableAIVideo">
					<view class="feature-item">
						<text class="feature-check">✓</text>
						<text class="feature-text">AI分析营养成分</text>
					</view>
					<view class="feature-item">
						<text class="feature-check">✓</text>
						<text class="feature-text">生成专业营养分析视频</text>
					</view>
					<view class="feature-item">
						<text class="feature-check">✓</text>
						<text class="feature-text">分享到社区，获得更多积分</text>
					</view>
				</view>
			</view>

			<!-- 底部安全距离 -->
			<view class="safe-bottom"></view>
		</scroll-view>

		<!-- 底部操作栏 -->
		<view class="bottom-bar">
			<view class="cancel-btn" @click="handleCancel">
				<text>取消</text>
			</view>
			<view class="publish-btn" @click="handlePublish">
				<text>发布打卡</text>
			</view>
		</view>
	</view>
</template>

<script>
import api from '@/api/models-api.js';
import { submitCheckin } from '@/api/tool.js';
import { mapGetters } from 'vuex';

export default {
	computed: {
		...mapGetters(['userInfo','uid'])
	},
	data() {
		return {
			selectedImages: [],
			selectedMealType: 'breakfast',
			mealTypes: [
				{ label: '早餐', value: 'breakfast' },
				{ label: '午餐', value: 'lunch' },
				{ label: '晚餐', value: 'dinner' },
				{ label: '加餐', value: 'snack' }
			],
			remark: '',
			enableAIVideo: false,
			
			// 语音输入相关
			isRecording: false,
			recorderManager: null,
			recordDuration: 0,
			recordTimer: null
		}
	},
	onLoad(options) {
		// 初始化录音管理器
		this.initRecorder();
		
		// 根据参数处理
		if (options.type === 'video') {
			this.enableAIVideo = true;
		}
		
		// 处理一键复制/借鉴打卡
		if (options.mode === 'copy') {
			try {
				const copyData = uni.getStorageSync('checkin_copy_data');
				if (copyData) {
					this.selectedImages = copyData.images || [];
					this.selectedMealType = copyData.mealType || 'breakfast';
					this.remark = copyData.notes || '';
					
					// 清除缓存
					uni.removeStorageSync('checkin_copy_data');
					
					uni.showToast({
						title: '已加载打卡内容',
						icon: 'success'
					});
				}
			} catch (e) {
				console.error('读取复制数据失败:', e);
			}
		}
	},
	onUnload() {
		// 清理录音计时器
		this.stopRecordTimer();
		
		// 如果正在录音，停止录音
		if (this.isRecording && this.recorderManager) {
			this.recorderManager.stop();
		}
	},
	methods: {
		// 初始化录音管理器
		initRecorder() {
			// #ifdef MP-WEIXIN || APP-PLUS
			this.recorderManager = uni.getRecorderManager();
			
			// 录音开始事件
			this.recorderManager.onStart(() => {
				console.log('录音开始');
				this.recordDuration = 0;
				this.startRecordTimer();
			});
			
			// 录音结束事件
			this.recorderManager.onStop((res) => {
				console.log('录音结束', res);
				this.stopRecordTimer();
				
				if (res.duration < 1000) {
					uni.showToast({
						title: '录音时间太短',
						icon: 'none'
					});
					return;
				}
				
				// 处理录音结果
				this.handleRecordResult(res);
			});
			
			// 录音错误事件
			this.recorderManager.onError((err) => {
				console.error('录音错误:', err);
				this.isRecording = false;
				this.stopRecordTimer();
				uni.showToast({
					title: '录音失败，请重试',
					icon: 'none'
				});
			});
			// #endif
			
			// #ifdef H5
			console.log('H5环境暂不支持录音功能');
			// #endif
		},
		
		// 开始录音计时
		startRecordTimer() {
			this.recordTimer = setInterval(() => {
				this.recordDuration++;
				if (this.recordDuration >= 60) {
					// 录音超过60秒自动停止
					this.stopVoiceInput();
				}
			}, 1000);
		},
		
		// 停止录音计时
		stopRecordTimer() {
			if (this.recordTimer) {
				clearInterval(this.recordTimer);
				this.recordTimer = null;
			}
			this.recordDuration = 0;
		},
		
		// 处理语音备注按钮点击
		handleVoiceRemark() {
			if (this.isRecording) {
				this.stopVoiceInput();
			} else {
				this.startVoiceInput();
			}
		},
		
		// 开始语音输入
		startVoiceInput() {
			// #ifdef H5
			uni.showModal({
				title: '提示',
				content: 'H5环境暂不支持语音输入，请使用小程序或APP',
				showCancel: false
			});
			return;
			// #endif
			
			// #ifdef MP-WEIXIN || APP-PLUS
			if (!this.recorderManager) {
				uni.showToast({
					title: '录音功能初始化失败',
					icon: 'none'
				});
				return;
			}
			
			// 检查录音权限
			uni.authorize({
				scope: 'scope.record',
				success: () => {
					this.startRecording();
				},
				fail: () => {
					uni.showModal({
						title: '需要录音权限',
						content: '请在设置中开启录音权限',
						confirmText: '去设置',
						success: (res) => {
							if (res.confirm) {
								uni.openSetting();
							}
						}
					});
				}
			});
			// #endif
		},
		
		// 开始录音
		startRecording() {
			this.isRecording = true;
			
			uni.showToast({
				title: '开始录音',
				icon: 'none',
				duration: 1000
			});
			
			// 开始录音
			this.recorderManager.start({
				duration: 60000, // 最长录音60秒
				sampleRate: 16000,
				numberOfChannels: 1,
				encodeBitRate: 96000,
				format: 'mp3'
			});
		},
		
		// 停止语音输入
		stopVoiceInput() {
			if (!this.isRecording) {
				return;
			}
			
			this.isRecording = false;
			
			// #ifdef MP-WEIXIN || APP-PLUS
			if (this.recorderManager) {
				this.recorderManager.stop();
			}
			// #endif
			
			uni.showToast({
				title: '正在识别...',
				icon: 'loading',
				duration: 2000
			});
		},
		
		// 处理录音结果
		async handleRecordResult(res) {
			console.log('录音文件路径:', res.tempFilePath);
			
			try {
				// 1. 上传录音文件
				// 按照 oneclick.vue 的逻辑，使用 api.uploadFile 上传音频
				const uploadRes = await api.uploadFile(res.tempFilePath, {
					model: 'audio',
					pid: '8'
				});
				
				if (!uploadRes || uploadRes.code !== 200) {
					throw new Error('录音文件上传失败');
				}
				
				const audioUrl = uploadRes.data.fullUrl;
				console.log('录音文件上传成功，URL:', audioUrl);
				
				// 2. 识别语音
				const recognizedText = await this.recognizeSpeech(audioUrl);
				
				if (recognizedText) {
					// 将识别结果添加到备注中
					if (this.remark) {
						this.remark += ' ' + recognizedText;
					} else {
						this.remark = recognizedText;
					}
					
					uni.showToast({
						title: '识别成功',
						icon: 'success',
						duration: 1500
					});
				}
			} catch (error) {
				console.error('语音识别流程失败:', error);
				uni.showToast({
					title: '识别失败，请重试',
					icon: 'none',
					duration: 2000
				});
			}
		},
		
		// 语音识别（对接腾讯云语音识别服务）
		async recognizeSpeech(audioUrl) {
			try {
				// 创建语音识别任务
				console.log('创建语音识别任务, URL:', audioUrl);
				const createTaskRes = await api.createAsrTask({
					url: audioUrl,
					engineModelType: '16k_zh',
					channelNum: 1,
					resTextFormat: 0,
					sourceType: 0
				});
				
				if (!createTaskRes || createTaskRes.code !== 200) {
					throw new Error('创建识别任务失败');
				}
				
				const taskId = createTaskRes.data.taskId;
				console.log('识别任务创建成功，任务ID:', taskId);
				
				// 轮询查询识别结果
				const result = await this.pollAsrResult(taskId);
				
				// 解析识别文本
				return this.parseAsrResult(result);
				
			} catch (error) {
				console.error('语音识别请求失败:', error);
				throw error;
			}
		},
		
		// 轮询查询ASR识别结果
		async pollAsrResult(taskId, maxAttempts = 30, interval = 2000) {
			let attempts = 0;
			
			while (attempts < maxAttempts) {
				attempts++;
				
				try {
					const statusRes = await api.queryAsrStatus(taskId);
					
					if (!statusRes || statusRes.code !== 200) {
						throw new Error('查询识别状态失败');
					}
					
					const status = statusRes.data.status;
					
					// status: 0-等待处理, 1-处理中, 2-识别成功, 3-识别失败
					if (status === 2) {
						return statusRes.data;
					} else if (status === 3) {
						throw new Error(statusRes.data.errorMsg || '识别失败');
					}
					
					// 等待一段时间后继续查询
					await new Promise(resolve => setTimeout(resolve, interval));
					
				} catch (error) {
					console.error('查询识别状态出错:', error);
					if (attempts >= maxAttempts) throw error;
					await new Promise(resolve => setTimeout(resolve, interval));
				}
			}
			
			throw new Error('识别超时，请重试');
		},
		
		// 解析ASR识别结果文本
		parseAsrResult(data) {
			if (!data || !data.result) {
				return '';
			}
			
			let text = data.result;
			// 去除时间戳标记
			text = text.replace(/\[\d+:\d+\.\d+,\d+:\d+\.\d+\]\s*/g, '');
			// 去除多余的空格和换行
			text = text.replace(/\n+/g, ' ').trim();
			text = text.replace(/\s+/g, ' ');
			
			return text;
		},

		async chooseImage() {
			const maxCount = 6 - this.selectedImages.length;
			if (maxCount <= 0) return;
			
			try {
				const res = await new Promise((resolve, reject) => {
					uni.chooseImage({
						count: maxCount,
						sizeType: ['compressed'],
						sourceType: ['album', 'camera'],
						success: resolve,
						fail: reject
					});
				});

				uni.showLoading({
					title: '正在上传...',
					mask: true
				});

				for (const filePath of res.tempFilePaths) {
					try {
						const uploadResult = await api.uploadFile(filePath, {
							model: 'checkin',
							pid: '7'
						});

						if (uploadResult && uploadResult.code === 200) {
							// 直接保存完整的URL
							this.selectedImages.push(uploadResult.data.fullUrl);
						} else {
							console.error('上传失败:', uploadResult);
							uni.showToast({
								title: '部分图片上传失败',
								icon: 'none'
							});
						}
					} catch (uploadError) {
						console.error('上传异常:', uploadError);
					}
				}
				
				uni.hideLoading();

			} catch (error) {
				uni.hideLoading();
				console.error('选择图片失败', error);
				if (!error.errMsg || !error.errMsg.includes('cancel')) {
					uni.showToast({
						title: '选择图片失败',
						icon: 'none'
					});
				}
			}
		},
		removeImage(index) {
			this.selectedImages.splice(index, 1)
		},
		selectMealType(value) {
			this.selectedMealType = value
		},
		onRemarkInput(e) {
			this.remark = e.detail.value
		},

		toggleAIVideo(e) {
			this.enableAIVideo = e.detail.value
		},
		handleCancel() {
			uni.showModal({
				title: '提示',
				content: '确定要取消发布吗？',
				success: (res) => {
					if (res.confirm) {
						uni.navigateBack()
					}
				}
			})
		},
		async handlePublish() {
			if (this.selectedImages.length === 0) {
				uni.showToast({
					title: '请至少上传一张照片',
					icon: 'none'
				})
				return
			}
			// 防止重复提交
			if (this._publishing) return
			this._publishing = true
			
			uni.showLoading({ title: '发布中...' });

			try {
				const imageUrls = this.selectedImages;
				const today = new Date().toISOString().split('T')[0];
				const result = await submitCheckin({
					mealType: this.selectedMealType,
					date: today,
					photosJson: JSON.stringify(imageUrls),
					notes: this.remark,
					enableAIVideo: this.enableAIVideo,
					enableAIAnalysis: false
				});

				uni.hideLoading();

				const points = result.data?.points || 0;
				const taskId = result.data?.taskId;
				const successMsg = (this.enableAIVideo && taskId)
					? '打卡成功！视频生成中...'
					: `打卡成功！获得${points}积分`;
				uni.showToast({
					title: successMsg,
					icon: 'success',
					duration: 2000
				});
				
				// 延迟跳转
				setTimeout(() => {
					uni.redirectTo({
						url: '/pages/tool/dietary-records'
					});
				}, 1000);
			} catch (error) {
				uni.hideLoading();
				console.error('发布失败:', error);
				const msg = typeof error === 'string' ? error : (error && (error.message || error.msg));
				uni.showToast({
					title: msg || '发布失败，请重试',
					icon: 'none',
					duration: msg ? 2500 : 2000
				});
			} finally {
				this._publishing = false
			}
		}
	}
}
</script>

<style lang="scss" scoped>
.checkin-publish-page {
	min-height: 100vh;
	background: #f4f5f7;
	display: flex;
	flex-direction: column;
}

/* 内容滚动区域 */
.content-scroll {
	flex: 1;
	margin-bottom: 120rpx;
	padding: 32rpx 0;
}

/* 卡片样式 */
.card {
	background: #ffffff;
	border: 1rpx solid #d0dbea;
	border-radius: 24rpx;
	margin: 0 32rpx 32rpx;
	padding: 32rpx;
}

.card-header {
	display: flex;
	align-items: center;
	justify-content: space-between;
	margin-bottom: 24rpx;

	.card-title {
		font-size: 28rpx;
		color: #2e3e5c;
		font-weight: 500;
	}

	.photo-count {
		font-size: 24rpx;
		color: #9fa5c0;
	}

	.ai-header-left {
		display: flex;
		align-items: center;
		gap: 16rpx;

		.ai-icon {
			font-size: 32rpx;
		}
	}
}

/* 照片网格 */
.photo-grid {
	display: flex;
	flex-wrap: wrap;
	gap: 16rpx;
	margin-bottom: 24rpx;
}

.photo-item {
	width: 195rpx;
	height: 195rpx;
	border-radius: 24rpx;
	overflow: hidden;
	position: relative;
	background: #f4f5f7;

	.photo-image {
		width: 100%;
		height: 100%;
	}

	.photo-delete {
		position: absolute;
		right: 8rpx;
		top: 8rpx;
		width: 48rpx;
		height: 48rpx;
		background: rgba(0, 0, 0, 0.5);
		border-radius: 50%;
		display: flex;
		align-items: center;
		justify-content: center;

		.delete-icon {
			font-size: 32rpx;
			color: #ffffff;
			line-height: 1;
		}
	}
}

.photo-add-btn {
	width: 195rpx;
	height: 195rpx;
	border: 2rpx solid #d0dbea;
	border-radius: 24rpx;
	background: #f4f5f7;
	display: flex;
	flex-direction: column;
	align-items: center;
	justify-content: center;
	gap: 12rpx;

	.add-icon {
		font-size: 48rpx;
		color: #9fa5c0;
		line-height: 1;
	}

	.add-text {
		font-size: 24rpx;
		color: #9fa5c0;
	}
}

.photo-tip {
	background: #e3f2fd;
	border-radius: 16rpx;
	padding: 16rpx;
	display: flex;
	align-items: center;
	gap: 16rpx;

	.tip-icon {
		font-size: 32rpx;
	}

	.tip-text {
		flex: 1;
		font-size: 24rpx;
		color: #1976d2;
		line-height: 1.5;
	}
}

/* 餐次选择 */
.meal-type-list {
	display: flex;
	gap: 16rpx;
}

.meal-type-item {
	flex: 1;
	height: 70rpx;
	border: 2rpx solid #d0dbea;
	border-radius: 50rpx;
	background: #ffffff;
	display: flex;
	align-items: center;
	justify-content: center;
	font-size: 24rpx;
	color: #9fa5c0;
	transition: all 0.3s;

	&.active {
		background: #fff5f0;
		border-color: #ff6b35;
		color: #ff6b35;
	}
}

/* 备注说明 */
.remark-input {
	width: 100%;
	min-height: 200rpx;
	background: #ffffff;
	border: 1rpx solid #d0dbea;
	border-radius: 12rpx;
	padding: 16rpx;
	font-size: 28rpx;
	color: #2e3e5c;
	line-height: 1.6;
	margin-bottom: 16rpx;
}

.remark-footer {
	display: flex;
	align-items: center;
	justify-content: space-between;
}

.char-count {
	font-size: 24rpx;
	color: #9fa5c0;
}

.voice-btn {
	background: linear-gradient(135deg, #ff8c52 0%, #ff6b35 100%);
	border-radius: 50rpx;
	padding: 12rpx 32rpx;
	display: flex;
	align-items: center;
	gap: 12rpx;
	box-shadow: 0 4rpx 12rpx rgba(255, 107, 53, 0.3);
	transition: all 0.3s;

	.voice-icon {
		font-size: 32rpx;
		color: #ffffff;
	}

	.voice-text {
		font-size: 26rpx;
		color: #ffffff;
		font-weight: 500;
	}
	
	&:active {
		transform: scale(0.95);
		opacity: 0.9;
	}
	
	&.recording {
		background: linear-gradient(135deg, #ff4d4f 0%, #f5222d 100%);
		box-shadow: 0 4rpx 12rpx rgba(245, 34, 45, 0.3);
		
		.voice-text {
			color: #ffffff;
		}
		
		.voice-icon {
			animation: pulse 1s infinite;
			color: #ffffff;
		}
	}
}

@keyframes pulse {
	0% { opacity: 1; }
	50% { opacity: 0.5; }
	100% { opacity: 1; }
}

/* AI视频功能 */
.ai-switch {
	transform: scale(0.8);
}

.ai-features {
	display: flex;
	flex-direction: column;
	gap: 16rpx;
	margin-top: 24rpx;
}

.feature-item {
	display: flex;
	align-items: center;
	gap: 16rpx;

	.feature-check {
		font-size: 24rpx;
		color: #ff6b35;
		width: 24rpx;
		height: 24rpx;
		display: flex;
		align-items: center;
		justify-content: center;
	}

	.feature-text {
		font-size: 24rpx;
		color: #3e5481;
	}
}

/* 底部安全距离 */
.safe-bottom {
	height: 40rpx;
}

/* 底部操作栏 */
.bottom-bar {
	position: fixed;
	bottom: 0;
	left: 0;
	right: 0;
	height: 120rpx;
	background: #ffffff;
	border-top: 1rpx solid #d0dbea;
	padding: 24rpx 32rpx;
	display: flex;
	align-items: center;
	gap: 24rpx;
	z-index: 1000;
}

.cancel-btn {
	flex: 1;
	height: 96rpx;
	border: 2rpx solid #d0dbea;
	border-radius: 40rpx;
	background: #ffffff;
	display: flex;
	align-items: center;
	justify-content: center;

	text {
		font-size: 28rpx;
		color: #3e5481;
		font-weight: 500;
	}
}

.publish-btn {
	flex: 1;
	height: 96rpx;
	background: #ff6b35;
	border-radius: 40rpx;
	display: flex;
	align-items: center;
	justify-content: center;
	box-shadow: 0 8rpx 24rpx rgba(255, 107, 53, 0.3);

	text {
		font-size: 32rpx;
		color: #ffffff;
		font-weight: 500;
	}
}
</style>

