<template>
	<view class="page-container">
		<!-- Tab切换 -->
		<view class="tab-header">
			<view 
				class="tab-item" 
				:class="{ active: currentTab === 'isbn' }"
				@click="switchTab('isbn')"
			>
				<text class="tab-text">ISBN上传</text>
			</view>
			<view 
				class="tab-item" 
				:class="{ active: currentTab === 'no-isbn' }"
				@click="switchTab('no-isbn')"
			>
				<text class="tab-text">无ISBN上传</text>
			</view>
			<view 
				class="tab-item" 
				:class="{ active: currentTab === 'settings' }"
				@click="switchTab('settings')"
			>
				<text class="tab-text">⚙️</text>
			</view>
		</view>

		<view class="tab-swiper">
			<!-- ISBN上传内容 -->
			<view class="tab-panel" v-show="swiperIndex === 0">
				<view class="tab-content">
					<scroll-view class="content-scroll" scroll-y="true">
						<!-- 基本信息块（品相 + 货区&ISBN + 书名 + 价格&库存） -->
						<view class="info-block">
							<!-- 品相（标签在前） -->
							<view class="info-inline-row">
								<text class="info-inline-label">品相</text>
								<view class="condition-list" style="flex:1;">
									<view
										class="condition-item"
										v-for="(item, index) in conditionList"
										:key="index"
										:class="{ active: selectedCondition === item }"
										@click="selectCondition(item)"
									>
										<text class="condition-text">{{ item }}</text>
									</view>
								</view>
							</view>

							<view class="info-block-divider"></view>

							<!-- 货区 & ISBN -->
							<view class="info-block-row">
								<view class="field-label">
									<text class="label-text">货区 & ISBN</text>
								</view>
								<view class="inline-fields" style="flex:1;">
									<view class="inline-field narrow">
										<view class="picker-box" style="flex:1;" @click="openWarehousePicker('isbn')">
											<text class="picker-value">{{ isbnSelectedArea || '请选择货区' }}</text>
											<text class="picker-arrow">›</text>
										</view>
									</view>
									<view class="inline-field isbn-field">
										<view class="isbn-input-box" style="flex:1;">
											<input class="isbn-input" v-model="isbn" placeholder="ISBN或扫码" maxlength="13"/>
											<view class="scan-btn" @click="scanISBN">
												<text class="scan-icon">📷</text>
											</view>
											<view class="search-btn" @click="searchISBN">
												<text class="search-text">搜</text>
											</view>
										</view>
									</view>
								</view>
							</view>

							<view class="info-block-divider"></view>

							<!-- 书名（标签在前） -->
							<view class="info-inline-row">
								<text class="info-inline-label">书名</text>
								<input class="form-input info-inline-input" v-model="bookName" placeholder="请输入书名"/>
							</view>

							<view class="info-block-divider"></view>

							<!-- 价格 & 库存（标签在前） -->
							<view class="info-inline-row">
								<text class="info-inline-label">价格 & 库存</text>
								<view class="inline-fields" style="flex:1;">
									<view class="inline-field">
										<view class="price-input-box" style="flex:1;">
											<text class="price-symbol">¥</text>
											<input class="price-input" v-model="price" type="digit" placeholder="价格"/>
										</view>
									</view>
									<view class="inline-field">
										<input class="form-input" v-model="stock" type="number" placeholder="库存" style="flex:1;"/>
									</view>
								</view>
							</view>
						</view>

						<!-- 拍照 -->
						<view class="form-section">
							<view class="section-title">
								<text class="title-text">拍照</text>
								<text class="photo-count">已拍{{ photoList.length }}/9张</text>
							</view>
							<view class="photo-section">
								<view class="photo-list">
									<view class="photo-item" v-for="(photo, index) in photoList" :key="index">
										<image class="photo-image" :src="photo" mode="aspectFill" @click="previewPhoto(photo, index)"></image>
										<view class="photo-index-badge">
											<text class="photo-index-badge-text">{{ index + 1 }}</text>
										</view>
										<view class="photo-delete" @click="deletePhoto(index)">
											<text class="delete-icon">✕</text>
										</view>
									</view>
									<view class="photo-add" @click="takePhoto" v-if="photoList.length < 9">
										<text class="add-icon">+</text>
										<text class="add-text">单拍</text>
									</view>
									<view class="photo-add photo-burst" @click="openCameraCapture('isbn')" v-if="photoList.length < 9">
										<text class="add-icon" style="font-size:28rpx;">⚡</text>
										<text class="add-text">连拍</text>
									</view>
								</view>
							</view>
						</view>

						<!-- 市场竞争 & 在售商品（合并块） -->
						<view class="form-section">
							<!-- 市场统计 -->
							<view class="market-stats">
								<view class="stat-item">
									<text class="stat-label">在售</text>
									<text class="stat-value">{{ marketData.onSale }}</text>
								</view>
								<view class="stat-item">
									<text class="stat-label">旧</text>
									<text class="stat-value">{{ marketData.old }}</text>
								</view>
								<view class="stat-item">
									<text class="stat-label">新</text>
									<text class="stat-value">{{ marketData.new }}</text>
								</view>
								<view class="stat-item">
									<text class="stat-label">已售</text>
									<text class="stat-value">{{ marketData.sold }}</text>
								</view>
							</view>

							<view class="info-block-divider" style="margin:14rpx 0;"></view>

							<!-- 在售商品 -->
							<view class="section-header-row">
								<view class="section-title" style="margin-bottom:0;">
									<text class="title-text">在售商品</text>
								</view>
								<view class="compare-toggle">
									<text class="toggle-btn" :class="{ active: compareType === 'isbn' }" @click="switchCompare('isbn')">ISBN比价</text>
									<text class="toggle-btn" :class="{ active: compareType === 'name' }" @click="switchCompare('name')">书名比价</text>
								</view>
								<view class="sort-toggle">
									<text class="sort-btn" :class="{ active: sortBy === 'total' }" @click="sortProducts('total')">总价</text>
									<text class="sort-btn" :class="{ active: sortBy === 'book' }" @click="sortProducts('book')">书价</text>
								</view>
								<text class="filter-btn" @click="showMoreFilter">筛选</text>
							</view>
							
							<!-- 加载状态 -->
							<view class="loading-box" v-if="isLoading">
								<view class="loading-spinner"></view>
								<text class="loading-text">正在比价...</text>
							</view>
							
							<!-- 商品列表 -->
							<view class="product-grid" v-else>
								<view class="grid-item" v-for="(item, index) in sortedProductList.slice(0, 12)" :key="index">
									<image class="grid-image" :src="item.image" mode="aspectFill" @click="previewProductImage(index)" v-if="item.image"></image>
									<text class="grid-book-name">{{ item.bookName || '未知书名' }}</text>
									<text class="grid-author">{{ item.author || '' }}</text>
									<text class="grid-total-price">¥{{ item.totalPrice.toFixed(2) }}</text>
									<text class="grid-price-detail">书¥{{ item.bookPrice.toFixed(2) }}+运¥{{ item.shippingFee.toFixed(2) }}</text>
									<text class="grid-condition">{{ item.condition || '' }}</text>
									<text class="grid-shop">{{ item.shopName || '' }}</text>
								</view>

								<!-- 无数据提示 -->
								<view class="no-data" v-if="productList.length === 0">
									<text class="no-data-text">暂无在售商品，请先进行比价</text>
								</view>
							</view>
						</view>
						
						<!-- 上书记录 -->
						<view class="form-section">
							<view class="section-title">
								<text class="title-text">上书记录</text>
							</view>
							<view class="history-list">
								<view class="history-item" v-for="(item, index) in historyList" :key="index">
									<view class="history-row">
										<text class="history-date">{{ item.date }}</text>
										<text class="history-condition">{{ item.condition }}</text>
									</view>
									<view class="history-row">
										<text class="history-price">¥{{ item.price }}</text>
										<text class="history-stock">库存{{ item.stock }}本</text>
									</view>
								</view>
							</view>
						</view>

						<view class="bottom-placeholder"></view>
					</scroll-view>
				</view>
			</view>		<!-- /tab-panel ISBN -->

			<!-- 无ISBN上传内容 -->
			<view class="tab-panel" v-show="swiperIndex === 1">
				<view class="tab-content">
					<scroll-view class="content-scroll" scroll-y="true">

						<!-- ===== 基本信息块（品相 + 货区 + 书名 + 价格&库存） ===== -->
						<view class="info-block">
							<!-- 品相（标签在前） -->
							<view class="info-inline-row">
								<text class="info-inline-label">品相</text>
								<view class="condition-list" style="flex:1;">
									<view 
										class="condition-item" 
										v-for="(item, index) in conditionList" 
										:key="index"
										:class="{ active: noIsbnSelectedCondition === item }"
										@click="noIsbnSelectedCondition = item"
									>
										<text class="condition-text">{{ item }}</text>
									</view>
								</view>
							</view>

							<view class="info-block-divider"></view>

							<!-- 货区 -->
							<view class="info-block-row">
								<view class="field-label">
									<text class="label-text">货区</text>
								</view>
								<view class="picker-box" @click="openWarehousePicker('no-isbn')">
									<text class="picker-value">{{ noIsbnSelectedArea || '请选择货区' }}</text>
									<text class="picker-arrow">›</text>
								</view>
							</view>

							<view class="info-block-divider"></view>

							<!-- 书名（标签在前） -->
							<view class="info-inline-row">
								<text class="info-inline-label">书名</text>
								<view class="inline-fields" style="flex:1;">
									<view class="inline-field" style="flex:1;">
										<input class="form-input" v-model="noIsbnBookName" placeholder="请输入书名" style="flex:1;" />
									</view>
									<view class="inline-field" style="flex:none;">
										<view class="search-btn" @click="searchNoIsbn">
											<text class="search-text">搜</text>
										</view>
									</view>
									<view class="inline-field" style="flex:none;margin-left:10rpx;">
										<view class="scan-btn" @click="chooseImageNoIsbn">
											<text class="scan-icon">📷</text>
										</view>
									</view>
								</view>
							</view>

							<view class="info-block-divider"></view>

							<!-- 价格 & 库存（标签在前） -->
							<view class="info-inline-row">
								<text class="info-inline-label">价格 & 库存</text>
								<view class="inline-fields" style="flex:1;">
									<view class="inline-field" style="flex:1;">
										<view class="price-input-box" style="flex:1;">
											<text class="price-symbol">¥</text>
											<input class="price-input" v-model="noIsbnPrice" placeholder="售价" type="digit" />
										</view>
									</view>
									<view class="inline-field" style="flex:1;">
										<input class="form-input" v-model="noIsbnStock" type="number" placeholder="库存" style="flex:1;" />
									</view>
								</view>
							</view>
						</view>

						<!-- ===== 图书详情 ===== -->
						<view class="info-block" style="margin-top:16rpx;">
							<!-- 作者 -->
							<view class="info-inline-row">
								<text class="info-inline-label">作者</text>
								<view class="dropdown-wrapper" style="flex:1;">
									<input class="form-input" v-model="noIsbnAuthor" placeholder="请输入作者" style="flex:1;" />
									<view class="dropdown-btn" @click.stop="noIsbnAuthorDropdownVisible = !noIsbnAuthorDropdownVisible">▼</view>
									<view v-if="noIsbnAuthorDropdownVisible && noIsbnAuthorOptions.length > 0" class="dropdown-list">
										<view class="dropdown-item" v-for="(item, idx) in noIsbnAuthorOptions" :key="idx" @click="selectNoIsbnAuthor(item)">{{ item }}</view>
									</view>
								</view>
							</view>

							<view class="info-block-divider"></view>

							<!-- 出版社 -->
							<view class="info-inline-row">
								<text class="info-inline-label">出版社</text>
								<view class="dropdown-wrapper" style="flex:1;">
									<input class="form-input" v-model="noIsbnPublisher" placeholder="请输入出版社" style="flex:1;" />
									<view class="dropdown-btn" @click.stop="noIsbnPublisherDropdownVisible = !noIsbnPublisherDropdownVisible">▼</view>
									<view v-if="noIsbnPublisherDropdownVisible && noIsbnPublisherOptions.length > 0" class="dropdown-list">
										<view class="dropdown-item" v-for="(item, idx) in noIsbnPublisherOptions" :key="idx" @click="selectNoIsbnPublisher(item)">{{ item }}</view>
									</view>
								</view>
							</view>

							<view class="info-block-divider"></view>

							<!-- 印刷时间 -->
							<view class="info-inline-row">
								<text class="info-inline-label">印刷时间</text>
								<picker mode="multiSelector" :range="noIsbnPrintTimeColumns" @columnchange="onNoIsbnPrintTimeColumnChange" @change="onNoIsbnPrintTimeChange" :value="noIsbnPrintTimeIndexes" style="flex:1;">
									<view class="form-input picker-value-text">
										<text>{{ noIsbnPrintTime || '选择年/月' }}</text>
									</view>
								</picker>
							</view>

							<view class="info-block-divider"></view>

							<!-- 定价 -->
							<view class="info-inline-row">
								<text class="info-inline-label">定价</text>
								<view class="price-input-box" style="flex:1;">
									<text class="price-symbol">¥</text>
									<input class="price-input" v-model="noIsbnOriginalPrice" placeholder="请输入定价" type="digit" />
								</view>
							</view>

							<view class="info-block-divider"></view>

							<!-- 书号 -->
							<view class="info-inline-row">
								<text class="info-inline-label">书号</text>
								<input class="form-input" v-model="noIsbnUnifyIsbn" placeholder="请输入统一书号" style="flex:1;" />
							</view>

							<view class="info-block-divider"></view>

							<!-- ISBN -->
							<view class="info-inline-row">
								<text class="info-inline-label">ISBN</text>
								<input class="form-input" v-model="noIsbnIsbn" placeholder="请输入ISBN" type="number" style="flex:1;" />
							</view>

							<view class="info-block-divider"></view>

							<!-- 图书分类 -->
							<view class="info-inline-row">
								<text class="info-inline-label">图书分类</text>
								<view style="flex:1;">
									<picker v-if="noIsbnCategoryColumns.length > 0" mode="multiSelector" :range="noIsbnCategoryColumns" range-key="name" @columnchange="onNoIsbnCategoryColumnChange" @change="onNoIsbnCategoryChange" :value="noIsbnCategoryIndexes">
										<view class="category-select">
											<text class="category-value">{{ noIsbnCategoryPathText || '请选择分类' }}</text>
											<text class="picker-arrow">›</text>
										</view>
									</picker>
									<view v-else-if="noIsbnCategoryLoading" class="category-select">
										<text class="category-value" style="color:#999;">加载中...</text>
									</view>
									<view v-else class="category-select" @click="loadNoIsbnCategory">
										<text class="category-value" style="color:#999;">点击加载分类</text>
										<text class="picker-arrow">›</text>
									</view>
								</view>
							</view>

							<view class="info-block-divider"></view>

							<!-- 装订 -->
							<view class="info-inline-row">
								<text class="info-inline-label">装订</text>
								<view class="dropdown-wrapper" style="flex:1;">
									<input class="form-input" v-model="noIsbnBinding" placeholder="请选择装订" style="flex:1;" />
									<view class="dropdown-btn" @click.stop="noIsbnBindingDropdownVisible = !noIsbnBindingDropdownVisible">▼</view>
									<view v-if="noIsbnBindingDropdownVisible" class="dropdown-list">
										<view class="dropdown-item" v-for="(item, idx) in noIsbnBindingOptions" :key="idx" @click="selectNoIsbnBinding(item)">{{ item }}</view>
									</view>
								</view>
							</view>

							<view class="info-block-divider"></view>

							<!-- 开本 -->
							<view class="info-inline-row">
								<text class="info-inline-label">开本</text>
								<view class="dropdown-wrapper" style="flex:1;">
									<input class="form-input" v-model="noIsbnFormat" placeholder="请选择开本" style="flex:1;" />
									<view class="dropdown-btn" @click.stop="noIsbnFormatDropdownVisible = !noIsbnFormatDropdownVisible">▼</view>
									<view v-if="noIsbnFormatDropdownVisible" class="dropdown-list">
										<view class="dropdown-item" v-for="(item, idx) in noIsbnFormatOptions" :key="idx" @click="selectNoIsbnFormat(item)">{{ item }}</view>
									</view>
								</view>
							</view>

							<view class="info-block-divider"></view>

							<!-- 字数 -->
							<view class="info-inline-row">
								<text class="info-inline-label">字数</text>
								<input class="form-input" v-model="noIsbnWordCount" placeholder="请输入字数" type="number" style="flex:1;" />
							</view>
						</view>

						<!-- ===== 拍照 ===== -->
						<view class="form-section">
							<view class="section-title">
								<text class="title-text">拍照</text>
								<text class="photo-count">已拍{{ noIsbnPhotoList.length }}/9张</text>
							</view>
							<view class="photo-section">
								<view class="photo-list">
									<view class="photo-item" v-for="(photo, index) in noIsbnPhotoList" :key="index">
										<image class="photo-image" :src="photo" mode="aspectFill" @click="previewPhoto(photo, index)"></image>
										<view class="photo-index-badge">
											<text class="photo-index-badge-text">{{ index + 1 }}</text>
										</view>
										<view class="photo-delete" @click="deleteNoIsbnPhoto(index)">
											<text class="delete-icon">✕</text>
										</view>
									</view>
									<view class="photo-add" @click="takePhotoNoIsbn" v-if="noIsbnPhotoList.length < 9">
										<text class="add-icon">+</text>
										<text class="add-text">单拍</text>
									</view>
									<view class="photo-add photo-burst" @click="openCameraCapture('no-isbn')" v-if="noIsbnPhotoList.length < 9">
										<text class="add-icon" style="font-size:28rpx;">⚡</text>
										<text class="add-text">连拍</text>
									</view>
								</view>
							</view>
						</view>

						<!-- ===== 在售商品 ===== -->
						<view class="form-section" v-if="noIsbnProductList.length > 0">
							<!-- 市场统计 -->
							<view class="market-stats">
								<view class="stat-item">
									<text class="stat-label">在售</text>
									<text class="stat-value">{{ noIsbnMarketData.onSale }}</text>
								</view>
								<view class="stat-item">
									<text class="stat-label">旧</text>
									<text class="stat-value">{{ noIsbnMarketData.old }}</text>
								</view>
								<view class="stat-item">
									<text class="stat-label">新</text>
									<text class="stat-value">{{ noIsbnMarketData.new }}</text>
								</view>
								<view class="stat-item">
									<text class="stat-label">已售</text>
									<text class="stat-value">{{ noIsbnMarketData.sold }}</text>
								</view>
							</view>
							<view class="info-block-divider" style="margin:14rpx 0;"></view>
							<view class="section-header-row">
								<view class="section-title">
									<text class="title-text">在售商品</text>
								</view>
								<view class="copyright-btn" @click="searchNoIsbnCopyright">
									<text class="copyright-btn-text">版权页比价</text>
								</view>
							</view>
							<view class="loading-box" v-if="noIsbnLoading">
								<view class="loading-spinner"></view>
								<text class="loading-text">正在比价...</text>
							</view>
							<view class="product-grid" v-else>
								<view class="grid-item" v-for="(item, index) in noIsbnProductList" :key="index">
									<image class="grid-image" :src="item.image" mode="aspectFill" @click="previewProductImage(index)" v-if="item.image"></image>
									<text class="grid-book-name">{{ item.bookName || '未知书名' }}</text>
									<text class="grid-author">{{ item.author || '' }}</text>
									<text class="grid-total-price">¥{{ item.totalPrice.toFixed(2) }}</text>
									<text class="grid-price-detail">书¥{{ item.bookPrice.toFixed(2) }}+运¥{{ item.shippingFee.toFixed(2) }}</text>
									<text class="grid-condition">{{ item.condition || '' }}</text>
									<text class="grid-shop">{{ item.shopName || '' }}</text>
								</view>
								<view class="no-data" v-if="noIsbnProductList.length === 0">
									<text class="no-data-text">暂无在售商品</text>
								</view>
							</view>
						</view>

						<!-- ===== 上书记录 ===== -->
						<view class="form-section" v-if="noIsbnHistoryList.length > 0">
							<view class="section-title">
								<text class="title-text">上书记录</text>
							</view>
							<view class="history-list">
								<view class="history-item" v-for="(item, index) in noIsbnHistoryList" :key="index">
									<view class="history-row">
										<text class="history-date">{{ item.date }}</text>
										<text class="history-condition">{{ item.condition }}</text>
									</view>
									<view class="history-row">
										<text class="history-price">¥{{ item.price }}</text>
										<text class="history-stock">库存{{ item.stock }}本</text>
									</view>
								</view>
							</view>
						</view>

						<view class="bottom-placeholder"></view>
					</scroll-view>
				</view>
			</view>		<!-- /tab-panel 无ISBN -->

			<!-- 设置内容 -->
			<view class="tab-panel" v-show="swiperIndex === 2">
				<view class="tab-content">
					<view class="settings-swiper">
						<view class="settings-sub-tabs">
							<view class="settings-sub-tab" :class="{ active: settingsSubTabIndex === 0 }" @click="settingsSubTabIndex = 0">
								<text>账号</text>
							</view>
							<view class="settings-sub-tab" :class="{ active: settingsSubTabIndex === 1 }" @click="settingsSubTabIndex = 1">
								<text>屏蔽</text>
							</view>
							<view class="settings-sub-tab" :class="{ active: settingsSubTabIndex === 2 }" @click="settingsSubTabIndex = 2">
								<text>其他</text>
							</view>
						</view>
						<swiper :current="settingsSubTabIndex" @change="onSettingsSwiperChange" style="height:100%;">
							<swiper-item>
								<scroll-view class="content-scroll" scroll-y="true">
									<view class="form-section">
										<view class="section-title">
											<text class="title-text">账号管理</text>
										</view>
										<view class="logged-in-card" v-if="isLoggedIn">
											<view class="card-header">
												<view class="card-avatar"></view>
												<view class="card-user-info">
													<text class="card-shop-name">{{ shopName }}</text>
													<view class="card-region-row">
														<text class="card-region-icon">📍</text>
														<text class="card-region">{{ shopRegion }}</text>
													</view>
												</view>
											</view>
											<view class="card-footer">
												<text class="logout-btn-text" @click="handleLogout">退出登录</text>
											</view>
										</view>
										<view v-else>
											<view class="login-header">
												<text class="login-title">孔网账号登录</text>
											</view>
											<view class="login-form">
												<view class="input-row">
													<input class="form-input" v-model="loginAccount" placeholder="账号（手机号/用户名）" />
												</view>
												<view class="password-wrapper input-row">
													<input 
														class="form-input password-input" 
														v-model="loginPassword" 
														:type="showPassword ? 'text' : 'password'" 
														placeholder="密码"
													/>
													<view class="password-eye" @click="showPassword = !showPassword">
														<view class="eye-css">
															<view class="eye-open" :class="{ 'eye-active': showPassword }" v-if="showPassword">
																<view class="eye-open-inner">
																	<view class="pupil"></view>
																</view>
															</view>
															<view class="eye-close" v-else>
																<view class="eye-close-line"></view>
															</view>
														</view>
													</view>
												</view>
												<view class="checkbox-row">
													<switch :checked="rememberPassword" @change="rememberPassword = $event.detail.value" color="#409eff" style="transform:scale(0.7)" />
													<text class="checkbox-label">记住密码</text>
												</view>
												<view class="login-btn" @click="handleLogin">登录</view>
											</view>
										</view>
										<!-- 已保存账号列表 -->
										<view class="saved-accounts" v-if="savedAccountList.length > 0">
											<view class="saved-header">
												<text class="saved-title">已保存账号</text>
												<text class="saved-count">{{ savedAccountList.length }}个</text>
											</view>
											<view class="saved-list">
												<view
													class="saved-item"
													v-for="(acc, idx) in savedAccountList"
													:key="idx"
													@click="quickLogin(acc)"
												>
													<view class="saved-item-left">
														<view class="saved-avatar">&#128100;</view>
														<view class="saved-info">
															<text class="saved-name">{{ acc.username }}</text>
															<text class="saved-hint">点击直接登录</text>
														</view>
													</view>
													<text class="saved-del" @click.stop="deleteSavedAccount(idx)">删除</text>
												</view>
											</view>
										</view>
									</view>
								</scroll-view>
							</swiper-item>
							<swiper-item>
								<scroll-view class="content-scroll" scroll-y="true">
									<view class="form-section">
										<view class="section-title">
											<text class="title-text">屏蔽设置</text>
										</view>
										<text class="section-desc">填写后屏蔽指定ISBN或名称的商品</text>
										<textarea class="blocked-textarea" v-model="blockedList" placeholder="每行一个，支持ISBN或书名关键词" />
									</view>
								</scroll-view>
							</swiper-item>
							<swiper-item>
								<scroll-view class="content-scroll" scroll-y="true">
									<view class="form-section">
										<view class="section-title">
											<text class="title-text">定价策略</text>
										</view>
										<text class="section-desc">设置自动定价规则，影响比价结果的参考价格计算</text>
										
										<!-- 模式切换 -->
										<view class="mode-tabs">
											<view class="mode-tab" :class="{ active: priceMode === 'lowest' }" @click="priceMode = 'lowest'">
												<text class="mode-tab-text">最低价</text>
											</view>
											<view class="mode-tab" :class="{ active: priceMode === 'average' }" @click="priceMode = 'average'">
												<text class="mode-tab-text">均价</text>
											</view>
										</view>
										
										<!-- 最低价模式 -->
										<view v-if="priceMode === 'lowest'">
											<view class="config-field">
												<text class="config-label">以最低价为参照物（第{{ lowestRank }}条）</text>
												<text class="config-desc">选择第几条数据作为参考价</text>
												<view class="picker-wrap">
													<picker :value="lowestRank - 1" :range="lowestOptions" @change="e => lowestRank = e.detail.value + 1">
														<view class="picker-btn">
															<text class="picker-btn-text">第 {{ lowestRank }} 条</text>
															<text class="picker-arrow">›</text>
														</view>
													</picker>
												</view>
											</view>
											<view class="config-field">
												<text class="config-label">运费</text>
												<text class="config-desc">每单运费金额</text>
												<input class="num-input-field" v-model="shippingFee" type="digit" placeholder="0.00" @input="onDecimalInput('shippingFee', $event)" />
											</view>
											<view class="config-field">
												<text class="config-label">占位降价</text>
												<text class="config-desc">在参考价基础上降低的金额</text>
												<input class="num-input-field" v-model="priceDiscount" type="digit" placeholder="0.00" @input="onDecimalInput('priceDiscount', $event)" />
											</view>
											<view class="config-field">
												<text class="config-label">最低书价（不含运费）</text>
												<text class="config-desc">设置后的价格不低于此金额</text>
												<input class="num-input-field" v-model="minBookPrice" type="digit" placeholder="0.00" @input="onDecimalInput('minBookPrice', $event)" />
											</view>
										</view>
										
										<!-- 均价模式 -->
										<view v-if="priceMode === 'average'">
											<view class="config-field">
												<text class="config-label">以总价最低的{{ averageCount }}个价格平均值为参考物</text>
												<text class="config-desc">选择前{{ averageCount }}条数据取平均值</text>
												<view class="picker-wrap">
													<picker :value="averageCount - 2" :range="averageOptions" @change="e => averageCount = e.detail.value + 2">
														<view class="picker-btn">
															<text class="picker-btn-text">前 {{ averageCount }} 条</text>
															<text class="picker-arrow">›</text>
														</view>
													</picker>
												</view>
											</view>
											<view class="config-field">
												<text class="config-label">运费</text>
												<text class="config-desc">每单运费金额</text>
												<input class="num-input-field" v-model="shippingFee" type="digit" placeholder="0.00" @input="onDecimalInput('shippingFee', $event)" />
											</view>
											<view class="config-field">
												<text class="config-label">占位降价</text>
												<text class="config-desc">在参考价基础上降低的金额</text>
												<input class="num-input-field" v-model="priceDiscount" type="digit" placeholder="0.00" @input="onDecimalInput('priceDiscount', $event)" />
											</view>
											<view class="config-field">
												<text class="config-label">最低书价（不含运费）</text>
												<text class="config-desc">设置后的价格不低于此金额</text>
												<input class="num-input-field" v-model="minBookPrice" type="digit" placeholder="0.00" @input="onDecimalInput('minBookPrice', $event)" />
											</view>
										</view>
										
										<view class="save-config-btn" @click="savePriceConfig">
											<text>保存设置</text>
										</view>
									</view>
								</scroll-view>
							</swiper-item>
						</swiper>
					</view>
				</view>
			</view>		<!-- /tab-panel 设置 -->
		</view>		<!-- /tab-swiper -->

		<!-- 底部提交栏 -->
		<view class="bottom-bar">
			<view class="submit-btn" @click="submitUpload">
				<text class="submit-text">确认上传</text>
			</view>
		</view>

		<!-- 筛选弹窗 -->
		<view class="filter-popup" v-if="showFilterPopup" @click="showFilterPopup = false">
			<view class="popup-content" @click.stop>
				<view class="popup-header">
					<text class="popup-title">筛选在售商品</text>
					<text class="popup-close" @click="showFilterPopup = false">✕</text>
				</view>
				<view class="popup-body">
					<view class="filter-group" v-if="filterPublishers.length > 0">
						<text class="group-title">出版社</text>
						<view class="tag-list">
							<view 
								class="tag-item" 
								v-for="(item, index) in filterPublishers" 
								:key="'p'+index"
								:class="{ active: filterPress === item }"
								@click="filterPress = filterPress === item ? '' : item"
							>
								<text class="tag-text">{{ item }}</text>
							</view>
						</view>
					</view>
					<view class="filter-group" v-if="filterAuthors.length > 0">
						<text class="group-title">作者</text>
						<view class="tag-list">
							<view 
								class="tag-item" 
								v-for="(item, index) in filterAuthors" 
								:key="'a'+index"
								:class="{ active: filterAuthor === item }"
								@click="filterAuthor = filterAuthor === item ? '' : item"
							>
								<text class="tag-text">{{ item }}</text>
							</view>
						</view>
					</view>
				</view>
				<view class="popup-footer">
					<view class="reset-btn" @click="resetFilter">重置</view>
					<view class="confirm-btn" @click="applyFilter">确定</view>
				</view>
			</view>
		</view>

		<!-- 仓库货位选择弹窗 -->
		<view class="warehouse-overlay" v-if="showWarehousePicker" @click="closeWarehousePicker">
			<view class="warehouse-popup" @click.stop>
				<view class="popup-header">
					<text class="popup-title">选择仓库货位</text>
					<text class="popup-close" @click="closeWarehousePicker">✕</text>
				</view>
				<view class="popup-body wh-tabs-body">
					<scroll-view class="wh-tabs-bar" scroll-x :show-scrollbar="false">
						<view 
							class="wh-tab" 
							v-for="(w, idx) in popupWarehouseList" 
							:key="w.id"
							:class="{ active: popupActiveWhIndex === idx }"
							@click="selectPopupWarehouse(idx)"
						>
							<text class="wh-tab-text">{{ w.name }}</text>
						</view>
					</scroll-view>
					<!-- 货位搜索 -->
					<view class="wh-search-bar">
						<input class="wh-search-input" v-model="popupLocationSearch" placeholder="搜索货位编码/名称" @input="onLocationSearchInput" />
						<text class="wh-search-clear" v-if="popupLocationSearch" @click="clearLocationSearch">✕</text>
						<text class="wh-scan-btn" @click="scanLocationBarcode">📷</text>
					</view>
					<scroll-view class="wh-location-list" scroll-y :refresher-enabled="true" :refresher-triggered="popupRefreshing" @refresherrefresh="onPopupRefresh" @scrolltolower="loadMorePopupLocation">
						<view 
							class="wh-loc-item" 
							v-for="loc in filteredLocationList" 
							:key="loc.id"
							:class="{ active: popupSelectedLoc && popupSelectedLoc.id === loc.id }"
							@click="selectPopupLocation(loc)"
						>
							<text class="wh-loc-code">{{ loc.code }}</text>
							<text class="wh-loc-check" v-if="popupSelectedLoc && popupSelectedLoc.id === loc.id">✓</text>
						</view>
						<view class="popup-loading" v-if="popupLocLoadingMore">
							<view class="mini-spinner"></view>
							<text>加载中...</text>
						</view>
						<view class="popup-hint-end" v-if="!popupLocHasMore && popupLocationList.length > 0">
							<text>— 已全部加载 —</text>
						</view>
						<view class="popup-hint" v-if="filteredLocationList.length === 0 && !popupLoadingLocation">
							<text>暂无货位</text>
						</view>
						<view class="popup-hint" v-if="popupLoadingLocation">
							<view class="loading-spinner" style="width:40rpx;height:40rpx;"></view>
							<text>加载中...</text>
						</view>
					</scroll-view>
				</view>
				<view class="popup-footer">
					<view class="popup-footer-btn cancel" @click="closeWarehousePicker">取消</view>
					<view class="popup-footer-btn confirm" :class="{ disabled: !popupSelectedLoc }" @click="confirmWarehousePicker">确定</view>
				</view>
			</view>
		</view>
		
		<!-- 扫码结果弹窗 -->
		<view class="scan-result-overlay" v-if="showScanPopup" @click="closeScanPopup">
			<view class="scan-result-popup" @click.stop>
				<view class="popup-scan-header">
					<text class="popup-scan-title">扫码结果</text>
					<text class="popup-scan-close" @click="closeScanPopup">✕</text>
				</view>
				<view class="popup-scan-content">
					<view class="scan-result-row" v-if="scanPopupWhCode">
						<text class="scan-result-label">仓库编码</text>
						<text class="scan-result-value">{{ scanPopupWhCode }}</text>
					</view>
					<view class="scan-result-row" v-if="scanPopupLocCode">
						<text class="scan-result-label">货位号</text>
						<text class="scan-result-value">{{ scanPopupLocCode }}</text>
					</view>
					<view class="scan-result-row" v-if="!scanPopupWhCode && !scanPopupLocCode">
						<text class="scan-result-label">条码内容</text>
						<text class="scan-result-value">{{ scanPopupRaw }}</text>
					</view>
					<text class="scan-result-hint">点击「搜索」查询匹配货位</text>
				</view>
				<view class="popup-scan-footer">
					<view class="popup-scan-btn popup-scan-cancel" @click="closeScanPopup">取消</view>
					<view class="popup-scan-btn popup-scan-confirm" @click="confirmScanSearch">搜索</view>
				</view>
			</view>
		</view>

		<!-- 无ISBN已有图书选择弹窗 -->
		<view class="noisbn-book-mask" v-if="noIsbnBookPopupVisible" @click="closeNoIsbnBookPopup">
			<view class="noisbn-book-popup" @click.stop>
				<view class="noisbn-book-header">
					<text class="noisbn-book-title">已查到 {{ noIsbnBookList.length }} 条记录，点击选择</text>
					<text class="noisbn-book-close" @click="closeNoIsbnBookPopup">✕</text>
				</view>
				<scroll-view class="noisbn-book-scroll" scroll-y>
					<view class="noisbn-book-item" v-for="(item, idx) in noIsbnBookList" :key="idx" @click="selectNoIsbnBookItem(item)">
						<view class="noisbn-book-item-num">{{ idx + 1 }}</view>
						<view class="noisbn-book-item-body">
							<view class="noisbn-book-item-name">{{ item.book_name || '' }}</view>
							<view class="noisbn-book-item-meta" v-if="item.author || item.publishing || item.isbn">
								<text v-if="item.author" class="meta-tag">作者:{{ item.author }}</text>
								<text v-if="item.publishing" class="meta-tag">出版社:{{ item.publishing }}</text>
								<text v-if="item.isbn" class="meta-tag">ISBN:{{ item.isbn }}</text>
							</view>
						</view>
						<text class="noisbn-book-item-arrow">›</text>
					</view>
				</scroll-view>
				<view class="noisbn-book-footer">
					<view class="noisbn-book-btn noisbn-book-cancel" @click="closeNoIsbnBookPopup">取消</view>
				</view>
			</view>
		</view>
	</view>
</template>

<script>
import { getWarehouseList, getLocationList, searchBookByIsbn, calculateSign, buildFormBodyWithImages } from '@/utils/api.js'
import { login as kongfzLogin, searchProducts, searchFacet } from '@/utils/kongfz.js'
import { uploadImages } from '@/utils/minio.js'

export default {
	data() {
		return {
			currentTab: 'isbn',
			swiperIndex: 0,
			settingsSubTabIndex: 0,
			
			// ISBN表单
			isbn: '',
			bookName: '',
			author: '',
			publisher: '',
			fixPrice: '',
			printTime: '',
			price: '',
			stock: 1,
			selectedCondition: '八五品',
			conditionList: ['六品', '七品', '八品', '八五品', '九品', '九五品', '全新'],
			photoList: [],
			isbnSelectedArea: '',
			isbnWarehouseData: null,
			marketData: { onSale: 0, old: 0, new: 0, sold: 0 },
			productList: [],
			compareType: 'isbn',
			sortBy: 'total',
			historyList: [],
			isSubmitting: false,
			isLoading: false,
			
			// 无ISBN表单
			noIsbnPrintTime: '',
			noIsbnPrintTimeIndexes: [0, 0],
			noIsbnBookName: '',
			noIsbnAuthor: '',
			noIsbnPublisher: '',
			noIsbnFormat: '',
			noIsbnBinding: '',
			noIsbnOriginalPrice: '',
			noIsbnWordCount: '',
			noIsbnIsbn: '',
			noIsbnUnifyIsbn: '',
			noIsbnSelectedCondition: '八五品',
			noIsbnPrice: '',
			noIsbnStock: 1,
			noIsbnPhotoList: [],
			noIsbnSelectedArea: '',
			noIsbnWarehouseData: null,
			capturedPhotoList: null,
			capturedPhotoTab: '',
			
			// 无ISBN - 下拉列表
			noIsbnAuthorOptions: [],
			noIsbnAuthorDropdownVisible: false,
			noIsbnPublisherOptions: [],
			noIsbnPublisherDropdownVisible: false,
			noIsbnFormatDropdownVisible: false,
			noIsbnBindingDropdownVisible: false,

			// 开本选项（无ISBN专用）
			noIsbnFormatOptions: ['2', '4', '6', '8', '12', '16', '18', '20', '24', '32', '36', '40', '42', '48', '50', '60', '64', '72', '大16', '大32', '其他'],

			// 装订选项（无ISBN专用）
			noIsbnBindingOptions: ['平装', '精装', '软精装', '线装', '其他'],

			// 无ISBN已有图书弹窗
			noIsbnBookPopupVisible: false,
			noIsbnBookList: [],
			
			// 分类（从API加载）
			noIsbnCategoryData: [],
			noIsbnCategoryColumns: [],
			noIsbnCategoryIndexes: [],
			noIsbnCategoryLevels: [],
			noIsbnMaxCategoryLevel: 3,
			noIsbnCategoryPathText: '',
			noIsbnCategoryLoading: false,
			noIsbnSelectedCategoryId: '',
			
			// 无ISBN - 市场竞争/在售
			noIsbnProductList: [],
			noIsbnHistoryList: [],
			noIsbnLoading: false,
			noIsbnMarketData: { onSale: 0, old: 0, new: 0, sold: 0 },

			// 筛选
			showFilterPopup: false,
			filterPress: '',
			filterAuthor: '',
			
			// 仓库弹窗
			showWarehousePicker: false,
			pickerTargetTab: 'isbn',
			popupWarehouseList: [],
			popupActiveWhIndex: 0,
			popupLocationList: [],
			popupSelectedWh: null,
			popupSelectedLoc: null,
			popupLoading: false,
			popupLoadingLocation: false,
			popupLocPage: 1,
			popupLocPageSize: 20,
			popupLocHasMore: true,
			popupLocLoadingMore: false,
			popupLocationSearch: '',
			popupAllLocationList: [],
			popupLocTotal: 0,
			popupRefreshing: false,
			_pendingPreselectWh: null,
			_pendingPreselectLoc: null,
			
			// 扫码弹窗
			showScanPopup: false,
			scanPopupWhCode: '',
			scanPopupLocCode: '',
			scanPopupRaw: '',
			
			// 登录
			isLoggedIn: false,
			shopName: '',
			shopRegion: '',
			loginAccount: '',
			loginPassword: '',
			showPassword: false,
			rememberPassword: false,
			blockedList: '',
			kongfzToken: '',
			savedAccountList: [],
			
			// 定价策略
			priceMode: 'lowest',  // lowest | average
			lowestRank: 1,
			averageCount: 2,
			shippingFee: 0,
			priceDiscount: 0,
			minBookPrice: 0
		}
	},

	onLoad(options) {
		uni.setNavigationBarTitle({ title: '图书上传' })
		if (options && options.tab) {
			this.currentTab = options.tab
			this.swiperIndex = options.tab === 'no-isbn' ? 1 : 0
		}
		// 恢复登录状态
		const savedToken = uni.getStorageSync('kongfz_phpsessid')
		const savedName = uni.getStorageSync('kongfz_shop_name')
		if (savedToken && savedName) {
			this.kongfzToken = savedToken
			this.shopName = savedName
			this.shopRegion = uni.getStorageSync('kongfz_shop_region') || '孔夫子旧书网'
			this.isLoggedIn = true
		}
		// 恢复记住的账号
		const remembered = uni.getStorageSync('kongfz_remembered_account')
		if (remembered) {
			this.loginAccount = remembered
			this.rememberPassword = true
		}
		// 加载已保存账号列表
		this.loadSavedAccounts()
		// 恢复定价策略配置
		this.loadPriceConfig()
		// 预加载图书分类
		this.loadNoIsbnCategory()
		// 初始化印刷时间选择器默认值
		this.syncNoIsbnPrintTimeIndexes()
		// 恢复选择的仓库货位
		const savedWhData = uni.getStorageSync('selectedWarehouseData')
		if (savedWhData) {
			const locationText = savedWhData.warehouseName + ' - ' + savedWhData.locationCode
			const whData = {
				warehouseId: savedWhData.warehouseId,
				warehouseName: savedWhData.warehouseName,
				warehouseCode: savedWhData.warehouseCode,
				locationId: savedWhData.locationId,
				locationName: savedWhData.locationName,
				locationCode: savedWhData.locationCode,
				code: savedWhData.locationCode,
				name: savedWhData.locationName
			}
			this.isbnSelectedArea = locationText
			this.isbnWarehouseData = whData
			this.noIsbnSelectedArea = locationText
			this.noIsbnWarehouseData = whData
		}
	},

	computed: {
		conditionValue() {
			const map = {
				'全新': '100~',
				'九五品': '95~',
				'九品': '90~',
				'八五品': '85~',
				'八品': '80~',
				'七品': '70~',
				'六品': '60~'
			}
			return this.selectedCondition ? (map[this.selectedCondition] || '') : ''
		},
		noIsbnConditionValue() {
			const map = {
				'全新': '100~',
				'九五品': '95~',
				'九品': '90~',
				'八五品': '85~',
				'八品': '80~',
				'七品': '70~',
				'六品': '60~'
			}
			return this.noIsbnSelectedCondition ? (map[this.noIsbnSelectedCondition] || '') : ''
		},
		calculatedPrice() {
			const sorted = this.sortedProductList
			if (sorted.length === 0) return 0
			const shipping = Number(this.shippingFee) || 0
			const discount = Number(this.priceDiscount) || 0
			const minPrice = Number(this.minBookPrice) || 0
			let result = 0
			if (this.priceMode === 'lowest') {
				const idx = Math.min((Number(this.lowestRank) || 1) - 1, sorted.length - 1)
				const selectedTotal = parseFloat(sorted[idx].totalPrice) || 0
				result = selectedTotal - shipping - discount
			} else {
				const count = Math.min(Number(this.averageCount) || 2, sorted.length)
				let sum = 0
				for (let i = 0; i < count; i++) {
					sum += parseFloat(sorted[i].totalPrice) || 0
				}
				result = (sum / count) - shipping - discount
			}
			if (result <= minPrice) return minPrice
			return parseFloat(result.toFixed(2))
		},
		// ISBN - 核价商品的运费
		referenceShippingFee() {
			const sorted = this.sortedProductList
			if (sorted.length === 0) return 0
			if (this.priceMode === 'lowest') {
				const idx = Math.min((Number(this.lowestRank) || 1) - 1, sorted.length - 1)
				return parseFloat(sorted[idx].shippingFee) || 0
			} else {
				const count = Math.min(Number(this.averageCount) || 2, sorted.length)
				return parseFloat(sorted[count - 1].shippingFee) || 0
			}
		},
		// 无ISBN - 核价商品的运费
		noIsbnReferenceShippingFee() {
			const sorted = this.noIsbnSortedProductList
			if (sorted.length === 0) return 0
			if (this.priceMode === 'lowest') {
				const idx = Math.min((Number(this.lowestRank) || 1) - 1, sorted.length - 1)
				return parseFloat(sorted[idx].shippingFee) || 0
			} else {
				const count = Math.min(Number(this.averageCount) || 2, sorted.length)
				return parseFloat(sorted[count - 1].shippingFee) || 0
			}
		},
		sortedProductList() {
			let list = [...this.productList]
			// 筛选（精确匹配，同zhizhu）
			if (this.filterPress) {
				list = list.filter(item => item.press === this.filterPress)
			}
			if (this.filterAuthor) {
				list = list.filter(item => item.author === this.filterAuthor)
			}
			// 排序
			if (this.sortBy === 'total') {
				list.sort((a, b) => parseFloat(a.totalPrice) - parseFloat(b.totalPrice))
			} else if (this.sortBy === 'book') {
				list.sort((a, b) => parseFloat(a.bookPrice || 0) - parseFloat(b.bookPrice || 0))
			}
			return list
		},
		// 无ISBN - 按售价策略排序的商品列表
		noIsbnSortedProductList() {
			let list = [...this.noIsbnProductList].slice(0, 12)
			list.sort((a, b) => parseFloat(a.totalPrice) - parseFloat(b.totalPrice))
			return list
		},
		// 无ISBN - 自动计算售价（策略与ISBN页一致）
		calculatedNoIsbnPrice() {
			const sorted = this.noIsbnSortedProductList
			if (sorted.length === 0) return 0
			const shipping = Number(this.shippingFee) || 0
			const discount = Number(this.priceDiscount) || 0
			const minPrice = Number(this.minBookPrice) || 0
			let result = 0
			if (this.priceMode === 'lowest') {
				const idx = Math.min((Number(this.lowestRank) || 1) - 1, sorted.length - 1)
				const selectedTotal = parseFloat(sorted[idx].totalPrice) || 0
				result = selectedTotal - shipping - discount
			} else {
				const count = Math.min(Number(this.averageCount) || 2, sorted.length)
				let sum = 0
				for (let i = 0; i < count; i++) {
					sum += parseFloat(sorted[i].totalPrice) || 0
				}
				result = (sum / count) - shipping - discount
			}
			if (result <= minPrice) return minPrice
			return parseFloat(result.toFixed(2))
		},
		filterPublishers() {
			const set = new Set()
			this.productList.slice(0, 12).forEach(item => {
				if (item.press) set.add(item.press)
			})
			return Array.from(set)
		},
		filterAuthors() {
			const set = new Set()
			this.productList.slice(0, 12).forEach(item => {
				if (item.author) set.add(item.author)
			})
			return Array.from(set)
		},
		lowestOptions() {
			const arr = []
			for (let i = 1; i <= 12; i++) arr.push(i)
			return arr
		},
		averageOptions() {
			const arr = []
			for (let i = 2; i <= 12; i++) arr.push(i)
			return arr
		},
		noIsbnYearOptions() {
			const arr = []
			const cur = new Date().getFullYear()
			for (let i = 800; i <= cur; i++) arr.push(String(i))
			return arr
		},
		noIsbnMonthOptions() {
			const arr = []
			for (let i = 1; i <= 12; i++) arr.push(String(i).padStart(2, '0'))
			return arr
		},
		noIsbnPrintTimeColumns() {
			return [this.noIsbnYearOptions, this.noIsbnMonthOptions]
		},
		filteredLocationList() {
			if (!this.popupLocationSearch) return this.popupLocationList
			const kw = this.popupLocationSearch.toLowerCase()
			return this.popupAllLocationList.filter(loc => {
				const code = (loc.code || '').toLowerCase()
				const name = (loc.name || '').toLowerCase()
				return code.includes(kw) || name.includes(kw)
			})
		}
	},

	watch: {
		noIsbnSelectedCondition() {
			// 品相变化时重新搜索在售商品（无ISBN页）
			if (this.noIsbnProductList.length > 0 && this.noIsbnBookName && this.isLoggedIn) {
				this.searchNoIsbn()
			}
		},
		selectedCondition() {
			// 品相变化时重新搜索在售商品（ISBN页）
			if (this.productList.length > 0 && this.isbn && this.isLoggedIn) {
				this.searchISBN()
			}
		},
		noIsbnPrintTime() {
			this.syncNoIsbnPrintTimeIndexes()
		},
		noIsbnUnifyIsbn(val) {
			// 10位书号（ISBN-10）自动转为13位ISBN填入ISBN字段
			// 去掉分隔符（-、空格）后检测是否为10位ISBN
			var clean = (val || '').replace(/[-\s]/g, '')
			if (clean.length === 10 && /^\d{9}[\dXx]$/i.test(clean)) {
				if (!this.noIsbnIsbn) {
					this.noIsbnIsbn = this.convertIsbn10To13(clean)
				}
			}
		}
	},

	// 页面显示时处理连拍返回的照片
	onShow() {
		if (this.capturedPhotoList && this.capturedPhotoList.length > 0) {
			var photos = this.capturedPhotoList
			var targetTab = this.capturedPhotoTab || 'no-isbn'
			if (targetTab === 'isbn') {
				this.photoList = [...this.photoList, ...photos]
			} else {
				this.noIsbnPhotoList = [...this.noIsbnPhotoList, ...photos]
			}
			this.capturedPhotoList = null
			this.capturedPhotoTab = ''
		}
	},

	methods: {
		// ISBN-10 转 ISBN-13
		convertIsbn10To13(clean) {
			if (!clean || clean.length !== 10) return ''
			// 前9位 + 前缀978
			var digits = '978' + clean.slice(0, 9)
			// 计算ISBN-13校验码
			var sum = 0
			for (var i = 0; i < 12; i++) {
				var digit = parseInt(digits[i], 10)
				sum += i % 2 === 0 ? digit : digit * 3
			}
			var check = (10 - (sum % 10)) % 10
			return digits + check
		},

		// 标签切换
		switchTab(tab) {
			const idx = tab === 'isbn' ? 0 : tab === 'no-isbn' ? 1 : 2
			this.swiperIndex = idx
			this.currentTab = tab
			if (tab === 'settings') {
				this.settingsSubTabIndex = 0
			}
		},

		onTabSwiperChange(e) {
			const idx = e.detail.current
			this.swiperIndex = idx
			const tabs = ['isbn', 'no-isbn', 'settings']
			this.currentTab = tabs[idx]
		},

		onSettingsSwiperChange(e) {
			this.settingsSubTabIndex = e.detail.current
		},

		// ISBN扫码
		scanISBN() {
			// 必须已登录孔网
			if (!this.isLoggedIn) {
				uni.showToast({ title: '请先登录孔网账号', icon: 'none' })
				return
			}
			// 手机系统原生扫码（实时识别，对准即出结果）
			uni.scanCode({
				onlyFromCamera: true,
				scanType: ['barcode'],
				success: (res) => {
					this.isbn = (res.result || '').trim()
					this.searchISBN()
				},
				fail: () => {}
			})
		},

		// ISBN搜索 - 查询图书中心 + 孔网市场
		searchISBN() {
			// 必须已登录孔网
			if (!this.isLoggedIn) {
				uni.showToast({ title: '请先登录孔网账号', icon: 'none' })
				return
			}
			var that = this
			let keyword = ''
			if (this.compareType === 'isbn') {
				if (!this.isbn) {
					uni.showToast({ title: '请输入ISBN', icon: 'none' })
					return
				}
				keyword = this.isbn
			} else {
				if (!this.bookName) {
					uni.showToast({ title: '请输入书名', icon: 'none' })
					return
				}
				keyword = this.bookName
			}
			this.isLoading = true
			this.productList = []

			// 1. 查询图书中心 - 获取图书详情（仅ISBN模式）
			if (this.compareType === 'isbn') {
				searchBookByIsbn(this.isbn).then(data => {
					if (data.book_name) this.bookName = data.book_name
					if (data.author) this.author = data.author
					if (data.publisher) this.publisher = data.publisher
					if (data.fix_price && data.fix_price > 0) {
						this.fixPrice = (data.fix_price / 100).toFixed(2)
					}
					if (data.publication_time) this.printTime = data.publication_time
					if (data.binding_layout) this.noIsbnFormat = data.binding_layout
					console.log('图书中心查询成功:', data)
				}).catch(err => {
					console.log('图书中心查询无结果:', err)
				})
			}

			// 2. 搜索孔夫子 - 获取在售商品信息（带会话过期自动重登录）
			const sortType = this.sortBy === 'book' ? '5' : '7'
			this.kongfzSearchWithRetry(keyword, { sortType: sortType, quality: this.conditionValue }).then(function(result) {
				var productsData = result[0]
				var onSaleFacet = result[1]
				var soldFacet = result[2]
				that.isLoading = false
				if (productsData && productsData.total > 0) {
					// 在售商品列表（最多12条）
					const list = (productsData.list || []).slice(0, 12)
					that.productList = list.map(item => {
						const cleanPrice = parseFloat((item.priceText || '0').replace(/[^\d.]/g, ''))
						let shippingFee = 0
						// 多种格式兼容处理运费
						if (item.postage) {
							if (typeof item.postage === 'number' || typeof item.postage === 'string') {
								// 运费直接是数字/字符串
								shippingFee = parseFloat(item.postage) || 0
							} else if (item.postage.shippingList && item.postage.shippingList.length > 0) {
								// 标准格式: postage.shippingList[0].shippingFee
								shippingFee = parseFloat(item.postage.shippingList[0].shippingFee || 0)
							} else if (item.postage.shippingFee) {
								// 扁平格式: postage.shippingFee
								shippingFee = parseFloat(item.postage.shippingFee || 0)
							}
						}
						// 也检查顶层字段
						if (shippingFee === 0 && item.shippingFee) {
							shippingFee = parseFloat(item.shippingFee) || 0
						}
						const totalPrice = Number((cleanPrice + shippingFee).toFixed(2))
						return {
							image: item.imgBigUrl || '',
							totalPrice: totalPrice,
							bookPrice: cleanPrice,
							shippingFee: shippingFee,
							condition: item.qualityText || '',
							shopName: item.shopName || '',
							bookName: item.title || '',
							author: item.author || '',
							press: item.press || '',
							pubDate: item.pubDateText || '',
							bookId: item.id || ''
						}
					})
					// 自动填充计算价格
					that.$nextTick(() => {
						if (that.calculatedPrice > 0) {
							that.price = String(that.calculatedPrice)
						}
					})
				}
				// 市场统计：使用facet接口的真实数据（totalFound为准）
				that.marketData = {
					onSale: onSaleFacet ? onSaleFacet.totalFound : (productsData ? productsData.total : 0),
					old: onSaleFacet ? onSaleFacet.oldCount : 0,
					new: onSaleFacet ? onSaleFacet.newCount : 0,
					sold: soldFacet ? (soldFacet.oldCount + soldFacet.newCount) : 0
				}
			}).catch(function() {
				that.isLoading = false
				that.marketData = { onSale: 0, old: 0, new: 0, sold: 0 }
			})
		},

		// 品相选择
		selectCondition(item) {
			this.selectedCondition = item
		},

		// 拍照
		takePhoto() {
			if (this.photoList.length >= 9) return
			uni.chooseImage({
				count: 9 - this.photoList.length,
				success: (res) => {
					this.photoList = [...this.photoList, ...res.tempFilePaths]
				}
			})
		},

		deletePhoto(index) {
			this.photoList.splice(index, 1)
		},

		previewPhoto(photo, index) {
			uni.previewImage({
				urls: this.photoList,
				current: index
			})
		},

		// 无ISBN拍照
		takePhotoNoIsbn() {
			if (this.noIsbnPhotoList.length >= 9) return
			uni.chooseImage({
				count: 9 - this.noIsbnPhotoList.length,
				success: (res) => {
					this.noIsbnPhotoList = [...this.noIsbnPhotoList, ...res.tempFilePaths]
				}
			})
		},
		// 打开连拍页面
		openCameraCapture(tab) {
			this.capturedPhotoTab = tab || 'no-isbn'
			uni.navigateTo({
				url: 'camera_capture'
			})
		},

		deleteNoIsbnPhoto(index) {
			this.noIsbnPhotoList.splice(index, 1)
		},

		// 仓库弹窗
		openWarehousePicker(tab) {
			this.pickerTargetTab = tab
			this.showWarehousePicker = true
			const savedData = tab === 'isbn' ? this.isbnWarehouseData : this.noIsbnWarehouseData
			this._pendingPreselectWh = savedData ? savedData.warehouseId : null
			this._pendingPreselectLoc = savedData ? savedData.locationId : null
			this.loadPopupWarehouses()
		},

		closeWarehousePicker() {
			this.showWarehousePicker = false
			this.popupSelectedLoc = null
		},

		async loadPopupWarehouses() {
			this.popupLoading = true
			try {
				const res = await getWarehouseList({ status: 1, page: 1, page_size: 100 })
				console.log('仓库列表原始响应:', JSON.stringify(res))
				const list = res.data?.list || res.data?.records || res.list || res.records || []
				if (list.length > 0) {
					this.popupWarehouseList = list
					// 默认选中第一个仓库
					let whIdx = 0
					const preselectWhId = this._pendingPreselectWh
					if (preselectWhId) {
						const foundIdx = list.findIndex(w => w.id === preselectWhId)
						if (foundIdx !== -1) whIdx = foundIdx
					}
					this.popupActiveWhIndex = whIdx
					this.popupSelectedWh = list[whIdx]
					this.popupSelectedLoc = null
					await this.loadPopupLocations(list[whIdx].id)
					// 加载完货位后根据已选ID自动选中
					const preselectLocId = this._pendingPreselectLoc
					if (preselectLocId && this.popupLocationList.length > 0) {
						const foundLoc = this.popupLocationList.find(l => l.id === preselectLocId)
						if (foundLoc) {
							this.popupSelectedLoc = foundLoc
						}
					}
					this._pendingPreselectWh = null
					this._pendingPreselectLoc = null
				} else {
					console.warn('仓库列表为空, 响应code:', res.code, '响应data:', JSON.stringify(res.data))
				}
			} catch (e) {
				console.error('加载仓库失败:', e)
				const errMsg = e.message || String(e)
				if (errMsg.includes('NEED_LOGIN')) {
					uni.showModal({
						title: '系统提示',
						content: 'PSI系统登录已过期，请重新登录',
						confirmText: '去登录',
						cancelText: '取消',
						success: (modalRes) => {
							if (modalRes.confirm) {
								uni.removeStorageSync('token')
								uni.removeStorageSync('warehouseList')
								uni.removeStorageSync('aboutId')
								uni.navigateTo({ url: '/pages/login/login' })
							}
						}
					})
				}
			} finally {
				this.popupLoading = false
			}
		},

		async loadPopupLocations(warehouseId, keepExisting = false, searchKeyword = '') {
			if (!keepExisting) {
				this.popupLoadingLocation = true
				this.popupLocPage = 1
				this.popupLocHasMore = true
				this.popupAllLocationList = []
				this.popupLocTotal = 0
			}
			try {
				const params = {
					warehouse_id: warehouseId, type: 1, status: 1,
					page: this.popupLocPage, page_size: this.popupLocPageSize
				}
				// 如果传了搜索关键词,交给后端过滤
				if (searchKeyword) {
					params.code = searchKeyword
				}
				const res = await getLocationList(params)
				console.log('【货位列表】load响应:', JSON.stringify(res))
				// 兼容多种响应格式：{ code:0, data:{ list:[], total:100 } } 或直接 { list:[], total:100 }
				let newList = []
				let totalCount = 0
				if (res.code === 0 && res.data) {
					newList = res.data.list || res.data.records || []
					totalCount = res.data.total || 0
				} else if (res.list || res.records) {
					newList = res.list || res.records || []
					totalCount = res.total || 0
				}
				if (newList.length > 0) {
					if (keepExisting) {
						this.popupLocationList = [...this.popupLocationList, ...newList]
						this.popupAllLocationList = [...this.popupAllLocationList, ...newList]
					} else {
						this.popupLocationList = newList
						this.popupAllLocationList = newList
					}
					this.popupLocTotal = totalCount
					this.popupLocHasMore = this.popupLocPage * this.popupLocPageSize < totalCount
				} else {
					if (!keepExisting) {
						this.popupLocationList = []
						this.popupAllLocationList = []
					}
					this.popupLocHasMore = false
				}
			} catch (e) {
				console.error('加载货位失败:', e)
				const errMsg = e.message || String(e)
				if (errMsg.includes('NEED_LOGIN')) {
					uni.showModal({
						title: '系统提示',
						content: 'PSI系统登录已过期，请重新登录',
						confirmText: '去登录',
						cancelText: '取消',
						success: (modalRes) => {
							if (modalRes.confirm) {
								uni.removeStorageSync('token')
								uni.removeStorageSync('warehouseList')
								uni.removeStorageSync('aboutId')
								uni.navigateTo({ url: '/pages/login/login' })
							}
						}
					})
				}
				this.popupLocationList = this.popupAllLocationList
				this.popupLocHasMore = false
			} finally {
				if (!keepExisting) {
					this.popupLoadingLocation = false
				}
			}
		},

		selectPopupWarehouse(idx) {
			this.popupActiveWhIndex = idx
			const wh = this.popupWarehouseList[idx]
			if (wh) {
				this.popupSelectedWh = wh
				this.popupSelectedLoc = null
				this.popupLocationSearch = ''
				return this.loadPopupLocations(wh.id)
			}
		},

		selectPopupLocation(loc) {
			this.popupSelectedLoc = loc
		},

		confirmWarehousePicker() {
			if (!this.popupSelectedLoc) return
			const wh = this.popupWarehouseList[this.popupActiveWhIndex]
			if (this.pickerTargetTab === 'isbn') {
				this.isbnWarehouseData = {
					warehouseId: wh.id,
					warehouseName: wh.name,
					warehouseCode: wh.code,
					locationId: this.popupSelectedLoc.id,
					locationCode: this.popupSelectedLoc.code,
					locationName: this.popupSelectedLoc.name
				}
				this.isbnSelectedArea = `${wh.name} - ${this.popupSelectedLoc.code}`
			} else {
				this.noIsbnWarehouseData = {
					warehouseId: wh.id,
					warehouseName: wh.name,
					warehouseCode: wh.code,
					locationId: this.popupSelectedLoc.id,
					locationCode: this.popupSelectedLoc.code,
					locationName: this.popupSelectedLoc.name
				}
				this.noIsbnSelectedArea = `${wh.name} - ${this.popupSelectedLoc.code}`
			}
			this.showWarehousePicker = false
		},

		// 下拉刷新货位列表
		async onPopupRefresh() {
			this.popupRefreshing = true
			this.popupLocationSearch = ''
			const wh = this.popupWarehouseList[this.popupActiveWhIndex]
			if (wh) {
				await this.loadPopupLocations(wh.id)
			}
			this.popupRefreshing = false
		},

		// 上拉加载更多
		loadMorePopupLocation() {
			if (!this.popupLocHasMore || this.popupLocLoadingMore) return
			this.popupLocLoadingMore = true
			this.popupLocPage++
			const wh = this.popupWarehouseList[this.popupActiveWhIndex]
			if (!wh) { this.popupLocLoadingMore = false; return }
			this.loadPopupLocations(wh.id, true).catch(() => {
				this.popupLocPage--
			}).finally(() => {
				this.popupLocLoadingMore = false
			})
		},

		// 货位搜索
		onLocationSearchInput() {
			if (this.popupLocationSearch) {
				const kw = this.popupLocationSearch.toLowerCase()
				this.popupLocationList = this.popupAllLocationList.filter(loc => {
					const code = (loc.code || '').toLowerCase()
					const name = (loc.name || '').toLowerCase()
					return code.includes(kw) || name.includes(kw)
				})
			} else {
				this.popupLocationList = [...this.popupAllLocationList]
			}
		},

		clearLocationSearch() {
			this.popupLocationSearch = ''
			this.popupLocationList = [...this.popupAllLocationList]
		},

		// 扫码识别货位（格式：仓库编码##货位号，如 NS##a5-4）
		async scanLocationBarcode() {
			uni.scanCode({
				onlyFromCamera: true,
				scanType: ['barcode'],
				success: async (res) => {
					const scanned = (res.result || '').trim()
					if (!scanned) return

					// 尝试解析 编码##货位号 格式
					const sepIdx = scanned.indexOf('##')
					if (sepIdx > 0) {
						const whCode = scanned.substring(0, sepIdx).trim()
						const locCode = scanned.substring(sepIdx + 2).trim()
						if (whCode && locCode) {
							this.scanPopupWhCode = whCode
							this.scanPopupLocCode = locCode
							this.scanPopupRaw = ''
							this.showScanPopup = true
							return
						}
					}

					// 纯条码格式
					this.scanPopupWhCode = ''
					this.scanPopupLocCode = ''
					this.scanPopupRaw = scanned
					this.showScanPopup = true
				},
				fail: () => {}
			})
		},

		closeScanPopup() {
			this.showScanPopup = false
		},

		async confirmScanSearch() {
			this.showScanPopup = false
			const whCode = this.scanPopupWhCode
			const locCode = this.scanPopupLocCode
			const raw = this.scanPopupRaw

			if (whCode && locCode) {
				// 格式 NS##a5-4 → 按仓库编码匹配仓库，切换tab，带着货位号请求后端过滤
				const whIdx = this.popupWarehouseList.findIndex(w => {
					const code = (w.code || '').toLowerCase()
					const name = (w.name || '').toLowerCase()
					const search = whCode.toLowerCase()
					return code === search || name === search || code.includes(search)
				})
				if (whIdx !== -1) {
					const wh = this.popupWarehouseList[whIdx]
					// 切换到该仓库 tab
					this.popupActiveWhIndex = whIdx
					this.popupSelectedWh = wh
					this.popupSelectedLoc = null
					this.popupLocationSearch = ''
					// 带着货位号请求后端过滤货位列表（重新请求接口）
					await this.loadPopupLocations(wh.id, false, locCode)
					if (this.popupLocationList.length > 0) {
						this.popupSelectedLoc = this.popupLocationList[0]
						uni.showToast({ title: '已匹配 仓库' + whCode + ' 货位:' + this.popupLocationList[0].code, icon: 'success' })
					} else {
						uni.showToast({ title: '已切换到仓库' + whCode + '，但未找到货位' + locCode, icon: 'none' })
					}
				} else {
					uni.showToast({ title: '未找到仓库: ' + whCode, icon: 'none' })
				}
			} else if (raw) {
				// 纯条码，在当前仓库的货位列表中查找
				const search = raw.toLowerCase()
				const matched = this.popupAllLocationList.find(l => {
					const code = (l.code || '').toLowerCase()
					const name = (l.name || '').toLowerCase()
					return code === search || name === search ||
						code.includes(search) || search.includes(code)
				})
				if (matched) {
					this.popupSelectedLoc = matched
					this.popupLocationSearch = ''
					this.popupLocationList = [...this.popupAllLocationList]
					uni.showToast({ title: '已选中货位: ' + matched.code, icon: 'success' })
				} else {
					uni.showToast({ title: '未找到匹配货位', icon: 'none' })
				}
			}
		},

		// 比价切换 - 切换后触发搜索
		switchCompare(type) {
			this.compareType = type
			this.searchISBN()
		},

		// 排序 - 切换后重新请求孔夫子接口
		sortProducts(by) {
			this.sortBy = by
			this.searchISBN()
		},

		// 筛选
		showMoreFilter() {
			this.showFilterPopup = true
		},

		resetFilter() {
			this.filterPress = ''
			this.filterAuthor = ''
		},

		applyFilter() {
			this.showFilterPopup = false
		},

		// 分类
		// 无ISBN - 分类选择器：列变化
		onNoIsbnCategoryColumnChange(e) {
			const { column, value } = e.detail
			this.noIsbnCategoryIndexes[column] = value
			this.noIsbnCategoryLevels[column] = this.noIsbnCategoryColumns[column][value]
			if (column < this.noIsbnMaxCategoryLevel - 1) {
				this.updateNoIsbnSubsequentColumns(column + 1)
			}
			this.updateNoIsbnCategoryPathText()
		},

		// 无ISBN - 分类选择器：确认选择
		onNoIsbnCategoryChange(e) {
			const values = e.detail.value
			this.noIsbnCategoryIndexes = [...values]
			for (let i = 0; i < values.length; i++) {
				if (this.noIsbnCategoryColumns[i] && this.noIsbnCategoryColumns[i][values[i]]) {
					this.noIsbnCategoryLevels[i] = this.noIsbnCategoryColumns[i][values[i]]
				}
			}
			this.updateNoIsbnCategoryPathText()
			this.updateNoIsbnSelectedCategoryId()
		},

		updateNoIsbnSubsequentColumns(startColumn) {
			const parentCategory = this.noIsbnCategoryLevels[startColumn - 1]
			if (!parentCategory || !parentCategory.children || parentCategory.children.length === 0) {
				for (let i = startColumn; i < this.noIsbnMaxCategoryLevel; i++) {
					this.noIsbnCategoryColumns[i] = [{ name: '暂无数据', id: '' }]
					this.noIsbnCategoryIndexes[i] = 0
					this.noIsbnCategoryLevels[i] = { name: '暂无数据', id: '' }
				}
				return
			}
			this.noIsbnCategoryColumns[startColumn] = parentCategory.children
			this.noIsbnCategoryIndexes[startColumn] = 0
			this.noIsbnCategoryLevels[startColumn] = parentCategory.children[0]
			if (startColumn < this.noIsbnMaxCategoryLevel - 1) {
				this.updateNoIsbnSubsequentColumns(startColumn + 1)
			}
		},

		updateNoIsbnCategoryPathText() {
			const validLevels = this.noIsbnCategoryLevels.filter(level => level && level.name && level.name !== '暂无数据')
			this.noIsbnCategoryPathText = validLevels.map(level => level.name).join(' / ')
		},

		updateNoIsbnSelectedCategoryId() {
			const validLevels = this.noIsbnCategoryLevels.filter(level => level && level.id && level.id !== '')
			this.noIsbnSelectedCategoryId = validLevels.length > 0 ? validLevels[validLevels.length - 1].id : ''
		},

		// 加载图书分类（从API）
		loadNoIsbnCategory() {
			this.noIsbnCategoryLoading = true
			const cookies = uni.getStorageSync('cookies') || this.kongfzToken || ''
			uni.request({
				url: 'https://api.buzhiyushu.cn/api/kongfz/getCategory',
				method: 'GET',
				data: { token: cookies },
				header: { 'Content-Type': 'application/json' },
				success: (res) => {
					const responseData = res.data
					if (responseData && responseData.successResponse) {
						this.noIsbnCategoryData = responseData.successResponse
						this.initNoIsbnCategoryPicker()
					} else {
						console.error('获取分类数据失败:', responseData)
						// 使用本地默认分类
						this.loadDefaultNoIsbnCategory()
					}
				},
				fail: (err) => {
					console.error('获取分类数据异常:', err)
					this.loadDefaultNoIsbnCategory()
				},
				complete: () => {
					this.noIsbnCategoryLoading = false
				}
			})
		},

		loadDefaultNoIsbnCategory() {
			const defaultCategories = [
				{ name: '文学', id: '1', level: 1, children: [{ name: '中国文学', id: '11', level: 2, children: [] }] },
				{ name: '艺术', id: '2', level: 1, children: [] },
				{ name: '历史', id: '3', level: 1, children: [] },
				{ name: '哲学', id: '4', level: 1, children: [] },
				{ name: '科学', id: '5', level: 1, children: [] },
				{ name: '技术', id: '6', level: 1, children: [] },
				{ name: '教育', id: '7', level: 1, children: [] },
				{ name: '经济', id: '8', level: 1, children: [] },
				{ name: '政治', id: '9', level: 1, children: [] },
				{ name: '军事', id: '10', level: 1, children: [] },
				{ name: '法律', id: '11', level: 1, children: [] },
				{ name: '社会', id: '12', level: 1, children: [] },
				{ name: '文化', id: '13', level: 1, children: [] },
				{ name: '语言', id: '14', level: 1, children: [] },
				{ name: '工具书', id: '15', level: 1, children: [] },
				{ name: '其他', id: '16', level: 1, children: [] }
			]
			this.noIsbnCategoryData = defaultCategories
			this.initNoIsbnCategoryPicker()
		},

		initNoIsbnCategoryPicker() {
			this.noIsbnCategoryColumns = []
			this.noIsbnCategoryLevels = []
			this.noIsbnCategoryIndexes = []
			const level1Categories = (this.noIsbnCategoryData || []).filter(item => item.level === 1)
			if (level1Categories.length === 0) return
			this.noIsbnCategoryColumns[0] = level1Categories
			this.noIsbnCategoryIndexes[0] = 0
			let currentParent = level1Categories[0]
			let currentLevel = 1
			this.noIsbnCategoryLevels[0] = currentParent
			while (currentLevel < this.noIsbnMaxCategoryLevel) {
				const children = currentParent.children || []
				if (children.length === 0) break
				this.noIsbnCategoryColumns[currentLevel] = children
				this.noIsbnCategoryIndexes[currentLevel] = 0
				this.noIsbnCategoryLevels[currentLevel] = children[0]
				currentParent = children[0]
				currentLevel++
			}
			while (this.noIsbnCategoryColumns.length < this.noIsbnMaxCategoryLevel) {
				this.noIsbnCategoryColumns.push([{ name: '暂无数据', id: '' }])
				this.noIsbnCategoryIndexes.push(0)
				this.noIsbnCategoryLevels.push({ name: '暂无数据', id: '' })
			}
			this.updateNoIsbnCategoryPathText()
			this.updateNoIsbnSelectedCategoryId()
		},

		// 印刷时间 - 列变化
		onNoIsbnPrintTimeColumnChange(e) {
			const { column, value } = e.detail
			this.noIsbnPrintTimeIndexes[column] = value
		},

		// 印刷时间 - 确认选择
		onNoIsbnPrintTimeChange(e) {
			const values = e.detail.value
			this.noIsbnPrintTimeIndexes = [...values]
			const year = this.noIsbnYearOptions[values[0]]
			const month = this.noIsbnMonthOptions[values[1]]
			if (year && month) {
				this.noIsbnPrintTime = year + '/' + month
			}
		},

		// 同步印刷时间选择器索引（空→今年，有值→对应年/月）
		syncNoIsbnPrintTimeIndexes() {
			if (this.noIsbnPrintTime) {
				const parts = this.noIsbnPrintTime.split('/')
				const yearIdx = this.noIsbnYearOptions.indexOf(parts[0])
				const monthIdx = parts[1] ? this.noIsbnMonthOptions.indexOf(parts[1].padStart(2, '0')) : -1
				if (yearIdx >= 0) this.noIsbnPrintTimeIndexes[0] = yearIdx
				if (monthIdx >= 0) this.noIsbnPrintTimeIndexes[1] = monthIdx
			} else {
				const curYear = String(new Date().getFullYear())
				const curYearIdx = this.noIsbnYearOptions.indexOf(curYear)
				if (curYearIdx >= 0) this.noIsbnPrintTimeIndexes[0] = curYearIdx
				this.noIsbnPrintTimeIndexes[1] = 0
			}
		},

		// 商品预览
		previewProductImage(index) {
			const urls = this.productList.map(item => item.image).filter(Boolean)
			if (urls.length > 0) {
				uni.previewImage({ urls, current: index })
			}
		},

		// 提交上传
		async submitUpload() {
			if (this.isSubmitting) return

			const warehouseData = this.currentTab === 'isbn' ? this.isbnWarehouseData : this.noIsbnWarehouseData
			if (!warehouseData) {
				uni.showToast({ title: '请选择货区', icon: 'none' })
				return
			}

			// 检查是否有图片
			if (this.currentTab === 'isbn' && this.photoList.length < 1) {
				uni.showToast({ title: '请至少拍一张图片', icon: 'none' })
				return
			}
			if (this.currentTab === 'no-isbn' && this.noIsbnPhotoList.length < 1) {
				uni.showToast({ title: '请至少拍一张图片', icon: 'none' })
				return
			}

			// 校验必填字段
			if (this.currentTab === 'isbn') {
				if (!this.isbn) {
					uni.showToast({ title: 'ISBN不能为空', icon: 'none' })
					return
				}
				if (!this.price) {
					uni.showToast({ title: '售价不能为空', icon: 'none' })
					return
				}
			} else {
				if (!this.noIsbnPrice) {
					uni.showToast({ title: '售价不能为空', icon: 'none' })
					return
				}
				if (!this.noIsbnBookName) {
					uni.showToast({ title: '书名不能为空', icon: 'none' })
					return
				}
			}

			// 先上传图片到MinIO，拿到URL
			this.isSubmitting = true
			uni.showLoading({ title: '上传图片中...', mask: true })
			try {
				const photoList = this.currentTab === 'isbn' ? this.photoList : this.noIsbnPhotoList
				const typeDir = this.currentTab === 'isbn' ? (this.isbn || 'UnknownIsbn') : this.getNoIsbnIsbnValue()
				const imageUrls = await uploadImages(photoList, typeDir)

				console.log('【上传】MinIO图片URL列表:', imageUrls)

				// 图片上传完成后直接推送数据到接口
				if (this.currentTab === 'isbn') {
					await this.doSubmit(warehouseData, imageUrls)
				} else {
					await this.doNoIsbnSyncBook(imageUrls)
				}
			} catch (e) {
				uni.hideLoading()
				this.isSubmitting = false
				console.error('【上传】失败:', e)
				uni.showToast({ title: e.message || '上传失败', icon: 'none', duration: 3000 })
			}
		},

		async doSubmit(warehouseData, imageUrls) {
			this.isSubmitting = true
			uni.showLoading({ title: '上传中...', mask: true })
			try {
				var timestamp = String(Math.floor(Date.now() / 1000))

				// 出版时间转时间戳
				var pubTimeStr = this.printTime || ''
				var pubTimestamp = '0'
				if (pubTimeStr) {
					// 兼容 '1980/03' 和 '1980-03' 两种格式
					var normalized = pubTimeStr.replace(/\//g, '-')
					var parts = normalized.split('-')
					if (parts.length >= 2) {
						var d = new Date(parseInt(parts[0], 10), parseInt(parts[1], 10) - 1, 1)
						var ts = Math.floor(d.getTime() / 1000)
						if (ts >= 0) { pubTimestamp = String(ts) }
					}
				}

				const params = {
					app_key: 'psi',
					client_id: 'psi',
					fid: '0',
					type: '4',
					isbn: this.isbn || '',
					f_isbn: '0',
					book_name: this.bookName || '',
					f_book_name: '',
					author: this.author || '',
					publisher: this.publisher || '',
					publication_time: pubTimestamp,
					binding_layout: '',
					fix_price: this.price ? String(Math.round(parseFloat(this.price) * 100)) : '',
					page_count: '0',
					word_count: '',
					book_format: '',
					'live_image': imageUrls.join(','),
					timestamp: timestamp,
					sign_method: 'md5'
				}

				var sign = calculateSign(params)
				params.sign = sign
				var formBody = buildFormBodyWithImages(params, imageUrls, 'live_image')
				const apiUrl = 'https://psi.api.buzhiyushu.cn/api/syncBook'
				const token = uni.getStorageSync('token') || ''
				console.log('【syncBook】请求地址:', apiUrl)
				console.log('【syncBook】请求参数:', params)

				const res = await new Promise(function (resolve, reject) {
					uni.request({
						url: apiUrl,
						method: 'POST',
						header: {
							'Content-Type': 'application/x-www-form-urlencoded',
							'Authorization': 'Bearer ' + token
						},
						data: formBody,
						success: function (r) { resolve(r) },
						fail: function (e) { reject(e) }
					})
				})

				console.log('【syncBook】返回值:', res.statusCode, res.data)
				uni.hideLoading()

				if (res.statusCode !== 200) {
					throw new Error('API返回: HTTP ' + res.statusCode)
				}

				var respData = res.data
				if (typeof respData === 'string') {
					try { respData = JSON.parse(respData) } catch (e) { respData = { code: 500, msg: respData } }
				}

				if (respData && respData.code === 200) {
 					uni.showToast({ title: respData.msg || '上传成功', icon: 'success' })
				} else {
					throw new Error(respData && respData.msg || '上传失败')
				}

				// syncBook 成功后保存商品到 product 表，获取真实商品ID
				var syncData = respData.data || {}
				var bookInfoId = syncData.id || ''
				var barcode = this.currentTab === 'isbn' ? (this.isbn || '') : (this.noIsbnIsbn || '')
				var productName = this.currentTab === 'isbn' ? (this.bookName || '') : (this.noIsbnBookName || '')
				var appearanceValue = parseInt(this.currentTab === 'isbn' ? this.conditionValue : this.noIsbnConditionValue) || 0
				var productPrice = this.currentTab === 'isbn'
					? (this.fixPrice ? String(Math.round(parseFloat(this.fixPrice) * 100)) : '0')
					: (this.noIsbnOriginalPrice ? String(Math.round(parseFloat(this.noIsbnOriginalPrice) * 100)) : '0')
				var productId = await this.callProductSaveApi(productName, appearanceValue, barcode, productPrice, imageUrls)
				if (!productId) {
					console.warn('【product/save】保存商品失败,跳过波次')
					return
				}
				// product/save 成功后设置售价
				var salePrice = this.currentTab === 'isbn'
					? (this.price ? String(Math.round(parseFloat(this.price) * 100)) : '0')
					: (this.noIsbnPrice ? String(Math.round(parseFloat(this.noIsbnPrice) * 100)) : '0')
				var costPrice = String(Math.round(parseFloat(this.referenceShippingFee || '0') * 100))
				await this.callUpdatePriceApi(productId, salePrice, costPrice)
				if (warehouseData && productId) {
					await this.callWaveApi(warehouseData, productId)
				} else {
					console.warn('【syncBook】缺少warehouseData或productId,跳过波次')
				}

				// 保存上传记录到本地
				const uploadHistory = uni.getStorageSync('uploadHistory') || []
				uploadHistory.unshift({
					id: Date.now(),
					time: new Date().toLocaleString(),
					type: this.currentTab,
					apiUrl: apiUrl,
					apiResponse: res.data,
					data: params
				})
				uni.setStorageSync('uploadHistory', uploadHistory.slice(0, 100))

				// 清空表单
				this.photoList = []
				this.isbn = ''
				this.bookName = ''
				this.author = ''
				this.publisher = ''
				this.fixPrice = ''
				this.price = ''
				this.stock = 1
				this.printTime = ''
				this.productList = []

				// ISBN提交成功 → 自动打开扫码
				if (this.currentTab === 'isbn') {
					var that = this
					setTimeout(function() { that.scanISBN() }, 800)
				}
			} catch (e) {
				uni.hideLoading()
				console.error('【上传】失败:', e)
				uni.showToast({ title: '上传失败: ' + (e.message || '未知错误'), icon: 'none', duration: 3000 })
			} finally {
				this.isSubmitting = false
			}
		},

		// 无ISBN - 调用 syncBook 同步图书数据
		async doNoIsbnSyncBook(imageUrls) {
			this.isSubmitting = true
			uni.showLoading({ title: '上传中...', mask: true })
			try {
				const token = uni.getStorageSync('token') || ''

				// 构建参数（用于计算签名）
				var timestamp = String(Math.floor(Date.now() / 1000))

				// 出版时间转时间戳（1970-01-01 为 0）
				var pubTimeStr = this.noIsbnPrintTime || ''
				var pubTimestamp = '0'
				if (pubTimeStr) {
					// 兼容 '1980/03' 和 '1980-03' 两种格式
					var normalized = pubTimeStr.replace(/\//g, '-')
					var parts = normalized.split('-')
					if (parts.length >= 2) {
						var d = new Date(parseInt(parts[0], 10), parseInt(parts[1], 10) - 1, 1)
						var ts = Math.floor(d.getTime() / 1000)
						if (ts >= 0) { pubTimestamp = String(ts) }
					}
				}

				const params = {
					app_key: 'psi',
					client_id: 'psi',
					fid: '0',
					type: '4',
					isbn: this.noIsbnIsbn || '',
					f_isbn: '0',
					book_name: this.noIsbnBookName || '',
					f_book_name: '',
					author: this.noIsbnAuthor || '',
					publisher: this.noIsbnPublisher || '',
					publication_time: pubTimestamp,
					binding_layout: this.noIsbnBinding || '',
					fix_price: this.noIsbnPrice ? String(Math.round(parseFloat(this.noIsbnPrice) * 100)) : '',
					page_count: '0',
					word_count: this.noIsbnWordCount || '',
					book_format: '',
					'live_image': imageUrls.join(','),
					cat_id: JSON.stringify({
						xian_yu_cat_id: '',
						kong_fu_zi_cat_id: (this.noIsbnCategoryPathText || '').replace(/ \/ /g, '/'),
						pin_duo_duo_cat_id: ''
					}),
					timestamp: timestamp,
					sign_method: 'md5'
				}

				// 计算签名（与仓库列表一致的签名算法）
				var sign = calculateSign(params)
				params.sign = sign
				var formBody = buildFormBodyWithImages(params, imageUrls, 'live_image')

				const apiUrl = 'https://psi.api.buzhiyushu.cn/api/syncBook'
				console.log('【syncBook】请求地址:', apiUrl)
				console.log('【syncBook】请求参数:', params)

				const res = await new Promise(function (resolve, reject) {
					uni.request({
						url: apiUrl,
						method: 'POST',
						header: {
							'Content-Type': 'application/x-www-form-urlencoded',
							'Authorization': 'Bearer ' + token
						},
						data: formBody,
						success: function (r) { resolve(r) },
						fail: function (e) { reject(e) }
					})
				})

				console.log('【syncBook】返回值:', res.statusCode, res.data)

				uni.hideLoading()

				if (res.statusCode !== 200) {
					throw new Error('API返回: HTTP ' + res.statusCode)
				}

				var respData = res.data
				if (typeof respData === 'string') {
					try { respData = JSON.parse(respData) } catch (e) { respData = { code: 500, msg: respData } }
				}

				if (respData && respData.code === 200) {
 					uni.showToast({ title: respData.msg || '上传成功', icon: 'success' })
				} else {
					throw new Error(respData && respData.msg || '上传失败')
				}

				// syncBook 成功后保存商品到 product 表，获取真实商品ID
				var syncData = respData.data || {}
				var barcode = this.noIsbnIsbn || ''
				var productName = this.noIsbnBookName || ''
				var appearanceValue = parseInt(this.noIsbnConditionValue) || 0
				var productPrice = this.noIsbnOriginalPrice ? String(Math.round(parseFloat(this.noIsbnOriginalPrice) * 100)) : '0'
				var productId = await this.callProductSaveApi(productName, appearanceValue, barcode, productPrice, imageUrls)
				if (!productId) {
					console.warn('【product/save】保存商品失败,跳过波次')
					return
				}
				// product/save 成功后设置售价
				var salePrice = this.noIsbnPrice ? String(Math.round(parseFloat(this.noIsbnPrice) * 100)) : '0'
				var costPrice = String(Math.round(parseFloat(this.noIsbnReferenceShippingFee || '0') * 100))
				await this.callUpdatePriceApi(productId, salePrice, costPrice)
				if (this.noIsbnWarehouseData && productId) {
					await this.callWaveApi(this.noIsbnWarehouseData, productId)
				} else {
					console.warn('【syncBook】缺少warehouseData或productId,跳过波次')
				}

				// 保存上传记录到本地
				const uploadHistory = uni.getStorageSync('uploadHistory') || []
				uploadHistory.unshift({
					id: Date.now(),
					time: new Date().toLocaleString(),
					type: this.currentTab,
					apiUrl: apiUrl,
					apiResponse: res.data,
					data: params
				})
				uni.setStorageSync('uploadHistory', uploadHistory.slice(0, 100))

				// 清空表单
				this.noIsbnPhotoList = []
				this.noIsbnBookName = ''
				this.noIsbnPrice = ''
				this.noIsbnStock = 1
				this.noIsbnAuthor = ''
				this.noIsbnPublisher = ''
				this.noIsbnOriginalPrice = ''
				this.noIsbnIsbn = ''
				this.noIsbnUnifyIsbn = ''
				this.noIsbnPrintTime = ''
				this.noIsbnFormat = ''
				this.noIsbnBinding = ''
				this.noIsbnProductList = []
			} catch (e) {
				uni.hideLoading()
				console.error('【syncBook】失败:', e)
				uni.showToast({ title: e.message || '上传失败', icon: 'none', duration: 3000 })
			} finally {
				this.isSubmitting = false
			}
		},

		// 保存商品到 product 表，返回商品ID
		async callProductSaveApi(name, appearance, barcode, price, imageUrls) {
			var timestamp = String(Math.floor(Date.now() / 1000))
			const token = uni.getStorageSync('token') || ''
			const params = {
				app_key: 'psi',
				client_id: 'psi',
				name: name,
				appearance: String(appearance),
				barcode: barcode,
				price: price,
				'live_image[]': imageUrls.join(','),
				timestamp: timestamp,
				sign_method: 'md5'
			}
			var sign = calculateSign(params)
			params.sign = sign
			// 构建 form body（live_image[] 每个 URL 单独发送，product/save 需要 live_image[]）
			var formBody = buildFormBodyWithImages(params, imageUrls, 'live_image[]')
			var saveUrl = 'https://psi.api.buzhiyushu.cn/api/product/save'
			console.log('【保存商品】请求地址:', saveUrl)
			console.log('【保存商品】请求参数:', params)

			try {
				const res = await new Promise(function (resolve, reject) {
					uni.request({
						url: 'https://psi.api.buzhiyushu.cn/api/product/save',
						method: 'POST',
						header: {
							'Content-Type': 'application/x-www-form-urlencoded',
							'Authorization': 'Bearer ' + token
						},
						data: formBody,
						success: function (r) { resolve(r) },
						fail: function (e) { reject(e) }
					})
				})
				console.log('【product/save】返回值:', res.statusCode, res.data)

				if (res.statusCode === 200 && res.data) {
					var saveResp = res.data
					if (typeof saveResp === 'string') {
						try { saveResp = JSON.parse(saveResp) } catch (e) { saveResp = {} }
					}
					if (saveResp.code === 200 && saveResp.data && saveResp.data.id) {
						return saveResp.data.id
					} else {
						uni.showToast({ title: '保存商品: ' + (saveResp.msg || '返回数据异常'), icon: 'none', duration: 3000 })
					}
				} else {
					uni.showToast({ title: '保存商品: 请求失败 HTTP ' + res.statusCode, icon: 'none', duration: 3000 })
				}
				return ''
			} catch (e) {
				console.warn('【product/save】请求失败:', e)
				uni.showToast({ title: '保存商品: 网络请求失败', icon: 'none', duration: 3000 })
				return ''
			}
		},

		// 设置售价（product/save 成功后调用）
		async callUpdatePriceApi(productId, salePrice, costPrice) {
			var timestamp = String(Math.floor(Date.now() / 1000))
			const token = uni.getStorageSync('token') || ''
			var userId = uni.getStorageSync('aboutId') || ''
			const params = {
				app_key: 'psi',
				client_id: 'psi',
				product_id: String(productId),
				user_id: String(userId),
				sale_price: String(salePrice),
				cost: String(costPrice),
				timestamp: timestamp,
				sign_method: 'md5'
			}
			var sign = calculateSign(params)
			params.sign = sign
			var updateUrl = 'https://psi.api.buzhiyushu.cn/api/product/updatePrice'
			console.log('【设置售价】请求地址:', updateUrl)
			console.log('【设置售价】请求参数:', params)

			try {
				const res = await new Promise(function (resolve, reject) {
					uni.request({
						url: updateUrl,
						method: 'POST',
						header: {
							'Content-Type': 'application/x-www-form-urlencoded',
							'Authorization': 'Bearer ' + token
						},
						data: params,
						success: function (r) { resolve(r) },
						fail: function (e) { reject(e) }
					})
				})
				console.log('【设置售价】返回值:', res.statusCode, res.data)

				if (res.statusCode === 200 && res.data) {
					var priceResp = res.data
					if (typeof priceResp === 'string') {
						try { priceResp = JSON.parse(priceResp) } catch (e) { priceResp = {} }
					}
					if (priceResp.code !== 200) {
						uni.showToast({ title: '设置售价: ' + (priceResp.msg || '返回数据异常'), icon: 'none', duration: 3000 })
					}
				} else {
					uni.showToast({ title: '设置售价: 请求失败 HTTP ' + res.statusCode, icon: 'none', duration: 3000 })
				}
			} catch (e) {
				console.warn('【设置售价】请求失败:', e)
				uni.showToast({ title: '设置售价: 网络请求失败', icon: 'none', duration: 3000 })
			}
		},

		// 调用波次接口（syncBook 成功后调用）
		// 复用波次机制：首次创建后永久复用，绑定失败时重新创建
		async callWaveApi(warehouseData, productId) {
			var timestamp = String(Math.floor(Date.now() / 1000))
			var price = this.currentTab === 'isbn'
				? (this.price ? String(Math.round(parseFloat(this.price) * 100)) : '0')
				: (this.noIsbnPrice ? String(Math.round(parseFloat(this.noIsbnPrice) * 100)) : '0')
			var stock = this.currentTab === 'isbn'
				? String(this.stock ?? '1')
				: String(this.noIsbnStock ?? '1')

			const token = uni.getStorageSync('token') || ''

			// 先查询小车列表，获取 car_id / car_code
			var carInfo = await this.callCarListApi(timestamp)
			if (!carInfo) {
				// 无小车时 callCarListApi 已弹窗提示，此处直接返回
				return
			}

			var waveNo = uni.getStorageSync('reuseWaveNo') || ''

			// 已有波次 → 尝试复用
			if (waveNo) {
				console.log('【波次】尝试复用 wave_no=' + waveNo)
				var bindResult = await this.callBindWaveApi(timestamp, waveNo)
				if (bindResult) {
					await this.callReceiveSubmitApi(timestamp, bindResult, productId, stock, warehouseData)
					return
				}
				console.log('【波次】复用失败，创建新波次')
			}

			// 无波次或复用失败 → 创建新波次
			console.log('【波次】创建新波次')

			// 调用波次接口
			const params = {
				app_key: 'psi',
				client_id: 'psi',
				warehouse_id: String(warehouseData.warehouseId || ''),
				'items[0][product_id]': String(productId),
				'items[0][quantity]': stock,
				'items[0][unit_price]': price,
				direction: '1',
				car_id: String(carInfo.car_id),
				car_code: String(carInfo.car_code),
				timestamp: timestamp,
				sign_method: 'md5'
			}

			var sign = calculateSign(params)
			params.sign = sign

			var waveUrl = 'https://psi.api.buzhiyushu.cn/api/purchase-order/create-with-wave'
			console.log('【波次】请求地址:', waveUrl)
			console.log('【波次】请求参数:', params)

			try {
				const waveRes = await new Promise(function (resolve, reject) {
					uni.request({
						url: waveUrl,
						method: 'POST',
						header: {
							'Content-Type': 'application/x-www-form-urlencoded',
							'Authorization': 'Bearer ' + token
						},
						data: params,
						success: function (r) { resolve(r) },
						fail: function (e) { reject(e) }
					})
				})
				console.log('【波次】返回值:', waveRes.statusCode, waveRes.data)

				if (waveRes.statusCode === 200 && waveRes.data) {
					var waveResp = waveRes.data
					if (typeof waveResp === 'string') {
						try { waveResp = JSON.parse(waveResp) } catch (e) { waveResp = {} }
					}
					if (waveResp.code === 200 && waveResp.data && waveResp.data.wave_id && waveResp.data.order_id) {
						var waveId = waveResp.data.wave_id
						var orderId = waveResp.data.order_id
						// 1. 提交波次，获取 wave_no
						var releaseWaveNo = await this.callWaveReleaseApi(timestamp, waveId, orderId, carInfo, productId, stock, price)
						// 2. 绑定波次（使用 release 返回的 wave_no）
						if (releaseWaveNo) {
							// 保存 wave_no 供后续永久复用
							uni.setStorageSync('reuseWaveNo', releaseWaveNo)
							var bindResult = await this.callBindWaveApi(timestamp, releaseWaveNo)
							// 3. 提交入库（使用 bind-wave 返回的数据）
							if (bindResult) {
								await this.callReceiveSubmitApi(timestamp, bindResult, productId, stock, warehouseData)
							}
						}
					} else {
						uni.showToast({ title: '创建波次: ' + (waveResp.msg || '返回数据异常'), icon: 'none', duration: 3000 })
					}
				} else {
					uni.showToast({ title: '创建波次: 请求失败 HTTP ' + waveRes.statusCode, icon: 'none', duration: 3000 })
				}
			} catch (e) {
				console.warn('【波次】请求失败:', e)
				uni.showToast({ title: '创建波次: 网络请求失败', icon: 'none', duration: 3000 })
			}
		},

		// 提交波次（波次创建成功后调用），返回 wave_no
		async callWaveReleaseApi(timestamp, waveId, orderId, carInfo, productId, stock, price) {
			const token = uni.getStorageSync('token') || ''
			const params = {
				app_key: 'psi',
				client_id: 'psi',
				wave_id: String(waveId),
				related_order_id: String(orderId),
				car_id: String(carInfo.car_id),
				car_code: String(carInfo.car_code),
				'items[0][product_id]': String(productId),
				'items[0][quantity]': stock,
				'items[0][unit_price]': price,
				timestamp: timestamp,
				sign_method: 'md5'
			}
			var sign = calculateSign(params)
			params.sign = sign

			try {
				const res = await new Promise(function (resolve, reject) {
					uni.request({
						url: 'https://psi.api.buzhiyushu.cn/api/wave/release',
						method: 'POST',
						header: {
							'Content-Type': 'application/x-www-form-urlencoded',
							'Authorization': 'Bearer ' + token
						},
						data: params,
						success: function (r) { resolve(r) },
						fail: function (e) { reject(e) }
					})
				})
				console.log('【提交波次】返回值:', res.statusCode, res.data)

				if (res.statusCode === 200 && res.data) {
					var releaseResp = res.data
					if (typeof releaseResp === 'string') {
						try { releaseResp = JSON.parse(releaseResp) } catch (e) { releaseResp = {} }
					}
					if (releaseResp.code === 200 && releaseResp.data && releaseResp.data.wave_no) {
						return releaseResp.data.wave_no
					} else {
						uni.showToast({ title: '提交波次: ' + (releaseResp.msg || '返回数据异常'), icon: 'none', duration: 3000 })
					}
				} else {
					uni.showToast({ title: '提交波次: 请求失败 HTTP ' + res.statusCode, icon: 'none', duration: 3000 })
				}
				return ''
			} catch (e) {
				console.warn('【提交波次】请求失败:', e)
				uni.showToast({ title: '提交波次: 网络请求失败', icon: 'none', duration: 3000 })
				return ''
			}
		},

		// 绑定波次（提交波次成功后调用），返回 { receiving_order_id, wave_task_batch_no }
		async callBindWaveApi(timestamp, waveNo) {
			const token = uni.getStorageSync('token') || ''
			var operatorName = uni.getStorageSync('nickName') || ''
			var operatorId = uni.getStorageSync('aboutId') || ''
			const params = {
				app_key: 'psi',
				client_id: 'psi',
				wave_no: String(waveNo),
				operator: operatorName,
				operator_id: String(operatorId),
				remark: 'app',
				timestamp: timestamp,
				sign_method: 'md5'
			}
			var sign = calculateSign(params)
			params.sign = sign

			try {
				const res = await new Promise(function (resolve, reject) {
					uni.request({
						url: 'https://psi.api.buzhiyushu.cn/api/receiving/bind-wave',
						method: 'POST',
						header: {
							'Content-Type': 'application/x-www-form-urlencoded',
							'Authorization': 'Bearer ' + token
						},
						data: params,
						success: function (r) { resolve(r) },
						fail: function (e) { reject(e) }
					})
				})
				console.log('【绑定波次】返回值:', res.statusCode, res.data)

				if (res.statusCode === 200 && res.data) {
					var bindResp = res.data
					if (typeof bindResp === 'string') {
						try { bindResp = JSON.parse(bindResp) } catch (e) { bindResp = {} }
					}
					if (bindResp.code === 200 && bindResp.data && bindResp.data.receiving_order_id) {
						return {
							receiving_order_id: bindResp.data.receiving_order_id,
							wave_task_batch_no: bindResp.data.wave_task_batch_no || '',
							wave_task_id: bindResp.data.wave_task_id || ''
						}
					} else {
						uni.showToast({ title: '绑定波次: ' + (bindResp.msg || '返回数据异常'), icon: 'none', duration: 3000 })
					}
				} else {
					uni.showToast({ title: '绑定波次: 请求失败 HTTP ' + res.statusCode, icon: 'none', duration: 3000 })
				}
				return null
			} catch (e) {
				console.warn('【绑定波次】请求失败:', e)
				uni.showToast({ title: '绑定波次: 网络请求失败', icon: 'none', duration: 3000 })
				return null
			}
		},

		// 提交入库（bind-wave 成功后调用）
		async callReceiveSubmitApi(timestamp, bindResult, productId, stock, warehouseData) {
			const token = uni.getStorageSync('token') || ''
			var locationId = warehouseData && warehouseData.locationId
				? String(warehouseData.locationId)
				: (warehouseData && warehouseData.id ? String(warehouseData.id) : '')
			const params = {
				app_key: 'psi',
				client_id: 'psi',
				receiving_order_id: String(bindResult.receiving_order_id),
				'items[0][product_id]': String(productId),
				'items[0][quantity]': stock,
				'items[0][location_id]': locationId,
				'items[0][batch_no]': bindResult.wave_task_batch_no,
				wave_task_id: String(bindResult.wave_task_id),
				timestamp: timestamp,
				sign_method: 'md5'
			}
			var sign = calculateSign(params)
			params.sign = sign

			console.log('【提交入库】请求地址:', 'https://psi.api.buzhiyushu.cn/api/receiving/submit')
			console.log('【提交入库】请求参数:', params)

			try {
				const res = await new Promise(function (resolve, reject) {
					uni.request({
						url: 'https://psi.api.buzhiyushu.cn/api/receiving/submit',
						method: 'POST',
						header: {
							'Content-Type': 'application/x-www-form-urlencoded',
							'Authorization': 'Bearer ' + token
						},
						data: params,
						success: function (r) { resolve(r) },
						fail: function (e) { reject(e) }
					})
				})
				console.log('【提交入库】返回值:', res.statusCode, res.data)

				if (res.statusCode === 200 && res.data) {
					var submitResp = res.data
					if (typeof submitResp === 'string') {
						try { submitResp = JSON.parse(submitResp) } catch (e) { submitResp = {} }
					}
					if (submitResp.code !== 200) {
						uni.showToast({ title: '提交入库: ' + (submitResp.msg || '返回数据异常'), icon: 'none', duration: 3000 })
					}
				} else {
					uni.showToast({ title: '提交入库: 请求失败 HTTP ' + res.statusCode, icon: 'none', duration: 3000 })
				}
			} catch (e) {
				console.warn('【提交入库】请求失败:', e)
				uni.showToast({ title: '提交入库: 网络请求失败', icon: 'none', duration: 3000 })
			}
		},

		// 查看小车列表，返回第一个小车的 {car_id, car_code}，无小车时弹窗提示返回 null
		async callCarListApi(timestamp) {
			const token = uni.getStorageSync('token') || ''
			const params = {
				app_key: 'psi',
				client_id: 'psi',
				page: '1',
				page_size: '999999',
				timestamp: timestamp,
				sign_method: 'md5'
			}
			var sign = calculateSign(params)
			params.sign = sign

			try {
				const res = await new Promise(function (resolve, reject) {
					uni.request({
						url: 'https://psi.api.buzhiyushu.cn/api/car/list',
						method: 'GET',
						header: {
							'Content-Type': 'application/x-www-form-urlencoded',
							'Authorization': 'Bearer ' + token
						},
						data: params,
						success: function (r) { resolve(r) },
						fail: function (e) { reject(e) }
					})
				})
				console.log('【小车列表】返回值:', res.statusCode, res.data)

				if (res.statusCode === 200 && res.data && res.data.code === 0 && res.data.data) {
					var list = res.data.data.list || []
					if (list.length > 0) {
						var firstCar = list[0]
						return { car_id: firstCar.id, car_code: firstCar.code }
					}
				} else if (res.data && res.data.code !== 0) {
					uni.showToast({ title: '获取小车列表: ' + (res.data.msg || '查询失败'), icon: 'none', duration: 3000 })
				} else if (res.statusCode !== 200) {
					uni.showToast({ title: '获取小车列表: 请求失败 HTTP ' + res.statusCode, icon: 'none', duration: 3000 })
				}

				// 无小车 → 弹窗提示，返回 null
				uni.showModal({
					title: '系统提示',
					content: '当前没有可用的购物车，请先创建购物车',
					showCancel: false
				})
				return null
			} catch (e) {
				console.warn('【小车列表】请求失败:', e)
				uni.showModal({
					title: '系统提示',
					content: '获取购物车列表失败，请稍后重试',
					showCancel: false
				})
				return null
			}
		},

		// 无ISBN - 书名搜索（使用与ISBN相同的kongfz接口）
		searchNoIsbn() {
			if (!this.isLoggedIn) {
				uni.showToast({ title: '请先登录孔网账号', icon: 'none' })
				return
			}
			if (!this.noIsbnBookName) {
				uni.showToast({ title: '请输入书名', icon: 'none' })
				return
			}
			// 先查询PSI系统已有图书
			this.searchNoIsbnBook(function(hasData) {
				if (!hasData) {
					// 无匹配数据，走孔网搜索
					this.searchNoIsbnKongfz()
				}
			}.bind(this))
		},

		// 无ISBN - 查询PSI系统已有图书（getNoIsbnBook），有数据则弹窗选择
		searchNoIsbnBook(callback) {
			var ts = String(Math.floor(Date.now() / 1000))
			var token = uni.getStorageSync('token') || ''
			var params = {
				app_key: 'psi',
				client_id: 'psi',
				timestamp: ts,
				sign_method: 'md5',
				book_name: this.noIsbnBookName || '',
				author: this.noIsbnAuthor || '',
				publisher: this.noIsbnPublisher || ''
			}
			var sign = calculateSign(params)

			var q = []
			q.push('app_key=' + encodeURIComponent(params.app_key))
			q.push('client_id=' + encodeURIComponent(params.client_id))
			q.push('timestamp=' + encodeURIComponent(params.timestamp))
			q.push('sign_method=' + encodeURIComponent(params.sign_method))
			q.push('book_name=' + encodeURIComponent(params.book_name))
			q.push('author=' + encodeURIComponent(params.author))
			q.push('publisher=' + encodeURIComponent(params.publisher))
			q.push('sign=' + encodeURIComponent(sign))
			var url = 'https://psi.api.buzhiyushu.cn/api/getNoIsbnBook?' + q.join('&')

			console.log('【getNoIsbnBook】请求URL:', url)

			var that = this
			uni.request({
				url: url,
				method: 'GET',
				header: {
					'Authorization': 'Bearer ' + token
				},
				success: function(res) {
					console.log('【getNoIsbnBook】响应:', res.statusCode, res.data)
					if (res.statusCode === 200 && res.data && res.data.code === 200) {
						var list = (res.data.data && res.data.data.list) || []
						if (list.length > 0) {
							// 使用自定义弹窗
							that.noIsbnBookList = list
							that.noIsbnBookPopupVisible = true
							return
						}
						// code=200但无数据，走回调（进入孔网搜索）
						if (typeof callback === 'function') callback.call(that, false)
					} else {
						// 非200或code≠200，显示错误，不执行下一步
						var errMsg = ''
						if (res.data) {
							errMsg = res.data.msg || res.data.message || ('请求失败: ' + res.statusCode)
						} else {
							errMsg = '请求失败: HTTP ' + res.statusCode
						}
						console.error('【getNoIsbnBook】错误:', errMsg)
						uni.showToast({ title: errMsg, icon: 'none', duration: 3000 })
						if (typeof callback === 'function') callback.call(that, true)
					}
				},
				fail: function(err) {
					console.error('【getNoIsbnBook】网络请求失败:', JSON.stringify(err))
					uni.showToast({ title: '网络请求失败', icon: 'none', duration: 3000 })
					if (typeof callback === 'function') callback.call(that, true)
				}
			})
		},

		// 无ISBN已有图书弹窗 - 关闭（取消选择，走孔夫子搜索）
		closeNoIsbnBookPopup() {
			this.noIsbnBookPopupVisible = false
			this.noIsbnBookList = []
			// 取消选择，用表单数据走孔夫子搜索
			this.searchNoIsbnKongfz()
		},
		// 无ISBN已有图书弹窗 - 选中一项
		selectNoIsbnBookItem(selected) {
			if (selected.book_name) this.noIsbnBookName = selected.book_name
			if (selected.author) this.noIsbnAuthor = selected.author
			if (selected.publishing) this.noIsbnPublisher = selected.publishing
			if (selected.isbn) {
				this.noIsbnIsbn = selected.isbn
				this.noIsbnUnifyIsbn = ''
			}
			if (selected.publication_time && Number(selected.publication_time) > 0) {
				var d = new Date(Number(selected.publication_time) * 1000)
				this.noIsbnPrintTime = d.getFullYear() + '-' + String(d.getMonth() + 1).padStart(2, '0')
			}
			if (selected.words_count) this.noIsbnWordCount = String(selected.words_count)
			if (selected.price) this.noIsbnOriginalPrice = String(selected.price)
			if (selected.binding) this.noIsbnBinding = selected.binding
			uni.showToast({ title: '已选择: ' + (selected.book_name || ''), icon: 'success' })
			this.closeNoIsbnBookPopup()
			// 选择后继续走孔夫子搜索流程
			this.searchNoIsbnKongfz()
		},

		// 孔夫子搜索（带会话过期自动重登录+重试）
		kongfzSearchWithRetry(keyword, searchOpts) {
			var that = this
			var maxRetry = 1  // 最多重试1次
			return new Promise(function(resolve, reject) {
				var doSearch = function(phpsessid, retryCount) {
					var opts = Object.assign({}, searchOpts, { phpsessid: phpsessid })
					Promise.all([
						searchProducts(keyword, opts),
						searchFacet(keyword, opts),
						searchFacet(keyword, Object.assign({}, opts, { dataType: 1 }))
					]).then(function(results) {
						resolve(results)
					}).catch(function(err) {
						if (err && err.message === 'KONGZ_SESSION_EXPIRED' && retryCount < maxRetry) {
							console.warn('孔夫子-会话过期,尝试自动重新登录...')
							// 使用第一个已保存账号重新登录
							var accountList = that.savedAccountList || []
							if (accountList.length > 0) {
								var acc = accountList[0]
								console.log('孔夫子-自动登录:', acc.username)
								uni.showToast({ title: '孔网会话过期,自动登录中...', icon: 'none', duration: 2000 })
								kongfzLogin(acc.username, acc.password).then(function(loginRes) {
									if (loginRes.success) {
										that.kongfzToken = loginRes.token
										that.isLoggedIn = true
										uni.setStorageSync('kongfz_phpsessid', loginRes.token)
										console.log('孔夫子-自动登录成功,重试搜索')
										doSearch(loginRes.token, retryCount + 1)
									} else {
										console.warn('孔夫子-自动登录失败:', loginRes.message)
										uni.showToast({ title: '孔网自动登录失败: ' + loginRes.message, icon: 'none', duration: 3000 })
										resolve([{ total: 0, list: [] }, { newCount: 0, oldCount: 0, totalFound: 0 }, { newCount: 0, oldCount: 0, totalFound: 0 }])
									}
								}).catch(function() {
									uni.showToast({ title: '孔网自动登录失败: 网络异常', icon: 'none', duration: 3000 })
									resolve([{ total: 0, list: [] }, { newCount: 0, oldCount: 0, totalFound: 0 }, { newCount: 0, oldCount: 0, totalFound: 0 }])
								})
							} else {
								console.warn('孔夫子-无已保存账号,无法自动登录')
								uni.showToast({ title: '孔网会话过期,无已保存账号无法自动登录', icon: 'none', duration: 3000 })
								resolve([{ total: 0, list: [] }, { newCount: 0, oldCount: 0, totalFound: 0 }, { newCount: 0, oldCount: 0, totalFound: 0 }])
							}
						} else {
							resolve([{ total: 0, list: [] }, { newCount: 0, oldCount: 0, totalFound: 0 }, { newCount: 0, oldCount: 0, totalFound: 0 }])
						}
					})
				}
				var phpsessid = that.kongfzToken || uni.getStorageSync('kongfz_phpsessid') || ''
				doSearch(phpsessid, 0)
			})
		},

		// 无ISBN - 孔夫子搜索（原searchNoIsbn逻辑）
		searchNoIsbnKongfz() {
			if (!this.isLoggedIn) {
				uni.showToast({ title: '请先登录孔网账号', icon: 'none' })
				return
			}
			if (!this.noIsbnBookName) {
				uni.showToast({ title: '请输入书名', icon: 'none' })
				return
			}
			var that = this
			this.noIsbnLoading = true
			this.noIsbnProductList = []
			const keyword = this.noIsbnBookName
			this.kongfzSearchWithRetry(keyword, { sortType: '7', quality: this.noIsbnConditionValue }).then(function(result) {
				var productsData = result[0]
				var onSaleFacet = result[1]
				var soldFacet = result[2]
				that.noIsbnLoading = false
				// 收集作者和出版社选项
				const authorSet = new Set()
				const publisherSet = new Set()
				if (productsData && productsData.total > 0) {
					const list = (productsData.list || []).slice(0, 12)
					that.noIsbnProductList = list.map(item => {
						const cleanPrice = parseFloat((item.priceText || '0').replace(/[^\d.]/g, ''))
						let shippingFee = 0
						if (item.postage) {
							if (typeof item.postage === 'number' || typeof item.postage === 'string') {
								shippingFee = parseFloat(item.postage) || 0
							} else if (item.postage.shippingList && item.postage.shippingList.length > 0) {
								shippingFee = parseFloat(item.postage.shippingList[0].shippingFee || 0)
							} else if (item.postage.shippingFee) {
								shippingFee = parseFloat(item.postage.shippingFee || 0)
							}
						}
						if (shippingFee === 0 && item.shippingFee) {
							shippingFee = parseFloat(item.shippingFee) || 0
						}
						const totalPrice = Number((cleanPrice + shippingFee).toFixed(2))
						// 提取作者和出版社
						if (item.author) authorSet.add(item.author.trim())
						if (item.shopName) publisherSet.add(item.shopName.trim())
						return {
							image: item.imgBigUrl || '',
							totalPrice: totalPrice,
							bookPrice: cleanPrice,
							shippingFee: shippingFee,
							condition: item.qualityText || '',
							shopName: item.shopName || '',
							bookName: item.title || '',
							author: item.author || '',
							press: item.press || '',
							pubDate: item.pubDateText || '',
							bookId: item.id || ''
						}
					})
				}
				// 市场统计
				that.noIsbnMarketData = {
					onSale: onSaleFacet ? onSaleFacet.totalFound : (productsData ? productsData.total : 0),
					old: onSaleFacet ? onSaleFacet.oldCount : 0,
					new: onSaleFacet ? onSaleFacet.newCount : 0,
					sold: soldFacet ? (soldFacet.oldCount + soldFacet.newCount) : 0
				}
				// 填充下拉选项
				that.noIsbnAuthorOptions = Array.from(authorSet).filter(Boolean).slice(0, 10)
				that.noIsbnPublisherOptions = Array.from(publisherSet).filter(Boolean).slice(0, 10)
				// 自动计算并填入售价
				that.$nextTick(() => {
					if (that.calculatedNoIsbnPrice > 0) {
						that.noIsbnPrice = String(that.calculatedNoIsbnPrice)
					}
				})
			}).catch(function(err) {
				console.error('无ISBN搜索失败:', err)
				that.noIsbnLoading = false
				that.noIsbnMarketData = { onSale: 0, old: 0, new: 0, sold: 0 }
				uni.showToast({ title: '查询失败', icon: 'none' })
			})
		},

		// 无ISBN - 版权页比价（带作者+出版社精确搜索）
		searchNoIsbnCopyright() {
			if (!this.isLoggedIn) {
				uni.showToast({ title: '请先登录孔网账号', icon: 'none' })
				return
			}
			if (!this.noIsbnBookName) {
				uni.showToast({ title: '请输入书名', icon: 'none' })
				return
			}
			this.noIsbnLoading = true
			this.noIsbnProductList = []
			const phpsessid = this.kongfzToken || uni.getStorageSync('kongfz_phpsessid') || ''
			const keyword = this.noIsbnBookName
			searchProducts(keyword, {
				phpsessid,
				sortType: '7',
				quality: this.noIsbnConditionValue,
				publisher: this.noIsbnPublisher,
				author: this.noIsbnAuthor
			}).then((productsData) => {
				this.noIsbnLoading = false
				if (productsData && productsData.total > 0) {
					const list = (productsData.list || []).slice(0, 12)
					this.noIsbnProductList = list.map(item => {
						const cleanPrice = parseFloat((item.priceText || '0').replace(/[^\d.]/g, ''))
						let shippingFee = 0
						if (item.postage) {
							if (typeof item.postage === 'number' || typeof item.postage === 'string') {
								shippingFee = parseFloat(item.postage) || 0
							} else if (item.postage.shippingList && item.postage.shippingList.length > 0) {
								shippingFee = parseFloat(item.postage.shippingList[0].shippingFee || 0)
							} else if (item.postage.shippingFee) {
								shippingFee = parseFloat(item.postage.shippingFee || 0)
							}
						}
						if (shippingFee === 0 && item.shippingFee) {
							shippingFee = parseFloat(item.shippingFee) || 0
						}
						const totalPrice = Number((cleanPrice + shippingFee).toFixed(2))
						return {
							image: item.imgBigUrl || '',
							totalPrice: totalPrice,
							bookPrice: cleanPrice,
							shippingFee: shippingFee,
							condition: item.qualityText || '',
							shopName: item.shopName || '',
							bookName: item.title || '',
							author: item.author || '',
							press: item.press || '',
							pubDate: item.pubDateText || '',
							bookId: item.id || ''
						}
					})
					// 自动计算并填入售价
					this.$nextTick(() => {
						if (this.calculatedNoIsbnPrice > 0) {
							this.noIsbnPrice = String(this.calculatedNoIsbnPrice)
						}
					})
				}
			}).catch(err => {
				console.error('版权比价失败:', err)
				this.noIsbnLoading = false
				uni.showToast({ title: '比价失败', icon: 'none' })
			})
		},

		// 无ISBN - 识图上传（拍照→OCR识别→自动填写表单）
		chooseImageNoIsbn() {
			uni.showToast({ title: '请选择图书封面', icon: 'none' })
			uni.chooseImage({
				count: 1,
				sizeType: ['original', 'compressed'],
				sourceType: ['album', 'camera'],
				success: (res) => {
					const tempFilePaths = res.tempFilePaths
					if (!tempFilePaths || tempFilePaths.length === 0) return
					const filePath = tempFilePaths[0]
					uni.showLoading({ title: '识别中...', mask: true })
					// 压缩图片（大于500KB）
					this.compressNoIsbnImage(filePath).then(compressedPath => {
						this.ocrNoIsbnImage(compressedPath)
					})
				}
			})
		},

		// 压缩图片
		compressNoIsbnImage(filePath) {
			return new Promise((resolve) => {
				uni.getFileInfo({
					filePath: filePath,
					success: (info) => {
						if (info.size > 500 * 1024) {
							uni.compressImage({
								src: filePath,
								quality: 80,
								success: (res) => resolve(res.tempFilePath),
								fail: () => resolve(filePath)
							})
						} else {
							resolve(filePath)
						}
					},
					fail: () => resolve(filePath)
				})
			})
		},

		// OCR识别并填充表单
		ocrNoIsbnImage(filePath) {
			uni.uploadFile({
				url: 'https://book.xcx.ocr.buzhiyushu.cn/ocr',
				filePath: filePath,
				name: 'file',
				success: (res) => {
					uni.hideLoading()
					try {
						const ocrData = JSON.parse(res.data)
						console.log('【OCR】原始返回:', JSON.stringify(ocrData))
						if (ocrData && ocrData.texts) {
							const texts = ocrData.texts
							// 自动填充表单
							if (texts.书名) this.noIsbnBookName = texts.书名
							if (texts.作者) this.noIsbnAuthor = texts.作者
							if (texts.出版社) this.noIsbnPublisher = texts.出版社
							if (texts.出版时间) this.noIsbnPrintTime = texts.出版时间
							if (texts.定价) {
								this.noIsbnOriginalPrice = texts.定价.replace('元', '').trim()
							}
							if (texts.开本) {
								const fmt = String(texts.开本).replace('开', '').trim()
								this.noIsbnFormat = this.noIsbnFormatOptions.includes(fmt) ? fmt : fmt + '开'
							}
							// 尝试多种字段名获取 ISBN（OCR 可能返回不同字段名）
							var isbnText = texts.ISBN || texts.isbn || texts.isbn13 || texts.barcode || texts.条码 || ''
							if (isbnText && /^\d/.test(isbnText)) {
								this.noIsbnIsbn = isbnText
								this.noIsbnUnifyIsbn = ''
							}
							// 书号（OCR 可能返回 书号 或 统一书号）
							var bookCodeText = texts.书号 || texts.统一书号 || texts.bookcode || texts.unified_code || ''
							if (bookCodeText) {
								const bookCode = bookCodeText.replace(/\D/g, '')
								if (bookCode.length === 13) {
									this.noIsbnIsbn = bookCode
								} else if (bookCode.length === 10 && /^\d{9}[\dXx]$/i.test(bookCode)) {
									this.noIsbnIsbn = this.convertIsbn10To13(bookCode)
								} else {
									this.noIsbnIsbn = '678' + String(Date.now()).slice(-10)
								}
								this.noIsbnUnifyIsbn = bookCodeText
							}
							// ISBN 和书号都为空 → 生成 678 开头随机数显示在表单中
							if (!this.noIsbnIsbn && !this.noIsbnUnifyIsbn) {
								this.noIsbnIsbn = this.generateRandomIsbn()
							}
							if (texts.字数) this.noIsbnWordCount = this.processNoIsbnWordage(texts.字数)

							uni.showToast({ title: '识别成功', icon: 'success' })

							// 有书名则先查PSI系统已有图书，无匹配时自动搜索孔网比价
							if (this.noIsbnBookName) {
								setTimeout(() => this.searchNoIsbn(), 500)
							}
						} else {
							uni.showToast({ title: '识别失败，未识别到图书信息', icon: 'none' })
						}
					} catch (e) {
						console.error('OCR解析失败:', e)
						uni.showToast({ title: '识别失败，请重试', icon: 'none' })
					}
				},
				fail: (err) => {
					uni.hideLoading()
					console.error('OCR请求失败:', err)
					uni.showToast({ title: '网络错误，请重试', icon: 'none' })
				}
			})
		},

		// 处理字数文本（如"300千字"→300000）
		processNoIsbnWordage(wordage) {
			if (!wordage) return ''
			if (typeof wordage === 'string' && wordage.includes('千字')) {
				const match = wordage.match(/(\d+(\.\d+)?)/)
				if (match && match[1]) {
					return Math.round(parseFloat(match[1]) * 1000).toString()
				}
			}
			return wordage.replace(/[^\d]/g, '')
		},

		// 无ISBN - 选择作者
		selectNoIsbnAuthor(item) {
			this.noIsbnAuthor = item
			this.noIsbnAuthorDropdownVisible = false
		},

		// 无ISBN - 选择出版社
		selectNoIsbnPublisher(item) {
			this.noIsbnPublisher = item
			this.noIsbnPublisherDropdownVisible = false
		},

		// 无ISBN - 选择开本
		selectNoIsbnFormat(item) {
			this.noIsbnFormat = item
			this.noIsbnFormatDropdownVisible = false
		},

		selectNoIsbnBinding(item) {
			this.noIsbnBinding = item
			this.noIsbnBindingDropdownVisible = false
		},

		// 登录 - 接入孔夫子真实登录
		handleLogin() {
			if (!this.loginAccount) {
				uni.showToast({ title: '请输入账号', icon: 'none' })
				return
			}
			if (!this.loginPassword) {
				uni.showToast({ title: '请输入密码', icon: 'none' })
				return
			}
			this.doLogin(this.loginAccount, this.loginPassword)
		},

		doLogin(username, password) {
			uni.showLoading({ title: '登录中...', mask: true })
			kongfzLogin(username, password).then(res => {
				uni.hideLoading()
				if (res.success) {
					this.kongfzToken = res.token
					this.isLoggedIn = true
					this.shopName = username
					this.shopRegion = '孔夫子旧书网'
					// 持久化登录状态
					uni.setStorageSync('kongfz_phpsessid', res.token)
					uni.setStorageSync('kongfz_shop_name', username)
					uni.setStorageSync('kongfz_shop_region', '孔夫子旧书网')
					if (this.rememberPassword) {
						uni.setStorageSync('kongfz_remembered_account', username)
					}
					// 保存到账号列表
					this.saveAccount(username, password)
					uni.showToast({ title: '登录成功', icon: 'success' })
				} else {
					uni.showToast({ title: res.message || '登录失败', icon: 'none' })
				}
			}).catch(err => {
				uni.hideLoading()
				uni.showToast({ title: '网络异常，请重试', icon: 'none' })
				console.error('登录异常:', err)
			})
		},

		handleLogout() {
			uni.showModal({
				title: '提示',
				content: '确定要退出登录吗？',
				success: (res) => {
					if (res.confirm) {
						this.isLoggedIn = false
						this.shopName = ''
						this.shopRegion = ''
						this.kongfzToken = ''
						uni.removeStorageSync('kongfz_phpsessid')
						uni.removeStorageSync('kongfz_shop_name')
						uni.removeStorageSync('kongfz_shop_region')
					}
				}
			})
		},

		// 加载已保存账号列表
		loadSavedAccounts() {
			try {
				const list = uni.getStorageSync('kongfz_saved_accounts')
				this.savedAccountList = list ? JSON.parse(list) : []
			} catch (e) {
				this.savedAccountList = []
			}
		},

		// 保存账号到列表
		saveAccount(username, password) {
			const accounts = [...this.savedAccountList]
			// 去重：如果已存在相同用户名，替换密码
			const idx = accounts.findIndex(a => a.username === username)
			if (idx >= 0) {
				accounts[idx].password = password
			} else {
				accounts.push({ username, password })
			}
			this.savedAccountList = accounts
			uni.setStorageSync('kongfz_saved_accounts', JSON.stringify(accounts))
		},

		// 点击已保存账号快速登录
		quickLogin(acc) {
			uni.showLoading({ title: '登录中...', mask: true })
			this.loginAccount = acc.username
			this.loginPassword = acc.password
			this.doLogin(acc.username, acc.password)
		},

		// 删除已保存账号
		deleteSavedAccount(idx) {
			uni.showModal({
				title: '提示',
				content: '确定要删除该账号吗？',
				success: (res) => {
					if (res.confirm) {
						this.savedAccountList.splice(idx, 1)
						uni.setStorageSync('kongfz_saved_accounts', JSON.stringify(this.savedAccountList))
					}
				}
			})
		},

		// 小数输入处理（保留两位小数）
		onDecimalInput(field, event) {
			let val = event.detail.value
			val = val.replace(/[^\d.]/g, '')
			const parts = val.split('.')
			if (parts.length > 2) {
				val = parts[0] + '.' + parts.slice(1).join('')
			}
			if (parts.length === 2 && parts[1].length > 2) {
				val = parts[0] + '.' + parts[1].substring(0, 2)
			}
			this[field] = val
		},

		// 加载定价策略配置
		loadPriceConfig() {
			try {
				const saved = uni.getStorageSync('price_config')
				if (saved) {
					const cfg = JSON.parse(saved)
					this.priceMode = cfg.priceMode || 'lowest'
					this.lowestRank = cfg.lowestRank || 1
					this.averageCount = cfg.averageCount || 2
					this.shippingFee = cfg.shippingFee || 0
					this.priceDiscount = cfg.priceDiscount || 0
					this.minBookPrice = cfg.minBookPrice || 0
				}
			} catch (e) {
				console.error('加载定价配置失败:', e)
			}
		},

		// 无ISBN上传 - 获取ISBN值（按规则处理）
		getNoIsbnIsbnValue() {
			var raw = (this.noIsbnIsbn || '').replace(/[^0-9]/g, '')

			// 1. 13位、978/979开头 → 直接返回
			if (raw.length === 13 && (raw.indexOf('978') === 0 || raw.indexOf('979') === 0)) {
				return raw
			}

			// 2. 10位 → 换算成13位
			if (raw.length === 10) {
				return this.convertIsbn10To13(raw)
			}

			// 3. 统一书号
			if (this.noIsbnUnifyIsbn) return this.noIsbnUnifyIsbn

			// 4. 其他情况（为空或无法识别）→ 生成678开头的13位随机数
			return this.generateRandomIsbn()
		},

		// 10位ISBN转13位
		convertIsbn10To13(isbn10) {
			var prefix = '978'
			var first9 = isbn10.substring(0, 9)
			var base12 = prefix + first9
			// 重新计算第13位校验码
			var sum = 0
			for (var i = 0; i < 12; i++) {
				var weight = (i % 2 === 0) ? 1 : 3
				sum += parseInt(base12[i], 10) * weight
			}
			var remainder = sum % 10
			var checkDigit = remainder === 0 ? 0 : 10 - remainder
			return base12 + checkDigit
		},

		// 生成678开头的13位随机ISBN
		generateRandomIsbn() {
			var rand = ''
			for (var i = 0; i < 10; i++) {
				rand += Math.floor(Math.random() * 10)
			}
			return '678' + rand
		},

		// 保存定价策略配置
		savePriceConfig() {
			const cfg = {
				priceMode: this.priceMode,
				lowestRank: Number(this.lowestRank) || 1,
				averageCount: Number(this.averageCount) || 2,
				shippingFee: Number(this.shippingFee) || 0,
				priceDiscount: Number(this.priceDiscount) || 0,
				minBookPrice: Number(this.minBookPrice) || 0
			}
			uni.setStorageSync('price_config', JSON.stringify(cfg))
			uni.showToast({ title: '设置已保存', icon: 'success' })
		}
	}
}
</script>

<style>
.page-container {
  background-color: #f5f6fa;
  min-height: 100vh;
}

/* ========== Tab 头部 ========== */
.tab-header {
  display: flex;
  background-color: #ffffff;
  border-bottom: 2rpx solid #e4e7ed;
}

.tab-item {
  flex: 1;
  text-align: center;
  padding: 26rpx 0;
  position: relative;
}

.tab-item.active::after {
  content: '';
  position: absolute;
  bottom: 0;
  left: 50%;
  transform: translateX(-50%);
  width: 48rpx;
  height: 4rpx;
  background-color: #409eff;
  border-radius: 2rpx;
}

.tab-text {
  font-size: 28rpx;
  color: #606266;
}

.tab-item.active .tab-text {
  color: #409eff;
  font-weight: 600;
}

/* ========== Swiper ========== */
.tab-swiper {
  height: calc(100vh - 180rpx);
}

.settings-swiper {
  height: calc(100vh - 280rpx);
}

.content-scroll {
  height: calc(100vh - 200rpx);
}

.tab-content {
  padding: 16rpx;
}

/* ========== 基本信息合并块（品相+货区+书名+价格） ========== */
.info-block {
  background-color: #ffffff;
  border-radius: 12rpx;
  border: 2rpx solid #ebeef5;
  padding: 20rpx 24rpx;
}

.info-block-row {
  padding: 4rpx 0;
}

.info-block-divider {
  height: 2rpx;
  background-color: #f2f3f5;
  margin: 6rpx 0;
}

/* 行内标签在前 */
.info-inline-row {
  display: flex;
  align-items: center;
  padding: 4rpx 0;
}

.info-inline-label {
  font-size: 26rpx;
  color: #606266;
  font-weight: 500;
  flex-shrink: 0;
  margin-right: 16rpx;
  white-space: nowrap;
}

.info-inline-input {
  flex: 1;
}

/* ========== 表单区块 ========== */
.form-section {
  background-color: #ffffff;
  border-radius: 12rpx;
  border: 2rpx solid #ebeef5;
  margin-bottom: 16rpx;
  padding: 24rpx;
}

.section-title {
  display: flex;
  align-items: center;
  margin-bottom: 14rpx;
}

.title-text {
  font-size: 28rpx;
  color: #303133;
  font-weight: 600;
}

.photo-count {
  font-size: 22rpx;
  color: #909399;
  margin-left: auto;
}

.field-label {
  display: block;
  margin-bottom: 10rpx;
}

.label-text {
  font-size: 26rpx;
  color: #606266;
  font-weight: 500;
}

/* ========== 输入框 ========== */
.form-input {
  background-color: #ffffff;
  border: 2rpx solid #dcdfe6;
  border-radius: 8rpx;
  height: 76rpx;
  padding: 0 16rpx;
  font-size: 28rpx;
  color: #303133;
  box-sizing: border-box;
  width: 100%;
  -webkit-appearance: none;
  appearance: none;
}

.form-input:focus {
  border-color: #409eff;
}

/* 下拉内联框：右侧直角与▼按钮衔接 */
.dropdown-wrapper .form-input {
  border-radius: 8rpx 0 0 8rpx;
  border-right: none;
}

/* ========== 选择器 ========== */
.picker-box {
  background-color: #ffffff;
  border: 2rpx solid #dcdfe6;
  border-radius: 8rpx;
  height: 76rpx;
  padding: 0 16rpx;
  font-size: 28rpx;
  box-sizing: border-box;
  display: flex;
  align-items: center;
  justify-content: space-between;
}

.picker-value {
  font-size: 28rpx;
  color: #606266;
  flex: 1;
}

.picker-arrow {
  font-size: 36rpx;
  color: #c0c4cc;
}

/* 印刷时间选择器：和表单输入框一致 */
.picker-value-text {
  display: flex;
  align-items: center;
}
uni-picker,
picker {
  display: block;
  width: 100%;
}

/* ========== ISBN 输入 ========== */
.isbn-input-box {
  display: flex;
  gap: 10rpx;
  align-items: center;
}

.isbn-input {
  flex: 1;
  background-color: #ffffff;
  border: 2rpx solid #dcdfe6;
  border-radius: 8rpx;
  height: 76rpx;
  padding: 0 16rpx;
  font-size: 28rpx;
  box-sizing: border-box;
}

/* ========== 行内字段 ========== */
.inline-fields {
  display: flex;
  align-items: center;
  gap: 16rpx;
}

.inline-field {
  flex: 1;
}

.inline-field.narrow {
  flex: none;
  width: 250rpx;
}

.inline-field.isbn-field {
  flex: 1;
  max-width: 80%;
}

/* ========== 价格输入 ========== */
.price-input-box {
  display: flex;
  align-items: center;
  background-color: #ffffff;
  border: 2rpx solid #dcdfe6;
  border-radius: 8rpx;
  height: 76rpx;
  padding: 0 16rpx;
  font-size: 28rpx;
  box-sizing: border-box;
}

.price-input-box:focus-within {
  border-color: #409eff;
}

.price-symbol {
  color: #f56c6c;
  font-size: 28rpx;
  font-weight: 500;
  margin-right: 6rpx;
}

.price-input {
  flex: 1;
  border: none;
  outline: none;
  height: 100%;
  font-size: 28rpx;
  background: transparent;
}

/* ========== 版权页比价按钮 ========== */
.copyright-btn {
  margin-left: auto;
  padding: 8rpx 16rpx;
  background-color: #409eff;
  border-radius: 6rpx;
  display: flex;
  align-items: center;
  justify-content: center;
}

.copyright-btn-text {
  font-size: 24rpx;
  color: #ffffff;
  font-weight: 500;
}

/* ========== 扫描/搜索按钮 ========== */
.scan-btn {
  background-color: #67c23a;
  border-radius: 6rpx;
  box-shadow: 0 2rpx 6rpx rgba(103,194,58,0.3);
  width: 64rpx;
  height: 64rpx;
  display: flex;
  align-items: center;
  justify-content: center;
}

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

.search-btn {
  background-color: #409eff;
  border-radius: 6rpx;
  box-shadow: 0 2rpx 6rpx rgba(64,158,255,0.3);
  width: 64rpx;
  height: 64rpx;
  display: flex;
  align-items: center;
  justify-content: center;
}

.search-text {
  color: #ffffff;
  font-size: 28rpx;
  font-weight: 600;
}

/* ========== 品相选择 ========== */
.condition-list {
  display: flex;
  flex-wrap: nowrap;
  gap: 8rpx;
  overflow-x: auto;
  white-space: nowrap;
  -webkit-overflow-scrolling: touch;
}

.condition-item {
  background-color: #f4f4f5;
  border: 2rpx solid #e9e9eb;
  border-radius: 6rpx;
  padding: 6rpx 16rpx;
  flex-shrink: 0;
}

.condition-item.active {
  background-color: #ecf5ff;
  border-color: #409eff;
}

.condition-text {
  font-size: 20rpx;
  color: #606266;
}

.condition-item.active .condition-text {
  color: #409eff;
}

/* ========== 拍照 ========== */
.photo-section {
  width: 100%;
}

.photo-list {
  display: flex;
  flex-wrap: wrap;
  gap: 10rpx;
}

.photo-item {
  width: 140rpx;
  height: 140rpx;
  border-radius: 8rpx;
  border: 2rpx solid #ebeef5;
  position: relative;
  overflow: hidden;
}

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

.photo-index-badge {
  position: absolute;
  bottom: 6rpx;
  left: 6rpx;
  background-color: rgba(0,0,0,0.55);
  border-radius: 50%;
  width: 30rpx;
  height: 30rpx;
  display: flex;
  align-items: center;
  justify-content: center;
}

.photo-index-badge-text {
  color: #ffffff;
  font-size: 20rpx;
}

.photo-delete {
  position: absolute;
  top: -8rpx;
  right: -8rpx;
  width: 38rpx;
  height: 38rpx;
  background-color: #f56c6c;
  border-radius: 50%;
  display: flex;
  align-items: center;
  justify-content: center;
  box-shadow: 0 2rpx 6rpx rgba(245,108,108,0.3);
}

.delete-icon {
  color: #ffffff;
  font-size: 22rpx;
}

.photo-add {
  width: 140rpx;
  height: 140rpx;
  border: 2rpx dashed #dcdfe6;
  border-radius: 8rpx;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  background-color: #fafafa;
}

.photo-burst {
  border-color: #409eff;
  background-color: #ecf5ff;
}

.add-icon {
  font-size: 40rpx;
  color: #909399;
}

.add-text {
  font-size: 22rpx;
  color: #909399;
  margin-top: 4rpx;
}

/* ========== 市场竞争统计 ========== */
.market-stats {
  background-color: #fafafa;
  border: 2rpx solid #ebeef5;
  border-radius: 8rpx;
  padding: 14rpx 6rpx;
  display: flex;
  justify-content: space-around;
}

.stat-item {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 4rpx;
}

.stat-label {
  font-size: 22rpx;
  color: #909399;
}

.stat-value {
  font-size: 28rpx;
  color: #303133;
  font-weight: 600;
}

/* ========== 在售商品 ========== */
.section-header-row {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: 10rpx;
  margin-bottom: 14rpx;
}

.product-count {
  font-size: 24rpx;
  color: #909399;
  margin-left: 6rpx;
}

.compare-toggle {
  display: flex;
  gap: 6rpx;
}

.toggle-btn {
  font-size: 22rpx;
  color: #909399;
  background-color: #f4f4f5;
  padding: 6rpx 14rpx;
  border-radius: 6rpx;
}

.toggle-btn.active {
  background-color: #ecf5ff;
  color: #409eff;
}

.sort-toggle {
  display: flex;
  gap: 6rpx;
}

.sort-btn {
  font-size: 22rpx;
  color: #909399;
  background-color: #f4f4f5;
  padding: 6rpx 14rpx;
  border-radius: 6rpx;
}

.sort-btn.active {
  background-color: #ecf5ff;
  color: #409eff;
}

.filter-btn {
  font-size: 24rpx;
  color: #409eff;
  margin-left: auto;
}

/* ========== 加载状态 ========== */
.loading-box {
  display: flex;
  flex-direction: column;
  align-items: center;
  padding: 40rpx 0;
  gap: 16rpx;
}

.loading-spinner {
  width: 60rpx;
  height: 60rpx;
  border: 4rpx solid #e4e7ed;
  border-top-color: #409eff;
  border-radius: 50%;
  animation: spin 0.8s linear infinite;
}

@keyframes spin {
  0% { transform: rotate(0deg); }
  100% { transform: rotate(360deg); }
}

.loading-text {
  font-size: 26rpx;
  color: #909399;
}

/* ========== 商品网格 ========== */
.product-grid {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  gap: 8rpx;
  margin-top: 10rpx;
}

.grid-item {
  background-color: #fafafa;
  border: 2rpx solid #ebeef5;
  border-radius: 8rpx;
  padding: 6rpx;
  overflow: hidden;
}

.grid-image {
  width: 100%;
  height: 120rpx;
  border-radius: 4rpx;
}

.grid-total-price {
  font-size: 20rpx;
  color: #f56c6c;
  font-weight: 600;
  display: block;
  text-align: center;
  margin-top: 2rpx;
  line-height: 1.4;
}

.grid-price-detail {
  font-size: 16rpx;
  color: #909399;
  display: block;
  text-align: center;
  line-height: 1.3;
}

.grid-book-name {
  font-size: 22rpx;
  color: #303133;
  font-weight: 500;
  display: block;
  text-align: center;
  width: 100%;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  line-height: 1.3;
}

.grid-author {
  font-size: 18rpx;
  color: #909399;
  display: block;
  text-align: center;
  width: 100%;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  line-height: 1.3;
}

.grid-condition {
  font-size: 20rpx;
  color: #606266;
  display: block;
  text-align: center;
  line-height: 1.3;
}

.grid-shop {
  font-size: 18rpx;
  color: #909399;
  display: block;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  text-align: center;
  line-height: 1.3;
}

.no-data {
  grid-column: 1 / -1;
  text-align: center;
  padding: 40rpx 0;
}

.no-data-text {
  font-size: 26rpx;
  color: #909399;
}

/* ========== 上书记录 ========== */
.history-list {
  display: flex;
  flex-direction: column;
  gap: 10rpx;
}

.history-item {
  background-color: #fafafa;
  border: 2rpx solid #f0f1f3;
  border-radius: 8rpx;
  padding: 14rpx 16rpx;
}

.history-row {
  display: flex;
  justify-content: space-between;
  align-items: center;
}

.history-date {
  font-size: 24rpx;
  color: #909399;
}

.history-condition {
  font-size: 24rpx;
  color: #606266;
}

.history-price {
  font-size: 28rpx;
  color: #f56c6c;
  font-weight: 600;
}

.history-stock {
  font-size: 24rpx;
  color: #909399;
}

.bottom-placeholder {
  height: 40rpx;
}

/* ========== 底部提交栏 ========== */
.bottom-bar {
  background-color: #ffffff;
  border-top: 2rpx solid #e4e7ed;
  padding: 16rpx 24rpx;
  position: fixed;
  bottom: 0;
  left: 0;
  right: 0;
}

.submit-btn {
  background-color: #409eff;
  border-radius: 10rpx;
  box-shadow: 0 4rpx 12rpx rgba(64,158,255,0.2);
  height: 88rpx;
  display: flex;
  align-items: center;
  justify-content: center;
}

/* ========== 折叠详情 ========== */
.detail-section-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 24rpx 20rpx;
  margin: 20rpx 0;
  background-color: #f5f7fa;
  border-radius: 8rpx;
}

.detail-section-title {
  font-size: 28rpx;
  font-weight: 600;
  color: #303133;
}

.detail-arrow {
  font-size: 24rpx;
  color: #909399;
  transition: transform 0.2s;
}

/* ========== 下拉列表（作者/出版社/开本） ========== */
.dropdown-wrapper {
  position: relative;
  display: flex;
  align-items: center;
  flex: 1;
}

.dropdown-btn {
  width: 60rpx;
  height: 76rpx;
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 24rpx;
  color: #909399;
  background-color: #f5f7fa;
  border: 2rpx solid #dcdfe6;
  border-left: none;
  border-radius: 0 8rpx 8rpx 0;
  flex-shrink: 0;
}

.dropdown-list {
  position: absolute;
  top: 100%;
  left: 0;
  right: 0;
  z-index: 100;
  background: #ffffff;
  border: 2rpx solid #dcdfe6;
  border-radius: 8rpx;
  max-height: 300rpx;
  overflow-y: auto;
  box-shadow: 0 4rpx 12rpx rgba(0,0,0,0.1);
}

.dropdown-item {
  padding: 20rpx 24rpx;
  font-size: 28rpx;
  color: #303133;
  border-bottom: 1rpx solid #f2f2f2;
}

.dropdown-item:last-child {
  border-bottom: none;
}

.dropdown-item:active {
  background-color: #f5f7fa;
}

.submit-text {
  color: #ffffff;
  font-size: 32rpx;
  font-weight: 600;
}

.submit-btn.disabled {
  opacity: 0.5;
  pointer-events: none;
}

/* ========== 筛选弹窗 ========== */
.filter-popup {
  position: fixed;
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
  background-color: rgba(0,0,0,0.3);
  z-index: 1000;
  display: flex;
  align-items: flex-end;
}

.popup-content {
  background-color: #ffffff;
  border-radius: 14rpx 14rpx 0 0;
  padding: 28rpx;
  width: 100%;
  box-sizing: border-box;
}

.popup-header {
  display: flex;
  justify-content: space-between;
  align-items: center;
  margin-bottom: 20rpx;
}

.popup-title {
  font-size: 30rpx;
  color: #303133;
  font-weight: 600;
}

.popup-close {
  font-size: 32rpx;
  color: #909399;
  padding: 8rpx;
}

.popup-body {
  max-height: 60vh;
  overflow-y: auto;
}

.filter-group {
  margin-bottom: 20rpx;
}

.group-title {
  font-size: 26rpx;
  color: #606266;
  font-weight: 500;
  display: block;
  margin-bottom: 10rpx;
}

.tag-list {
  display: flex;
  flex-wrap: wrap;
  gap: 10rpx;
}

.tag-item {
  background-color: #f4f4f5;
  border: 2rpx solid #e9e9eb;
  border-radius: 8rpx;
  padding: 12rpx 24rpx;
}

.tag-item.active {
  background-color: #ecf5ff;
  border-color: #409eff;
}

.tag-text {
  font-size: 26rpx;
  color: #606266;
}

.tag-item.active .tag-text {
  color: #409eff;
}

.popup-footer {
  display: flex;
  gap: 16rpx;
  margin-top: 24rpx;
}

.reset-btn {
  flex: 1;
  height: 76rpx;
  border: 2rpx solid #dcdfe6;
  border-radius: 10rpx;
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 28rpx;
  color: #606266;
}

.confirm-btn {
  flex: 1;
  height: 76rpx;
  background-color: #409eff;
  border-radius: 10rpx;
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 28rpx;
  color: #ffffff;
}

/* ========== 分类选择弹窗 ========== */
/* ========== 分类选择（input风格） ========== */
.category-select {
  background-color: #ffffff;
  border: 2rpx solid #dcdfe6;
  border-radius: 8rpx;
  height: 76rpx;
  padding: 0 16rpx;
  font-size: 28rpx;
  box-sizing: border-box;
  display: flex;
  align-items: center;
  justify-content: space-between;
}

.category-value {
  font-size: 28rpx;
  color: #606266;
  flex: 1;
}

/* ========== 仓库弹窗 ========== */
.warehouse-overlay {
  position: fixed;
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
  background-color: rgba(0,0,0,0.3);
  backdrop-filter: blur(4rpx);
  z-index: 1001;
  display: flex;
  align-items: flex-end;
}

.warehouse-popup {
  background-color: #f0f2f5;
  height: 68vh;
  border-radius: 14rpx 14rpx 0 0;
  width: 100%;
  display: flex;
  flex-direction: column;
}

/* ========== 仓库 Tabs ========== */
.wh-tabs-body {
  flex: 1;
  min-height: 0;
  overflow: hidden !important;
  max-height: none !important;
  display: flex;
  flex-direction: column;
}

.wh-tabs-bar {
  height: 80rpx;
  background-color: #ffffff;
  border-radius: 8rpx 8rpx 0 0;
  white-space: nowrap;
  display: flex;
}

.wh-tab {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  padding: 0 24rpx;
  height: 80rpx;
  position: relative;
  flex-shrink: 0;
}

.wh-tab.active::after {
  content: '';
  position: absolute;
  bottom: 0;
  left: 50%;
  transform: translateX(-50%);
  width: 40rpx;
  height: 4rpx;
  background-color: #409eff;
  border-radius: 2rpx;
}

.wh-tab-text {
  font-size: 26rpx;
  color: #606266;
}

.wh-tab.active .wh-tab-text {
  color: #409eff;
  font-weight: 600;
}

/* ========== 仓库货位搜索栏 ========== */
.wh-search-bar {
  display: flex;
  align-items: center;
  background: #ffffff;
  border-bottom: 2rpx solid #e4e7ed;
  padding: 8rpx 16rpx;
  position: relative;
}

.wh-search-input {
  flex: 1;
  background: #f0f2f5;
  border: none;
  border-radius: 8rpx;
  height: 56rpx;
  padding: 0 100rpx 0 16rpx;
  font-size: 26rpx;
  color: #303133;
  box-sizing: border-box;
  -webkit-appearance: none;
  appearance: none;
}

.wh-search-input::placeholder {
  color: #c0c4cc;
}

.wh-search-clear {
  position: absolute;
  right: 72rpx;
  top: 50%;
  transform: translateY(-50%);
  width: 36rpx;
  height: 36rpx;
  border-radius: 50%;
  background: #c0c4cc;
  color: #ffffff;
  font-size: 20rpx;
  display: flex;
  align-items: center;
  justify-content: center;
}

.wh-scan-btn {
  position: absolute;
  right: 24rpx;
  top: 50%;
  transform: translateY(-50%);
  width: 40rpx;
  height: 40rpx;
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 30rpx;
  color: #606266;
}

/* ========== 仓库货位列表 ========== */
.wh-location-list {
  flex: 1;
  height: 0;
  min-height: 0;
  overflow-y: auto;
  padding: 10rpx 16rpx;
}

.wh-loc-item {
  display: flex;
  justify-content: space-between;
  align-items: center;
  padding: 20rpx 16rpx;
  background-color: #ffffff;
  border-radius: 8rpx;
  margin-bottom: 8rpx;
}

.wh-loc-item.active {
  background-color: #ecf5ff;
  border: 2rpx solid #409eff;
}

.wh-loc-code {
  font-size: 26rpx;
  color: #303133;
}

.wh-loc-check {
  font-size: 28rpx;
  color: #409eff;
  font-weight: 600;
}

/* ========== Popup 提示 ========== */
.popup-hint {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 10rpx;
  padding: 30rpx 0;
  font-size: 26rpx;
  color: #909399;
}

.popup-hint-end {
  text-align: center;
  padding: 20rpx 0;
  font-size: 24rpx;
  color: #c0c4cc;
}

.popup-loading {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 10rpx;
  padding: 20rpx 0;
  font-size: 26rpx;
  color: #909399;
}

.mini-spinner {
  width: 28rpx;
  height: 28rpx;
  border: 3rpx solid #e4e7ed;
  border-top-color: #409eff;
  border-radius: 50%;
  animation: spin 0.8s linear infinite;
}

/* ========== Popup Footer Btn ========== */
.popup-footer-btn {
  flex: 1;
  height: 76rpx;
  border-radius: 10rpx;
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 28rpx;
}

.popup-footer-btn.cancel {
  background-color: #ffffff;
  border: 2rpx solid #dcdfe6;
  color: #606266;
}

.popup-footer-btn.confirm {
  background-color: #409eff;
  color: #ffffff;
}

.popup-footer-btn.confirm.disabled {
  background-color: #a0cfff;
  color: #ffffff;
  opacity: 0.6;
}

/* ========== 扫码结果弹窗 ========== */
.scan-result-overlay {
  position: fixed;
  top: 0; left: 0; right: 0; bottom: 0;
  background-color: rgba(0,0,0,0.3);
  z-index: 2000;
  display: flex;
  align-items: center;
  justify-content: center;
}

.scan-result-popup {
  width: 560rpx;
  background-color: #ffffff;
  border-radius: 12rpx;
  overflow: hidden;
}

.popup-scan-header {
  padding: 30rpx;
  display: flex;
  justify-content: space-between;
  align-items: center;
  border-bottom: 1rpx solid #f0f0f0;
}

.popup-scan-title {
  font-size: 32rpx;
  font-weight: bold;
  color: #333333;
}

.popup-scan-close {
  font-size: 36rpx;
  color: #999999;
  padding: 0 10rpx;
}

.popup-scan-content {
  padding: 30rpx;
  min-height: 120rpx;
}

.scan-result-row {
  display: flex;
  align-items: center;
  margin-bottom: 16rpx;
}

.scan-result-label {
  font-size: 28rpx;
  color: #666666;
  margin-right: 20rpx;
  min-width: 120rpx;
}

.scan-result-value {
  font-size: 30rpx;
  color: #333333;
  font-weight: 500;
}

.scan-result-hint {
  font-size: 26rpx;
  color: #999999;
  margin-top: 10rpx;
  display: block;
}

.popup-scan-footer {
  display: flex;
  border-top: 1rpx solid #f0f0f0;
}

.popup-scan-btn {
  flex: 1;
  height: 90rpx;
  line-height: 90rpx;
  text-align: center;
  font-size: 32rpx;
}

.popup-scan-cancel {
  background-color: #f5f5f5;
  color: #333333;
}

.popup-scan-confirm {
  background-color: #007aff;
  color: #ffffff;
}

/* ========== 定价策略 ========== */
.mode-tabs {
  display: flex;
  background: #f0f2f5;
  border-radius: 8rpx;
  padding: 4rpx;
  margin-bottom: 24rpx;
}

.mode-tab {
  flex: 1;
  text-align: center;
  padding: 16rpx 0;
  border-radius: 6rpx;
  font-size: 26rpx;
  color: #606266;
  transition: all 0.2s;
}

.mode-tab.active {
  background: #ffffff;
  color: #409eff;
  font-weight: 600;
  box-shadow: 0 1rpx 4rpx rgba(0,0,0,0.06);
}

.mode-tab-text {
  font-size: 26rpx;
}

.config-field {
  margin-bottom: 24rpx;
  padding-bottom: 20rpx;
  border-bottom: 2rpx solid #f0f2f5;
}

.config-field:last-of-type {
  border-bottom: none;
  margin-bottom: 16rpx;
}

.config-label {
  display: block;
  font-size: 26rpx;
  color: #303133;
  font-weight: 500;
  margin-bottom: 4rpx;
}

.config-desc {
  display: block;
  font-size: 22rpx;
  color: #909399;
  margin-bottom: 12rpx;
}

.picker-wrap {
  display: flex;
}

.picker-btn {
  display: flex;
  align-items: center;
  justify-content: space-between;
  background: #ffffff;
  border: 2rpx solid #dcdfe6;
  border-radius: 8rpx;
  padding: 0 16rpx;
  height: 72rpx;
  min-width: 200rpx;
  box-sizing: border-box;
}

.picker-btn:active {
  border-color: #409eff;
}

.picker-btn-text {
  font-size: 28rpx;
  color: #303133;
}

.num-input-field {
  background: #ffffff;
  border: 2rpx solid #dcdfe6;
  border-radius: 8rpx;
  padding: 0 16rpx;
  height: 72rpx;
  line-height: 72rpx;
  font-size: 28rpx;
  color: #303133;
  width: 100%;
  box-sizing: border-box;
  -webkit-appearance: none;
  appearance: none;
}

.num-input-field:focus {
  border-color: #409eff;
  outline: none;
}

.num-input-field::placeholder {
  color: #c0c4cc;
}

.save-config-btn {
  background: #409eff;
  color: #ffffff;
  text-align: center;
  padding: 22rpx 0;
  border-radius: 10rpx;
  font-size: 28rpx;
  font-weight: 500;
  margin-top: 12rpx;
  box-shadow: 0 2rpx 8rpx rgba(64,158,255,0.2);
}

.save-config-btn:active {
  opacity: 0.85;
}

/* ========== 设置子Tabs ========== */
.settings-sub-tabs {
  display: flex;
  background-color: #ffffff;
  border-bottom: 2rpx solid #e4e7ed;
}

.settings-sub-tab {
  flex: 1;
  text-align: center;
  padding: 20rpx 0;
  font-size: 26rpx;
  color: #606266;
  position: relative;
}

.settings-sub-tab.active {
  color: #409eff;
  font-weight: 600;
}

.settings-sub-tab.active::after {
  content: '';
  position: absolute;
  bottom: 0;
  left: 50%;
  transform: translateX(-50%);
  width: 48rpx;
  height: 4rpx;
  background-color: #409eff;
  border-radius: 2rpx;
}

/* ========== 设置 - 已登录卡片 ========== */
.logged-in-card {
  background-color: #fafafa;
  border: 2rpx solid #ebeef5;
  border-radius: 12rpx;
  overflow: hidden;
}

.card-header {
  display: flex;
  align-items: center;
  padding: 20rpx;
  gap: 14rpx;
}

.card-avatar {
  width: 72rpx;
  height: 72rpx;
  border-radius: 50%;
  background-color: #409eff;
  flex-shrink: 0;
}

.card-user-info {
  flex: 1;
}

.card-shop-name {
  font-size: 28rpx;
  color: #303133;
  font-weight: 600;
  display: block;
}

.card-region-row {
  display: flex;
  align-items: center;
  gap: 4rpx;
  margin-top: 6rpx;
}

.card-region-icon {
  font-size: 24rpx;
}

.card-region {
  font-size: 24rpx;
  color: #909399;
}

.card-footer {
  border-top: 2rpx solid #ebeef5;
  padding: 16rpx 20rpx;
  display: flex;
  justify-content: flex-end;
}

.logout-btn-text {
  font-size: 26rpx;
  color: #f56c6c;
}

/* ========== 登录样式 ========== */
.login-header {
  text-align: center;
  padding: 20rpx 0;
}

.login-title {
  font-size: 32rpx;
  color: #303133;
  font-weight: 600;
}

.login-form {
  padding-top: 10rpx;
}

.input-row {
  margin-bottom: 16rpx;
}

/* ========== 密码框 ========== */
.password-wrapper {
  position: relative;
  width: 100%;
  display: flex;
  align-items: center;
}

.password-input {
  flex: 1;
  padding-right: 90rpx !important;
  -webkit-appearance: none;
  appearance: none;
}

/* H5浏览器密码框默认眼睛图标隐藏 */
.password-input::-webkit-credentials-auto-fill-button,
.password-input::-webkit-reveal,
.password-input::-ms-reveal {
  display: none !important;
  -webkit-appearance: none;
  appearance: none;
}

/* H5密码框自动填充背景色覆盖 */
.password-input:-webkit-autofill {
  -webkit-box-shadow: 0 0 0 1000rpx #ffffff inset !important;
  -webkit-text-fill-color: #303133 !important;
}

.password-eye {
  position: absolute;
  right: 8rpx;
  top: 50%;
  transform: translateY(-50%);
  width: 64rpx;
  height: 64rpx;
  display: flex;
  align-items: center;
  justify-content: center;
  z-index: 10;
}

/* ========== 眼睛图标 CSS 实现 ========== */
.eye-css {
  width: 40rpx;
  height: 40rpx;
  display: flex;
  align-items: center;
  justify-content: center;
  position: relative;
}

.eye-open {
  width: 36rpx;
  height: 36rpx;
  border: 3rpx solid #909399;
  border-radius: 50%;
  display: flex;
  align-items: center;
  justify-content: center;
  position: relative;
}

.eye-open.eye-active {
  border-color: #409eff;
}

.eye-open-inner {
  width: 14rpx;
  height: 14rpx;
  border: 2rpx solid #909399;
  border-radius: 50%;
  display: flex;
  align-items: center;
  justify-content: center;
}

.eye-open.eye-active .eye-open-inner {
  border-color: #409eff;
}

.pupil {
  width: 6rpx;
  height: 6rpx;
  background-color: #909399;
  border-radius: 50%;
}

.eye-open.eye-active .pupil {
  background-color: #409eff;
}

.eye-close {
  width: 36rpx;
  height: 10rpx;
  border-top: 3rpx solid #909399;
  border-bottom: 3rpx solid #909399;
  position: relative;
  transform: rotate(0deg);
}

.eye-close-line {
  position: absolute;
  top: 50%;
  left: 50%;
  width: 40rpx;
  height: 3rpx;
  background-color: #909399;
  transform: translate(-50%, -50%) rotate(45deg);
}

.checkbox-row {
  display: flex;
  align-items: center;
  gap: 6rpx;
  margin-bottom: 20rpx;
}

.checkbox-label {
  font-size: 24rpx;
  color: #909399;
}

/* --- 已保存账号列表 --- */
.saved-accounts {
  margin-top: 28rpx;
  padding-top: 24rpx;
  border-top: 2rpx solid #ebeef5;
}

.saved-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  margin-bottom: 16rpx;
}

.saved-title {
  font-size: 26rpx;
  color: #303133;
  font-weight: 600;
}

.saved-count {
  font-size: 22rpx;
  color: #909399;
}

.saved-list {
  display: flex;
  flex-direction: column;
  gap: 12rpx;
}

.saved-item {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 16rpx 18rpx;
  background: #f7f8fa;
  border: 2rpx solid #ebeef5;
  border-radius: 10rpx;
}

.saved-item:active {
  background: #ecf5ff;
  border-color: #409eff;
}

.saved-item-left {
  display: flex;
  align-items: center;
  gap: 14rpx;
  flex: 1;
  min-width: 0;
}

.saved-avatar {
  width: 48rpx;
  height: 48rpx;
  border-radius: 50%;
  background: #ecf5ff;
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 24rpx;
  flex-shrink: 0;
}

.saved-info {
  display: flex;
  flex-direction: column;
  gap: 4rpx;
  min-width: 0;
  flex: 1;
}

.saved-name {
  font-size: 26rpx;
  color: #303133;
  font-weight: 500;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.saved-hint {
  font-size: 22rpx;
  color: #909399;
}

.saved-del {
  font-size: 24rpx;
  color: #f56c6c;
  padding: 6rpx 10rpx;
  flex-shrink: 0;
}

.saved-del:active {
  opacity: 0.7;
}

.login-btn {
  background-color: #409eff;
  border-radius: 10rpx;
  box-shadow: 0 4rpx 12rpx rgba(64,158,255,0.2);
  height: 80rpx;
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 30rpx;
  color: #ffffff;
  font-weight: 600;
}

/* ========== 屏蔽设置 ========== */
.section-desc {
  font-size: 24rpx;
  color: #909399;
  display: block;
  margin-bottom: 14rpx;
}

.blocked-textarea {
  width: 100%;
  min-height: 200rpx;
  background-color: #ffffff;
  border: 2rpx solid #dcdfe6;
  border-radius: 8rpx;
  padding: 16rpx;
  font-size: 26rpx;
  color: #303133;
  box-sizing: border-box;
}

.blocked-textarea:focus {
  border-color: #409eff;
}

/* 无ISBN已有图书弹窗 */
.noisbn-book-mask {
  position: fixed;
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
  background: rgba(0,0,0,0.45);
  z-index: 1000;
  display: flex;
  justify-content: center;
  align-items: center;
}
.noisbn-book-popup {
  background: #fff;
  border-radius: 20rpx;
  width: 85%;
  max-width: 650rpx;
  max-height: 75vh;
  display: flex;
  flex-direction: column;
  overflow: hidden;
}
.noisbn-book-header {
  padding: 30rpx;
  display: flex;
  justify-content: space-between;
  align-items: center;
  border-bottom: 1rpx solid #f0f0f0;
}
.noisbn-book-title {
  font-size: 32rpx;
  font-weight: bold;
  color: #333;
}
.noisbn-book-close {
  font-size: 36rpx;
  color: #999;
  padding: 8rpx;
}
.noisbn-book-scroll {
  max-height: 60vh;
  height: 600rpx;
  padding: 0 20rpx;
}
.noisbn-book-item {
  display: flex;
  align-items: center;
  padding: 24rpx 16rpx;
  border-bottom: 1rpx solid #f5f5f5;
  cursor: pointer;
}
.noisbn-book-item:active {
  background: #f5f7fa;
}
.noisbn-book-item-num {
  width: 48rpx;
  height: 48rpx;
  border-radius: 50%;
  background: #409eff;
  color: #fff;
  font-size: 22rpx;
  text-align: center;
  line-height: 48rpx;
  margin-right: 20rpx;
  flex-shrink: 0;
}
.noisbn-book-item-body {
  flex: 1;
  min-width: 0;
}
.noisbn-book-item-name {
  font-size: 28rpx;
  color: #303133;
  font-weight: 500;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.noisbn-book-item-meta {
  display: flex;
  flex-wrap: wrap;
  gap: 8rpx;
  margin-top: 8rpx;
}
.meta-tag {
  font-size: 22rpx;
  color: #909399;
  background: #f5f7fa;
  padding: 2rpx 12rpx;
  border-radius: 6rpx;
  white-space: nowrap;
}
.noisbn-book-item-arrow {
  color: #c0c4cc;
  font-size: 32rpx;
  margin-left: 12rpx;
  flex-shrink: 0;
}
.noisbn-book-footer {
  padding: 20rpx 30rpx 30rpx;
  display: flex;
  justify-content: center;
}
.noisbn-book-btn {
  padding: 18rpx 60rpx;
  border-radius: 40rpx;
  font-size: 28rpx;
  text-align: center;
  cursor: pointer;
}
.noisbn-book-cancel {
  background: #f5f7fa;
  color: #606266;
}
</style>
