<template>
  <view :class="theme_view" class="ticket-wallet-page">
    <!-- 顶部返回 + 标题导航 -->
    <!-- <view class="top-nav-bar">
      <view class="nav-back" @click="goBack">
        <text class="back-arrow">‹</text>
      </view>
      <view class="nav-title">
        <text class="title-text">我的票夹</text>
        <text class="ticket-count" v-if="totalActiveCount > 0">{{ totalActiveCount }}张待使用</text>
      </view>
      <view class="nav-placeholder"></view>
    </view> -->

    <!-- 主内容区域 -->
    <scroll-view
      class="wallet-scroll"
      scroll-y
      :refresher-enabled="true"
      :refresher-triggered="isRefreshing"
      @refresherrefresh="onPullDownRefresh"
    >
      <!-- 顶部潮流 Banner -->
      <view class="brand-banner">
        <!-- 氛围模糊渐变光晕 -->
        <view class="ambiance-light-1"></view>
        <view class="ambiance-light-2"></view>

        <!-- 等高线矢量线条背景 -->
        <svg class="contour-bg" viewBox="0 0 400 300" fill="none" stroke="currentColor">
          <path d="M-50,60 C80,30 180,120 450,40" stroke-width="1" stroke-dasharray="3 3" />
          <path d="M-50,110 C90,70 190,170 450,90" stroke-width="1" />
          <path d="M-50,160 C100,120 200,210 450,140" stroke-width="0.8" />
          <path d="M-50,210 C110,170 210,250 450,190" stroke-width="1.2" />
          <path d="M-50,260 C120,220 220,290 450,240" stroke-width="0.8" stroke-dasharray="4 2" />
        </svg>

        <!-- 旋转黑胶唱片左侧（背景大黑胶） -->
        <view class="record-disc-large">
          <view class="record-body">
            <view class="record-circle-1"></view>
            <view class="record-circle-2"></view>
            <view class="record-center">
              <view class="record-dot"></view>
            </view>
          </view>
        </view>

        <!-- 旋转黑胶唱片右侧（背景小黑胶） -->
        <view class="record-disc-small">
          <view class="record-body">
            <view class="record-circle-1"></view>
            <view class="record-circle-2"></view>
            <view class="record-center">
              <view class="record-dot"></view>
            </view>
          </view>
        </view>

        <!-- 涂鸦笑脸 -->
        <view class="graffiti-face">
          <svg class="graffiti-svg" viewBox="0 0 40 40" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round">
            <circle cx="20" cy="20" r="16" />
            <path d="M14,16 L14.01,16 M26,16 L26.01,16" stroke-width="3.5" />
            <path d="M13,22 Q20,29 27,22" />
          </svg>
        </view>

        <!-- Live Music 竖排小文字 -->
        <view class="live-music-tag">
          <text>l</text><text>i</text><text>v</text><text>e</text>
          <text class="live-music-dot">•</text>
          <text>m</text><text>u</text><text>s</text><text>i</text><text>c</text>
          <text class="live-music-dot">•</text>
          <text>i</text><text>n</text>
        </view>
        <view class="live-music-subtag">
          <text>v</text><text>r</text><text>t</text><text>i</text><text>c</text><text>k</text><text>e</text><text>t</text>
        </view>

        <!-- 品牌旋转星标 Hub -->
        <view class="brand-star-hub">
          <!-- 品牌旋转星标文字环 (使用 xlink:href 兼容小程序) -->
          <svg class="rotating-text-svg svg-compat" viewBox="0 0 120 120">
            <path id="vrTicketPath" d="M 60 16 A 44 44 0 1 1 59.9 16" fill="none" />
            <text fill="black" style="font-size: 7.2px; font-weight: 900; letter-spacing: 0.26em;">
              <textPath xlink:href="#vrTicketPath" startOffset="0%">
                VRTICKET • VRTICKET • VRTICKET • VRTICKET •
              </textPath>
            </text>
          </svg>

          <!-- 四角星中心 -->
          <svg class="star-core-svg" viewBox="0 0 100 100" fill="none">
            <path d="M 50 2 C 50 38 38 50 2 50 C 38 50 50 62 50 98 C 50 62 62 50 98 50 C 62 50 50 38 50 2 Z" fill="black" />
          </svg>

          <!-- 斜横幅标 -->
          <view class="brand-label-plate">
            VRTicket
          </view>
        </view>
      </view>

      <!-- 票券主面板容器 -->
      <view class="ticket-panel-container">
        <!-- 待使用演出列表 -->
        <view class="section-header-row" v-if="activeGroups.length > 0">
          <text class="section-main-title">待核销票据</text>
          <view class="section-count-badge">
            <text>共</text>
            <text class="section-count-number">{{ totalActiveCount }}</text>
            <text>张票</text>
          </view>
        </view>

        <view class="section-block" v-if="activeGroups.length > 0">
          <view
            class="ticket-group-card"
            v-for="(group, gIdx) in activeGroups"
            :key="'active-' + gIdx"
            @click="openQrPopup(group)"
          >
            <!-- 左右侧切打孔 notch -->
            <view class="ticket-punch-hole-left"></view>
            <view class="ticket-punch-hole-right"></view>

            <!-- 卡券主要内容区 -->
            <view class="card-inner-box">
              <!-- 影院/场馆行 + 动作按钮 -->
              <view class="card-header-row">
                <view class="cinema-title-wrap">
                  <iconfont name="icon-store" size="32rpx" color="#000000" propClass="lh-il va-m"></iconfont>
                  <text class="cinema-title-text">{{ group.venue_name || '测试场馆' }}</text>
                </view>
                
                <!-- 快捷联系 actions -->
                <view class="action-buttons">
                  <!-- 电话呼叫 -->
                  <view class="action-circle-btn" @click.stop="callService(group.venue_name)">
                    <iconfont name="icon-phone" size="28rpx" color="#444444" propClass="lh-il va-m"></iconfont>
                  </view>
                  <!-- 地图导航 -->
                  <view class="action-circle-btn" @click.stop="openNavigation(group.venue_name)">
                    <iconfont name="icon-map-location" size="28rpx" color="#444444" propClass="lh-il va-m"></iconfont>
                  </view>
                </view>
              </view>

              <!-- 详细内容主体 (左栏文本 + 右栏电影海报小卡) -->
              <view class="card-content-body">
                <!-- 左边栏：名称、时间、座位 -->
                <view class="card-left-info">
                  <text class="movie-title-text">{{ group.goods_title }}</text>
                  <!-- <text class="movie-format-tag">{{ group.tickets[0] && group.tickets[0].goods_type === 1 ? '国语 3D' : '国语 2D' }}</text> -->

                  <!-- 时间点（Montserrat 重磅粗体） -->
                  <view class="session-time-text">{{ formatSessionTime(group.session_time) }}</view>

                  <!-- 座位信息块 -->
                  <view class="seat-badge-block">
                    <!-- 场馆厅信息 -->
                    <view class="seat-hall-text" v-if="group.tickets[0] && getHallFromSeatInfo(group.tickets[0].seat_info)">
                      <iconfont name="icon-map-position" size="24rpx" color="#e1251b" propClass="lh-il va-m mr-xs"></iconfont> {{ getHallFromSeatInfo(group.tickets[0].seat_info) }}
                    </view>
                    <!-- 座位号列表 -->
                    <view class="seat-detail-wrap">
                      <view class="seat-numbers-list">
                        <text v-for="(t, tIdx) in group.tickets" :key="t.id" class="seat-item">
                          {{ t.seat_number }}
                        </text>
                      </view>
                    </view>
                  </view>
                </view>

                <!-- 右边栏：高颜值海报小卡 -->
                <view class="card-right-poster">
                  <!-- 红光氛围灯效 overlay -->
                  <view class="poster-spotlight"></view>
                  <image
                    class="poster-image-item"
                    :src="resolveImageUrl(group.goods_image) || defaultPoster"
                    mode="aspectFill"
                  />
                  <!-- 海报底部的水印文字 -->
                  <view class="poster-text-overlay" v-if="!group.goods_image">
                    <text class="poster-abbr-title">{{ getShortTitle(group.goods_title) }}</text>
                    <text class="poster-en-title">{{ getEnTitle(group.goods_title) }}</text>
                  </view>
                  <!-- <view class="poster-format-badge">EVE</view> -->
                </view>
              </view>

              <!-- 底部查看票码分割栏 -->
              <view class="ticket-card-footer">
                <text class="footer-tip-text">使用时请点击展示二维码/条形码</text>
                <text class="view-code-text">查看票码 ›</text>
              </view>
            </view>
          </view>
        </view>

        <!-- 空状态：没有待使用票据 -->
        <view class="empty-section" v-else-if="!isLoading && loadStatus === 3">
          <image class="empty-icon" src="/static/images/common/no-data.png" mode="aspectFit" />
          <text class="empty-text">暂无待使用的电子票</text>
          <view class="empty-tip">
            <text>购买演出票后，在这里查看</text>
          </view>
        </view>

        <!-- 加载中骨架 -->
        <view class="loading-section" v-if="isLoading">
          <view class="skeleton-card" v-for="i in 2" :key="i">
            <view class="skeleton-header">
              <view class="skeleton-thumb"></view>
              <view class="skeleton-meta">
                <view class="skeleton-line short"></view>
                <view class="skeleton-line"></view>
                <view class="skeleton-line"></view>
              </view>
            </view>
            <view class="skeleton-divider"></view>
            <view class="skeleton-footer"></view>
          </view>
        </view>

        <!-- 历史票根 -->
        <view v-if="historyGroups.length > 0">
          <view class="history-section-title-wrap">
            <text class="history-section-title">历史票根 ({{ historyGroups.length }})</text>
          </view>
          <view
            class="ticket-group-card history-card"
            v-for="(group, gIdx) in historyGroups"
            :key="'history-' + gIdx"
          >
            <!-- 左右侧切打孔 notch -->
            <!-- 左右侧切打孔 notch -->
            <view class="ticket-punch-hole-left"></view>
            <view class="ticket-punch-hole-right"></view>

            <!-- 核销水印盖章 -->
            <view class="stamp-container">
              <view class="verified-stamp" :class="{ 'refunded': group.tickets[0] && group.tickets[0].verify_status !== 1 }">
                {{ group.tickets[0] && group.tickets[0].verify_status === 1 ? '已核销 PASSED' : '已退款 REFUND' }}
              </view>
            </view>

            <!-- 卡券内容区 -->
            <view class="card-inner-box">
              <!-- 影院/场馆行 -->
              <view class="card-header-row">
                <view class="cinema-title-wrap">
                  <iconfont name="icon-store" size="32rpx" color="#888888" propClass="lh-il va-m"></iconfont>
                  <text class="cinema-title-text">{{ group.venue_name || '测试场馆' }}</text>
                </view>
              </view>

              <!-- 详细内容主体 -->
              <view class="card-content-body">
                <view class="card-left-info">
                  <text class="movie-title-text">{{ group.goods_title }}</text>
                  <!-- <text class="movie-format-tag">{{ group.tickets[0] && group.tickets[0].goods_type === 1 ? '国语 3D' : '国语 2D' }}</text> -->

                  <view class="session-time-text">{{ formatSessionTime(group.session_time) }}</view>

                  <!-- 座位信息块 -->
                  <view class="seat-badge-block">
                    <!-- 场馆厅信息 -->
                    <view class="seat-hall-text" v-if="group.tickets[0] && getHallFromSeatInfo(group.tickets[0].seat_info)">
                      <iconfont name="icon-map-position" size="24rpx" color="#888888" propClass="lh-il va-m mr-xs"></iconfont> {{ getHallFromSeatInfo(group.tickets[0].seat_info) }}
                    </view>
                    <!-- 座位号列表 -->
                    <view class="seat-detail-wrap">
                      <view class="seat-numbers-list">
                        <text v-for="(t, tIdx) in group.tickets" :key="t.id" class="seat-item">
                          {{ t.seat_number }}
                        </text>
                      </view>
                    </view>
                  </view>
                </view>

                <!-- 海报小卡 -->
                <view class="card-right-poster">
                  <image
                    class="poster-image-item"
                    :src="resolveImageUrl(group.goods_image) || defaultPoster"
                    mode="aspectFill"
                  />
                </view>
              </view>
            </view>
          </view>
        </view>
      </view>

      <!-- 底部安全区占位 -->
      <view class="safe-area-bottom"></view>
    </scroll-view>

    <!-- QR 弹窗 -->
    <u-popup
      ref="qrPopupRef"
      propType="center"
      :propIsMaskClick="true"
      :propRound="24"
      :propBackgroundColor="qrPopupBg"
      @change="onPopupChange"
      @close="onPopupClose"
    >
      <ticket-qr-popup
        :tickets="currentQrTickets"
        :current-index="currentQrIndex"
        :show-info="currentShowInfo"
        @change="onQrSlideChange"
        @refresh="onQrRefresh"
      />
    </u-popup>

    <!-- 提示弹窗 (Mock 效果) -->
    <view v-if="showInfoModal" class="info-modal-mask" @click="showInfoModal = false">
      <view class="info-modal-content" @click.stop>
        <view class="info-modal-icon">ℹ️</view>
        <view class="info-modal-title">系统模拟提示</view>
        <scroll-view scroll-y class="info-modal-scroll">
          <text class="info-modal-text">{{ infoModalText }}</text>
        </scroll-view>
        <button class="info-modal-btn" @click="showInfoModal = false">关闭</button>
      </view>
    </view>

    <!-- 快捷导航 -->
    <component-quick-nav :propIsNav="true" :propIsBar="true" :propIsGrayscale="plugins_mourning_data_is_app"></component-quick-nav>

    <!-- 公共 -->
    <component-common ref="common" :propIsGrayscale="plugins_mourning_data_is_app"></component-common>
  </view>
</template>

<script>
import uPopup from '@/components/u-popup/u-popup.vue';
import TicketQrPopup from './components/ticket-qr-popup/index.vue';
import componentCommon from '@/components/common/common';
import componentQuickNav from '@/components/quick-nav/quick-nav';

const app = getApp();

export default {
  name: 'TicketWallet',
  components: {
    uPopup,
    TicketQrPopup,
    componentCommon,
    componentQuickNav,
  },
  data() {
    return {
      // 主题样式
      theme_view: '',
      // 哀悼灰度插件
      plugins_mourning_data_is_app: app.globalData.is_app_mourning(),
      // 加载状态 1=加载中 2=加载失败 3=加载成功
      loadStatus: 1,
      isRefreshing: false,
      // 原始票据列表（API 返回扁平数组）
      rawTickets: [],
      // 默认海报兜底图
      defaultPoster: '/static/images/common/empty.png',
      // QR 弹窗控制（使用 ref.open()/close() 模式）
      qrPopupBg: '#ffffff',
      // 当前弹窗内展示的票（带 qr_payload）
      currentQrTickets: [],
      currentQrIndex: 0,
      currentShowInfo: {},
      // 内部定时器
      refreshTimer: null,
      // 屏幕亮度
      screenBrightnessValue: 0.5,
      // 当前展示票的剩余秒数
      currentExpiresIn: 0,
      // 快捷互动遮罩
      showInfoModal: false,
      infoModalText: '',
    };
  },
  computed: {
    isLoading() {
      return this.loadStatus === 1;
    },
    // 按演出 + 场次分组（verify_status == 0）
    activeGroups() {
      const active = this.rawTickets.filter(t => t.verify_status === 0);
      return this.groupByShow(active);
    },
    // 历史票根分组（verify_status == 1 已核销 或 2 已退款）
    historyGroups() {
      const history = this.rawTickets.filter(t => t.verify_status === 1 || t.verify_status === 2);
      return this.groupByShow(history);
    },
    // 待使用票据总张数
    totalActiveCount() {
      return this.activeGroups.reduce((sum, g) => sum + g.tickets.length, 0);
    },
  },
  onLoad(params) {
    // 调用公共事件方法
    app.globalData.page_event_onload_handle(params);

    // 记录来源页面
    if (params && params.from) {
      this.sourceFrom = params.from;
    }
    // 获取初始屏幕亮度
    // #ifndef H5
    uni.getScreenBrightness({
      success: (res) => {
        this.screenBrightnessValue = res.value;
      },
    });
    // #endif
  },
  onShow() {
    // 调用公共事件方法
    app.globalData.page_event_onshow_handle();


    // 加载票据列表
    this.init();

    // 初始化配置
    if (app.globalData.get_config('status') == 1) {
      app.globalData.init_config(0, this, 'init_config', true);
    } else {
      app.globalData.is_config(this, 'init_config');
    }

    // 公共onshow事件
    if ((this.$refs.common || null) != null) {
      this.$refs.common.on_show({object: this, method: 'init'});
    }
  },
  onUnload() {
    this.clearRefreshTimer();
    this.restoreScreenBrightness();
  },
  methods: {
    // 初始化配置
    init_config(status) {
      if ((status || false) == true) {
        var theme_view = app.globalData.get_theme_value_view();
        var mourning = parseInt(app.globalData.get_config('plugins_mourning_data') || 0) == 1;
        this.setData({
          theme_view: theme_view,
          plugins_mourning_data_is_app: mourning,
        });
      }
    },

    // 返回上一页
    goBack() {
      const pages = getCurrentPages();
      if (pages.length > 1) {
        uni.navigateBack();
      } else {
        uni.reLaunch({ url: '/pages/index/index' });
      }
    },

    // 格式化日期与时间
    formatSessionDate(timeStr) {
      if (!timeStr) return '';
      const parts = timeStr.split(' ');
      return parts[0] || '';
    },
    formatSessionTime(timeStr) {
      if (!timeStr) return '';
      // session_time is already in "08:00-23:59" format
      return timeStr;
    },
    getShortTitle(title) {
      if (!title) return '潮流演艺';
      return title.slice(0, 4);
    },
    // 从 seat_info 中提取场馆厅信息
    // seat_info 格式: "08:00-23:59|测试场馆|老展厅 1|A|2排1座"
    getHallFromSeatInfo(seatInfo) {
      if (!seatInfo) return '';
      const parts = seatInfo.split('|');
      // parts[2] 是厅信息，如 "老展厅 1"
      return parts[2] || '';
    },
    getEnTitle(title) {
      if (!title) return 'LIVE MUSIC SHOW';
      return 'CREATIVE EXPERIENCE';
    },
    // 将相对路径拼接为完整静态资源 URL（兼容非 H5 环境）
    resolveImageUrl(path) {
      if (!path) return '';
      // 已经是完整 URL 则直接返回
      if (path.indexOf('http') === 0) return path;
      // 相对路径补上 static_url
      var base = (app.globalData.data.static_url || '').replace(/\/+$/, '');
      return base + '/' + path.replace(/^\/+/, '');
    },
    callService(venueName) {
      this.infoModalText = `正在虚拟呼叫 「${venueName}」 客服热线：\n\n📞 400-880-9911\n\n[提示]：由于在安全沙箱中运行，呼叫将在本地虚拟完成，为您解答关于演出的任何问题。`;
      this.showInfoModal = true;
    },
    openNavigation(venueName) {
      this.infoModalText = `📌 正在智能检索并规划前往「${venueName}」的最佳通行路线：\n\n- 驾车：预计 12 分钟 (3.5公里)\n- 步行：预计 25 分钟 (1.8公里)\n- 地铁：2号线直达\n\n路线规划成功，已无线映射至您的智能HUD导航！`;
      this.showInfoModal = true;
    },

    // 初始化加载
    init() {
      var self = this;
      var user = app.globalData.get_user_info(this, 'init');
      if (user == false) {
        this.loadStatus = 2;
        return;
      }
      this.loadStatus = 1;
      uni.request({
        url: app.globalData.get_request_url('list', 'ticket', 'vr_ticket'),
        method: 'GET',
        dataType: 'json',
        success: function(res) {
          if (res.data.code == 0) {
            var tickets = res.data.data.tickets || [];
            self.rawTickets = tickets;
            self.loadStatus = 3;
          } else {
            self.loadStatus = 2;
            if (app.globalData.is_login_check(res.data, self, 'init')) {
              app.globalData.showToast(res.data.msg);
            }
          }
        },
        fail: function() {
          self.loadStatus = 2;
          app.globalData.showToast(self.$t('common.internet_error_tips'));
        },
      });
    },

    // 按演出 + 场馆 + 下单时间（issued_at）进行分组组织
    groupByShow(tickets) {
      var map = {};
      tickets.forEach(function(t) {
        var key = t.goods_id + '|' + (t.venue_name || '') + '|' + (t.issued_at || '');
        if (!map[key]) {
          map[key] = {
            goods_id: t.goods_id,
            goods_title: t.goods_title,
            goods_image: t.goods_image,
            session_time: t.session_time,
            venue_name: t.venue_name,
            issued_at: t.issued_at,
            tickets: [],
          };
        }
        map[key].tickets.push(t);
      });
      // 按下单时间或场次时间倒序（最近的在前）
      return Object.values(map).sort(function(a, b) {
        if (a.issued_at && b.issued_at) {
          return b.issued_at - a.issued_at;
        }
        return (b.session_time || '').localeCompare(a.session_time || '');
      });
    },

    // 下拉刷新
    onPullDownRefresh() {
      this.isRefreshing = true;
      var self = this;
      uni.request({
        url: app.globalData.get_request_url('list', 'ticket', 'vr_ticket'),
        method: 'GET',
        dataType: 'json',
        success: function(res) {
          uni.stopPullDownRefresh();
          self.isRefreshing = false;
          if (res.data.code == 0) {
            self.rawTickets = res.data.data.tickets || [];
            self.loadStatus = 3;
          } else {
            app.globalData.showToast(res.data.msg || '刷新失败');
          }
        },
        fail: function() {
          uni.stopPullDownRefresh();
          self.isRefreshing = false;
          app.globalData.showToast(self.$t('common.internet_error_tips'));
        },
      });
    },

    // 打开 QR 弹窗（点击演出卡）
    openQrPopup(group) {
      var self = this;
      var ticketIds = group.tickets.map(function(t) { return t.id; });

      uni.showLoading({ title: '加载中...' });

      // 并行请求每张票的 detail（含 qr_payload）
      var promises = ticketIds.map(function(id) {
        return self.fetchTicketDetail(id);
      });

      Promise.all(promises).then(function(results) {
        uni.hideLoading();
        // results 中可能有 undefined（请求失败的票），过滤掉
        var validTickets = results.filter(function(r) { return r != null; });
        if (validTickets.length === 0) {
          app.globalData.showToast('加载票据失败，请重试');
          return;
        }
        self.currentQrTickets = validTickets;
        self.currentQrIndex = 0;
        self.currentShowInfo = {
          title: group.goods_title,
          session_time: group.session_time,
          venue_name: group.venue_name,
        };
        // 匹配暗黑 iOS Wallet 风格的背景
        self.qrPopupBg = '#111111';
        self.boostScreenBrightness();
        self.startQrCountdown();

        // 打开弹窗（通过 ref.open() 方式）
        self.$nextTick(function() {
          if (self.$refs.qrPopupRef) {
            self.$refs.qrPopupRef.open();
          }
        });
      }).catch(function() {
        uni.hideLoading();
        app.globalData.showToast('加载票据失败，请重试');
      });
    },

    // QR 弹窗关闭回调（来自 u-popup @change show=false 或 @close）
    onPopupChange: function(e) {
      if (e && e.show === false) {
        this.clearRefreshTimer();
        this.restoreScreenBrightness();
      }
    },

    // QR 弹窗关闭事件
    onPopupClose: function() {
      this.clearRefreshTimer();
      this.restoreScreenBrightness();
    },

    // 获取单张票详情（含 qr_payload）
    fetchTicketDetail(ticketId) {
      return new Promise(function(resolve) {
        uni.request({
          url: app.globalData.get_request_url('detail', 'ticket', 'vr_ticket', 'id=' + ticketId),
          method: 'GET',
          dataType: 'json',
          success: function(res) {
            if (res.data.code == 0 && res.data.data.ticket) {
              resolve(res.data.data.ticket);
            } else {
              resolve(null);
            }
          },
          fail: function() {
            resolve(null);
          },
        });
      });
    },

    // Swiper 滑动切换
    onQrSlideChange(index) {
      this.currentQrIndex = index;
      // 重启倒计时（针对新票）
      this.startQrCountdown();
    },

    // 启动内部倒计时（无 UI）
    startQrCountdown() {
      var self = this;
      this.clearRefreshTimer();

      var currentTicket = this.currentQrTickets[this.currentQrIndex];
      if (!currentTicket) return;

      this.currentExpiresIn = currentTicket.qr_expires_in || 0;

      this.refreshTimer = setInterval(function() {
        self.currentExpiresIn--;
        // 剩余 ≤ 30 秒时静默刷新
        if (self.currentExpiresIn <= 30 && self.currentExpiresIn > 0) {
          self.silentRefreshQr(self.currentQrIndex);
        }
        if (self.currentExpiresIn <= 0) {
          self.clearRefreshTimer();
        }
      }, 1000);
    },

    // 静默刷新某张票 of QR
    silentRefreshQr(ticketIndex) {
      var self = this;
      var ticket = this.currentQrTickets[ticketIndex];
      if (!ticket) return;

      uni.request({
        url: app.globalData.get_request_url('refreshQr', 'ticket', 'vr_ticket', 'id=' + ticket.id),
        method: 'GET',
        dataType: 'json',
        success: function(res) {
          if (res.data.code == 0 && res.data.data.ticket) {
            self.$set(self.currentQrTickets, ticketIndex, res.data.data.ticket);
            self.currentExpiresIn = res.data.data.ticket.qr_expires_in || 0;
          }
        },
        fail: function() {
          // 静默失败，不提示
        },
      });
    },

    // 用户点击过期遮罩触发刷新（来自 popup 组件事件）
    onQrRefresh() {
      var self = this;
      var ticketIndex = this.currentQrIndex;
      var ticket = this.currentQrTickets[ticketIndex];
      if (!ticket) return;

      uni.showLoading({ title: '刷新中...' });
      uni.request({
        url: app.globalData.get_request_url('refreshQr', 'ticket', 'vr_ticket', 'id=' + ticket.id),
        method: 'GET',
        dataType: 'json',
        success: function(res) {
          uni.hideLoading();
          if (res.data.code == 0 && res.data.data.ticket) {
            self.$set(self.currentQrTickets, ticketIndex, res.data.data.ticket);
            self.currentExpiresIn = res.data.data.ticket.qr_expires_in || 0;
          } else {
            app.globalData.showToast(res.data.msg || '刷新失败');
          }
        },
        fail: function() {
          uni.hideLoading();
          app.globalData.showToast('网络错误，刷新失败');
        },
      });
    },

    // 清理定时器
    clearRefreshTimer() {
      if (this.refreshTimer) {
        clearInterval(this.refreshTimer);
        this.refreshTimer = null;
      }
    },

    // 提亮屏幕（检票场景）
    boostScreenBrightness() {
      // #ifndef H5
      uni.setScreenBrightness({ value: 1.0 });
      // #endif
    },

    // 恢复屏幕原始亮度
    restoreScreenBrightness() {
      // #ifndef H5
      if (this.screenBrightnessValue > 0) {
        uni.setScreenBrightness({ value: this.screenBrightnessValue });
      }
      // #endif
    },
  },
};
</script>

<style>
@import './ticket-wallet.css';
</style>
