13404089107
2026-01-04 9cb0ee550c94e0e86e1895c0fc0870c031f88857
Merge branch 'main' of http://120.76.84.145:10101/gitblit/r/H5/qingduTicketing
11个文件已添加
11个文件已修改
2198 ■■■■■ 已修改文件
miniprogram/pages.json 411 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/pages/agreement/agreement.vue 256 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/pages/good/good.vue 146 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/pages/home/home.vue 22 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/pages/invoice/addInvoice.vue 182 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/pages/invoice/applyInvoice.vue 182 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/pages/invoice/invoice.vue 182 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/pages/invoice/invoiceDetail.vue 182 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/pages/notice/notice.vue 2 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/pages/order/order.vue 7 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/pages/strategy/detail.vue 2 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/pages/sure-order/sure-order.vue 481 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/pages/ticket/ticket.vue 68 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/pages/tourist/editTourist.vue 21 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/pages/tourist/tourist.vue 30 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/static/image/good/add.png 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/static/image/good/bg.png 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/static/image/mine/arrowRight.png 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/static/image/mine/modify.png 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/static/image/ticket/orderInfoBg.png 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/static/image/ticket/uncheck.png 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/utils/store/index.js 24 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
miniprogram/pages.json
@@ -1,207 +1,222 @@
{
  "easycom": {
    "autoscan": true,
    "custom": {
      "^u-(.*)": "@/uni_modules/uview-pro/components/u-$1/u-$1.vue"
    }
  },
  "pages": [
    {
      "path": "pages/start/start",
      "style": {
        "navigationStyle": "custom", // 取消本页面的导航栏
        "app-plus": {
          "animationType": "fade-in", // 设置fade-in淡入动画,为最合理的动画类型
          "background": "transparent", // 背景透明
          "backgroundColor": "rgba(0,0,0,0)", // 背景透明
          "popGesture": "none" // 关闭IOS屏幕左边滑动关闭当前页面的功能
        }
      }
    },
    {
      "path": "pages/login/login",
      "style": {
        "navigationStyle": "custom"
      }
    },
    {
      "path": "pages/home/home",
      "style": {
        "navigationStyle": "custom"
      }
    },
    {
      "path": "pages/mine/mine",
      "style": {
        "navigationStyle": "custom"
      }
    },
    {
      "path": "pages/strategy/strategy",
      "style": {
        "navigationBarTitleText": "攻略",
        "navigationBarBackgroundColor": "#fff"
      }
    },
    {
      "path": "pages/good/good",
      "style": {
        "navigationBarTitleText": ""
      }
    },
    {
      "path": "pages/mineInfo/mineInfo",
      "style": {
        "navigationBarTitleText": "个人中心"
      }
    },
    {
      "path": "pages/order/order",
      "style": {
        "navigationBarTitleText": "我的订单"
      }
    },
    {
      "path": "pages/tourist/tourist",
      "style": {
        "navigationBarTitleText": "选择游客"
      }
    },
    {
      "path": "pages/tourist/editTourist",
      "style": {
        "navigationBarTitleText": "编辑游客"
      }
    },
    {
      "path": "pages/strategy/detail",
      "style": {
        "navigationStyle": "custom"
      }
    },
    {
      "path": "pages/notice/notice",
      "style": {
        "navigationBarTitleText": "景区公告",
        "navigationBarBackgroundColor": "#fff"
      }
    },
    {
      "path": "pages/notice/detail",
      "style": {
        "navigationBarTitleText": "景区公告",
        "navigationBarBackgroundColor": "#fff"
      }
    },
    {
      "path": "pages/contact/contact",
      "style": {
        "navigationBarTitleText": "联系客服",
        "navigationBarBackgroundColor": "#fff"
      }
    },
    {
      "path": "pages/ticket/ticket",
      "style": {
        "navigationBarTitleText": "青城后山门票预订",
        "navigationBarBackgroundColor": "#fff"
      }
    },
    {
      "path": "pages/book-notice/book-notice",
      "style": {
        "navigationBarTitleText": "预订须知",
        "navigationBarBackgroundColor": "#fff"
      }
    },
    {
      "path": "pages/orderDetail/orderDetail",
      "style": {
        "navigationStyle": "custom"
      }
    },
    {
      "path": "pages/orderDetail/refund",
      "style": {
        "navigationStyle": "custom"
      }
    },
    {
      "path" : "pages/sure-order/sure-order",
        "style" : {
            "navigationStyle": "custom"
        }
    },    {
            "path": "pages/goodOrder/goodOrder",
    "easycom": {
        "autoscan": true,
        "custom": {
            "^u-(.*)": "@/uni_modules/uview-pro/components/u-$1/u-$1.vue"
        }
    },
    "pages": [{
            "path": "pages/start/start",
            "style": {
                "navigationBarTitleText": "订单列表"
                "navigationStyle": "custom", // 取消本页面的导航栏
                "app-plus": {
                    "animationType": "fade-in", // 设置fade-in淡入动画,为最合理的动画类型
                    "background": "transparent", // 背景透明
                    "backgroundColor": "rgba(0,0,0,0)", // 背景透明
                    "popGesture": "none" // 关闭IOS屏幕左边滑动关闭当前页面的功能
                }
            }
        },
        {
            "path": "pages/goodOrder/orderDetail",
            "path": "pages/login/login",
            "style": {
                "navigationStyle": "custom"
            }
        },
        {
            "path": "pages/home/home",
            "style": {
                "navigationStyle": "custom"
            }
        },
        {
            "path": "pages/mine/mine",
            "style": {
                "navigationStyle": "custom"
            }
        },
        {
            "path": "pages/strategy/strategy",
            "style": {
                "navigationBarTitleText": "攻略",
                "navigationBarBackgroundColor": "#fff"
            }
        },
        {
            "path": "pages/good/good",
            "style": {
                "navigationStyle": "custom"
            }
        },
        {
            "path": "pages/mineInfo/mineInfo",
            "style": {
                "navigationBarTitleText": "个人中心"
            }
        },
        {
            "path": "pages/order/order",
            "style": {
                "navigationBarTitleText": "我的订单"
            }
        },
        {
            "path": "pages/tourist/tourist",
            "style": {
                "navigationBarTitleText": "选择游客"
            }
        },
        {
            "path": "pages/tourist/editTourist",
            "style": {
                "navigationBarTitleText": "编辑游客"
            }
        },
        {
            "path": "pages/strategy/detail",
            "style": {
                "navigationStyle": "custom"
            }
        },
        {
            "path": "pages/notice/notice",
            "style": {
                "navigationBarTitleText": "景区公告",
                "navigationBarBackgroundColor": "#fff"
            }
        },
        {
            "path": "pages/notice/detail",
            "style": {
                "navigationBarTitleText": "景区公告",
                "navigationBarBackgroundColor": "#fff"
            }
        },
        {
            "path": "pages/contact/contact",
            "style": {
                "navigationBarTitleText": "联系客服",
                "navigationBarBackgroundColor": "#fff"
            }
        },
        {
            "path": "pages/ticket/ticket",
            "style": {
                "navigationBarTitleText": "青城后山门票预订",
                "navigationBarBackgroundColor": "#fff"
            }
        },
        {
            "path": "pages/book-notice/book-notice",
            "style": {
                "navigationBarTitleText": "预订须知",
                "navigationBarBackgroundColor": "#fff"
            }
        },
        {
            "path": "pages/orderDetail/orderDetail",
            "style": {
                "navigationStyle": "custom"
            }
        },
        {
            "path": "pages/orderDetail/refund",
            "style": {
                "navigationStyle": "custom"
            }
        },
        {
            "path": "pages/sure-order/sure-order",
            "style": {
                "navigationStyle": "custom"
            }
        },
        {
            "path": "pages/agreement/agreement",
            "style": {
                "navigationBarTitleText": ""
            }
        },
        {
            "path": "pages/invoice/invoice",
            "style": {
                "navigationBarTitleText": "发票管理"
            }
        },
        {
            "path": "pages/invoice/addInvoice",
            "style": {
                "navigationBarTitleText": "我要开票"
            }
        },
        {
            "path": "pages/invoice/invoiceDetail",
            "style": {
                "navigationBarTitleText": "发票详情",
                "navigationStyle": "custom"
            }
        },
        {
            "path": "pages/invoice/applyInvoice",
            "style": {
                "navigationBarTitleText": "申请开票"
            }
        }
  ],
  "subPackages": [
    {
      "root": "pagesA",
      "pages": [
        {
          "path": "bannerDetail/bannerDetail",
          "style": {
            "navigationBarTitleText": "轮播图详情",
            "navigationBarBackgroundColor": "#fff"
          }
        },
        {
          "path": "mapAndGuide/mapAndGuide",
          "style": {
            "navigationBarTitleText": "景区导览",
            "navigationBarBackgroundColor": "#fff"
          }
        }
      ]
    }
  ],
  "tabBar": {
    "color": "#A5A3AF",
    "selectedColor": "#06C584",
    "borderStyle": "black",
    "backgroundColor": "#ffffff",
    "list": [
      {
        "pagePath": "pages/home/home",
        "iconPath": "static/image/tabBar/nohome.png",
        "selectedIconPath": "static/image/tabBar/home.png",
        "text": "首页"
      },
      {
        "pagePath": "pages/good/good",
        "iconPath": "static/image/tabBar/nogood.png",
        "selectedIconPath": "static/image/tabBar/good.png",
        "text": "文创商城"
      },
      {
        "pagePath": "pages/strategy/strategy",
        "iconPath": "static/image/tabBar/nostrategy.png",
        "selectedIconPath": "static/image/tabBar/strategy.png",
        "text": "攻略"
      },
      {
        "pagePath": "pages/mine/mine",
        "iconPath": "static/image/tabBar/nomine.png",
        "selectedIconPath": "static/image/tabBar/mine.png",
        "text": "我的"
      }
    ]
  },
  "globalStyle": {
    "navigationBarTextStyle": "black",
    "navigationBarTitleText": "青城后山",
    "navigationBarBackgroundColor": "#fff",
    "backgroundColor": "#fff"
  },
  "uniIdRouter": {}
}
    ],
    "subPackages": [{
        "root": "pagesA",
        "pages": [{
                "path": "bannerDetail/bannerDetail",
                "style": {
                    "navigationBarTitleText": "轮播图详情",
                    "navigationBarBackgroundColor": "#fff"
                }
            },
            {
                "path": "mapAndGuide/mapAndGuide",
                "style": {
                    "navigationBarTitleText": "景区导览",
                    "navigationBarBackgroundColor": "#fff"
                }
            }
        ]
    }],
    "tabBar": {
        "color": "#A5A3AF",
        "selectedColor": "#06C584",
        "borderStyle": "black",
        "backgroundColor": "#ffffff",
        "list": [{
                "pagePath": "pages/home/home",
                "iconPath": "static/image/tabBar/nohome.png",
                "selectedIconPath": "static/image/tabBar/home.png",
                "text": "首页"
            },
            {
                "pagePath": "pages/good/good",
                "iconPath": "static/image/tabBar/nogood.png",
                "selectedIconPath": "static/image/tabBar/good.png",
                "text": "文创商城"
            },
            {
                "pagePath": "pages/strategy/strategy",
                "iconPath": "static/image/tabBar/nostrategy.png",
                "selectedIconPath": "static/image/tabBar/strategy.png",
                "text": "攻略"
            },
            {
                "pagePath": "pages/mine/mine",
                "iconPath": "static/image/tabBar/nomine.png",
                "selectedIconPath": "static/image/tabBar/mine.png",
                "text": "我的"
            }
        ]
    },
    "globalStyle": {
        "navigationBarTextStyle": "black",
        "navigationBarTitleText": "青城后山",
        "navigationBarBackgroundColor": "#fff",
        "backgroundColor": "#fff"
    },
    "uniIdRouter": {}
}
miniprogram/pages/agreement/agreement.vue
New file
@@ -0,0 +1,256 @@
<template>
    <view class="container">
        <view class="content-box">
            <rich-text :nodes="content"></rich-text>
        </view>
    </view>
</template>
<script setup lang="ts">
    import { onLoad } from "@dcloudio/uni-app";
    import { ref } from "vue";
    const content = ref<string>("");
    // 生成协议1的富文本内容(青城山票务预订条款)
    const getAgreement1Content = () => {
        return `
            <div style="line-height: 1.8; color: #333; font-size: 28rpx;">
                <h2 style="text-align: center; font-size: 36rpx; font-weight: 600; margin-bottom: 40rpx; color: #191F3F;">青城山票务预订条款</h2>
                <p style="margin-bottom: 30rpx; text-indent: 2em;">
                    欢迎使用青城山票务预订服务。在您使用本服务前,请仔细阅读以下条款。一旦您使用本服务,即表示您已充分理解并同意接受本条款的全部内容。
                </p>
                <h3 style="font-size: 32rpx; font-weight: 600; margin: 40rpx 0 20rpx 0; color: #191F3F;">一、服务说明</h3>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    1.1 青城山票务预订平台(以下简称"本平台")为用户提供景区门票在线预订服务。
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    1.2 用户通过本平台预订的门票,需在指定日期和时段内使用,逾期未使用将视为自动放弃,不予退款。
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    1.3 本平台保留对门票价格、库存、使用规则等进行调整的权利,调整后的规则将在平台上公示。
                </p>
                <h3 style="font-size: 32rpx; font-weight: 600; margin: 40rpx 0 20rpx 0; color: #191F3F;">二、预订规则</h3>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    2.1 用户预订门票时,需如实填写游客信息,包括姓名、身份证号、联系电话等。
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    2.2 每个订单最多可预订10张门票,超出数量需分单预订。
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    2.3 门票预订成功后,系统将发送确认信息至用户预留的联系方式。
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    2.4 用户需在预订时选择使用日期和时段,选定后不可随意更改。
                </p>
                <h3 style="font-size: 32rpx; font-weight: 600; margin: 40rpx 0 20rpx 0; color: #191F3F;">三、支付规则</h3>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    3.1 用户需在预订后30分钟内完成支付,超时未支付订单将自动取消。
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    3.2 支付成功后,订单不可取消,门票不可退换。
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    3.3 如因不可抗力因素导致景区关闭,本平台将全额退款。
                </p>
                <h3 style="font-size: 32rpx; font-weight: 600; margin: 40rpx 0 20rpx 0; color: #191F3F;">四、使用规则</h3>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    4.1 用户需凭有效身份证件和电子门票在指定日期和时段内入园。
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    4.2 门票仅限本人使用,不得转让、转售或用于其他商业用途。
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    4.3 如发现门票被非法使用,本平台有权取消该门票并追究相关责任。
                </p>
                <h3 style="font-size: 32rpx; font-weight: 600; margin: 40rpx 0 20rpx 0; color: #191F3F;">五、免责声明</h3>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    5.1 因不可抗力(如自然灾害、政府行为等)导致的服务中断或终止,本平台不承担责任。
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    5.2 用户因自身原因(如信息填写错误、未按时使用等)造成的损失,由用户自行承担。
                </p>
                <h3 style="font-size: 32rpx; font-weight: 600; margin: 40rpx 0 20rpx 0; color: #191F3F;">六、其他条款</h3>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    6.1 本平台保留对本条款的最终解释权。
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    6.2 如有疑问,请联系客服:400-XXX-XXXX。
                </p>
                <p style="margin-top: 40rpx; text-align: right; color: #8E92AA; font-size: 24rpx;">
                    最后更新时间:2025年1月1日
                </p>
            </div>
        `;
    };
    // 生成协议2的富文本内容(用户隐私协议)
    const getAgreement2Content = () => {
        return `
            <div style="line-height: 1.8; color: #333; font-size: 28rpx;">
                <h2 style="text-align: center; font-size: 36rpx; font-weight: 600; margin-bottom: 40rpx; color: #191F3F;">用户隐私协议</h2>
                <p style="margin-bottom: 30rpx; text-indent: 2em;">
                    青城山票务平台(以下简称"我们")非常重视用户的隐私保护。本隐私协议说明了我们如何收集、使用、存储和保护您的个人信息。请您仔细阅读本协议。
                </p>
                <h3 style="font-size: 32rpx; font-weight: 600; margin: 40rpx 0 20rpx 0; color: #191F3F;">一、信息收集</h3>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    1.1 我们可能收集以下信息:
                </p>
                <p style="margin-bottom: 10rpx; padding-left: 60rpx;">
                    • 身份信息:姓名、身份证号码
                </p>
                <p style="margin-bottom: 10rpx; padding-left: 60rpx;">
                    • 联系方式:手机号码、电子邮箱
                </p>
                <p style="margin-bottom: 10rpx; padding-left: 60rpx;">
                    • 订单信息:预订的门票类型、数量、使用日期等
                </p>
                <p style="margin-bottom: 10rpx; padding-left: 60rpx;">
                    • 设备信息:设备型号、操作系统、IP地址等
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    1.2 我们仅收集提供服务所必需的信息,不会收集无关信息。
                </p>
                <h3 style="font-size: 32rpx; font-weight: 600; margin: 40rpx 0 20rpx 0; color: #191F3F;">二、信息使用</h3>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    2.1 我们使用收集的信息用于以下目的:
                </p>
                <p style="margin-bottom: 10rpx; padding-left: 60rpx;">
                    • 处理您的订单和支付
                </p>
                <p style="margin-bottom: 10rpx; padding-left: 60rpx;">
                    • 向您发送订单确认、服务通知等信息
                </p>
                <p style="margin-bottom: 10rpx; padding-left: 60rpx;">
                    • 改进我们的服务质量和用户体验
                </p>
                <p style="margin-bottom: 10rpx; padding-left: 60rpx;">
                    • 遵守法律法规要求
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    2.2 未经您同意,我们不会将您的个人信息用于其他目的。
                </p>
                <h3 style="font-size: 32rpx; font-weight: 600; margin: 40rpx 0 20rpx 0; color: #191F3F;">三、信息存储</h3>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    3.1 我们采用行业标准的安全措施保护您的个人信息,防止未经授权的访问、使用或泄露。
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    3.2 您的个人信息将存储在安全的服务器上,我们会对数据进行加密处理。
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    3.3 我们仅在必要的时间内保留您的个人信息,超出保留期限后将删除或匿名化处理。
                </p>
                <h3 style="font-size: 32rpx; font-weight: 600; margin: 40rpx 0 20rpx 0; color: #191F3F;">四、信息共享</h3>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    4.1 我们不会向第三方出售、出租或分享您的个人信息,除非:
                </p>
                <p style="margin-bottom: 10rpx; padding-left: 60rpx;">
                    • 获得您的明确同意
                </p>
                <p style="margin-bottom: 10rpx; padding-left: 60rpx;">
                    • 法律法规要求
                </p>
                <p style="margin-bottom: 10rpx; padding-left: 60rpx;">
                    • 为提供服务需要(如支付处理、短信发送等),但我们会要求第三方严格保密
                </p>
                <h3 style="font-size: 32rpx; font-weight: 600; margin: 40rpx 0 20rpx 0; color: #191F3F;">五、您的权利</h3>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    5.1 您有权访问、更正、删除您的个人信息。
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    5.2 您有权撤回对个人信息处理的同意。
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    5.3 您可以通过客服渠道行使上述权利。
                </p>
                <h3 style="font-size: 32rpx; font-weight: 600; margin: 40rpx 0 20rpx 0; color: #191F3F;">六、Cookie使用</h3>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    6.1 我们使用Cookie等技术来改善用户体验和分析服务使用情况。
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    6.2 您可以通过浏览器设置管理Cookie,但这可能影响部分功能的使用。
                </p>
                <h3 style="font-size: 32rpx; font-weight: 600; margin: 40rpx 0 20rpx 0; color: #191F3F;">七、未成年人保护</h3>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    7.1 我们非常重视未成年人的个人信息保护。
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    7.2 如果您是未成年人,请在监护人同意和指导下使用我们的服务。
                </p>
                <h3 style="font-size: 32rpx; font-weight: 600; margin: 40rpx 0 20rpx 0; color: #191F3F;">八、协议更新</h3>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    8.1 我们可能会不定期更新本隐私协议,更新后的协议将在平台上公示。
                </p>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    8.2 继续使用我们的服务即表示您接受更新后的协议。
                </p>
                <h3 style="font-size: 32rpx; font-weight: 600; margin: 40rpx 0 20rpx 0; color: #191F3F;">九、联系我们</h3>
                <p style="margin-bottom: 20rpx; text-indent: 2em;">
                    如您对本隐私协议有任何疑问,或需要行使相关权利,请联系我们:
                </p>
                <p style="margin-bottom: 10rpx; padding-left: 60rpx;">
                    客服电话:400-XXX-XXXX
                </p>
                <p style="margin-bottom: 10rpx; padding-left: 60rpx;">
                    电子邮箱:privacy@qingchengshan.com
                </p>
                <p style="margin-top: 40rpx; text-align: right; color: #8E92AA; font-size: 24rpx;">
                    最后更新时间:2025年1月1日
                </p>
            </div>
        `;
    };
    onLoad((params) => {
        const type = Number(params.type) || 1;
        const titles = ["", "青城山票务预订条款", "用户隐私协议"];
        // 设置导航栏标题
        uni.setNavigationBarTitle({
            title: titles[type] || "协议详情"
        });
        // 根据类型设置内容
        if (type === 1) {
            content.value = getAgreement1Content();
        } else if (type === 2) {
            content.value = getAgreement2Content();
        }
    });
</script>
<style>
    page {
        background-color: #fff;
    }
</style>
<style scoped lang="scss">
    .container {
        width: 100%;
        min-height: 100vh;
        background-color: #fff;
        .content-box {
            padding: 38rpx 27rpx;
            box-sizing: border-box;
        }
    }
</style>
miniprogram/pages/good/good.vue
@@ -1,19 +1,143 @@
<template>
    <view>
    <view class="container">
        <image src="/static/image/good/bg.png" class="bg"></image>
        <view class="pt-98 relative zIndex1000">
            <view class="search-card">
                <u-search placeholder-color="rgba(0,0,0,0.4)" search-icon-color="RGBA(152, 152, 152, 1)"
                    placeholder="请输入商品名称" style="line-height: 62rpx;" :action-style="actionStyle" v-model="keyword"
                    @search="fetchList" @custom="fetchList" @clear="fetchList"></u-search>
            </view>
            <view class="pl-23 pr-23">
                <image src="https://cdn.pixabay.com/photo/2015/12/01/20/28/road-1072823_1280.jpg" class="titImg">
                </image>
            </view>
            <view class="title">全部分类</view>
            <view class="good-list">
                <view class="good-item" v-for="(item,index) in 10" :key="item">
                    <image src="https://cdn.pixabay.com/photo/2015/12/01/20/28/road-1072823_1280.jpg" class="good-img">
                    </image>
                    <view class="good-name">四川地标青城山冰箱贴</view>
                    <view class="flex a-center j-between">
                        <view class="good-price">¥<text class="fs-38">20.00</text></view>
                        <image src="/static/image/good/add.png" class="w-46 h-46 mr-11">
                        </image>
                    </view>
                </view>
            </view>
        </view>
    </view>
</template>
<script>
    export default {
        data() {
            return {
            };
        }
    }
<script setup lang="ts">
    import { onLoad } from "@dcloudio/uni-app";
    import { ref } from "vue";
    const actionStyle = ref({
        'width': '135rpx',
        'height': '62rpx',
        'background': '#06C584',
        'border-radius': '67rpx',
        'font-weight': '500',
        'font-size': '23rpx',
        'color': '#FFFFFF',
        'line-height': '62rpx'
    })
    const keyword = ref('')
    const fetchList = () => { }
    onLoad((params) => {
    });
</script>
<style lang="scss">
<style>
    page {
        background-color: #fff;
    }
</style>
<style scoped lang="scss">
    .container {
        position: relative;
        .u-search {
            width: 696rpx;
            height: 77rpx;
            background: rgba(255, 255, 255, 0.7);
            box-shadow: 0rpx 8rpx 31rpx 0rpx rgba(0, 99, 65, 0.1);
            border-radius: 38rpx;
            border: 2rpx solid #06C584;
        }
        .bg {
            position: absolute;
            top: 0;
            left: 0;
            width: 100vw;
            height: 519rpx;
            z-index: 9;
        }
        .search-card {
            margin-left: 27rpx;
            margin-right: 203rpx;
            background: rgba(255, 255, 255, 0.7);
            box-shadow: 0rpx 8rpx 31rpx 0rpx rgba(0, 99, 65, 0.1);
            border-radius: 38rpx;
            padding: 6rpx 7rpx 7rpx 7rpx;
            margin-bottom: 38rpx;
        }
        .titImg {
            width: 704rpx;
            height: 250rpx;
            border-radius: 19rpx;
        }
        .title {
            font-weight: 600;
            font-size: 38rpx;
            color: #191F3F;
            line-height: 54rpx;
            margin: 65rpx 0 34rpx 38rpx;
        }
        .good-list {
            padding: 0 19rpx;
            display: flex;
            flex-wrap: wrap;
            justify-content: space-between;
            .good-item {
                margin-bottom: 38rpx;
                .good-img {
                    width: 346rpx;
                    height: 346rpx;
                    border-radius: 19rpx;
                    margin-bottom: 19rpx;
                }
                .good-name {
                    font-weight: 600;
                    font-size: 29rpx;
                    color: #191F3F;
                    line-height: 40rpx;
                    margin-left: 11rpx;
                    margin-bottom: 15rpx;
                }
                .good-price {
                    display: flex;
                    align-items: center;
                    font-weight: 600;
                    font-size: 27rpx;
                    color: #FF6257;
                    line-height: 38rpx;
                }
            }
        }
    }
</style>
miniprogram/pages/home/home.vue
@@ -14,7 +14,7 @@
            <u-notice-bar color="#191F3F" bg-color="transparent" volume-size="0" font-size="25" mode="horizontal"
                :list="noticeList"></u-notice-bar>
        </view>
        <wd-calendar :showPanelTitle="false" v-model="value" @confirm="handleConfirm">选择日期</wd-calendar>
        <view class="iconList">
            <view class="relative br-19 bgcolor2 pt-27 pb-29" @tap.stop="toTicket()">
                <view class="flex a-center br-154 py-12 px-12 ml-27 bgcolor3 w-fit">
@@ -56,11 +56,11 @@
                        <image src="/static/image/home/hot.png" class="w-37 h-38 shrink0 mr-17" />
                        <view class="fs-38 lh-54 font-bold">景区攻略精选</view>
                    </view>
                    <view class="fs-27 lh-38 color6">查看更多</view>
                    <view class="fs-27 lh-38 color6" @tap="toStrategy()">查看更多</view>
                </view>
            </view>
            <view class="listBox">
                <view v-for="item in 10" :key="item" class="relative">
                <view v-for="item in 10" :key="item" class="relative" @click="toStrategyDetail(item)">
                    <image class="br-19" style="height: 396rpx;width: 346rpx;"
                        src="https://huishou-1323682843.cos.ap-nanjing.myqcloud.com/images/832d1c03-9536-4019-8a1f-3d1388ac836e.png" />
                    <view class="absolute flex a-center br-138 h-35 pl-15 pr-12 bgcolor10"
@@ -80,7 +80,7 @@
    import { ref, reactive } from "vue";
    import { onLoad, onShow, onReachBottom } from "@dcloudio/uni-app"
    import Banner from '@/components/banner.vue'
    const value = ref<number>(Date.now())
    const params = ref({
        pageNum: 1,
        pageSize: 10,
@@ -103,9 +103,7 @@
    onReachBottom(() => {
    })
    const handleConfirm = ({ value }) => {
        console.log(value)
    }
    const toMap = () => {
        uni.navigateTo({
            url: '/pagesA/mapAndGuide/mapAndGuide'
@@ -127,6 +125,16 @@
            url: '/pages/ticket/ticket'
        })
    }
    const toStrategy = () => {
        uni.navigateTo({
            url: '/pages/strategy/strategy'
        })
    }
    const toStrategyDetail = () => {
        uni.navigateTo({
            url: '/pages/strategy/detail'
        })
    }
</script>
<style>
    page {
miniprogram/pages/invoice/addInvoice.vue
New file
@@ -0,0 +1,182 @@
<template>
    <view class="container">
        <view class="px-27">
            <view class="list-item" v-for="(item, index) in invoiceList" :key="index"  @click="toDetail(item)">
                <view class="flex a-center j-between">
                    <view class="time">{{ item.time || '' }}</view>
                    <view class="status flex a-center j-center">开票中</view>
                </view>
                <view class="flex a-center j-between">
                    <view class="name">{{ item.name || '' }}</view>
                    <view class="price"><text>¥ </text>{{ item.price || '' }}</view>
                </view>
            </view>
        </view>
    </view>
</template>
<script setup lang="ts">
import { ref } from "vue";
import { onLoad, onUnload, onShow, onReachBottom } from "@dcloudio/uni-app";
const invoiceList = ref([
    {
        time: '2023-08-01 10:00:00',
        name: '成人票',
        price: '100.00',
        img: '/static/image/mine/contact.png'
    }
]);
const finished = ref(false);
const loading = ref(false);
const searchParams = ref({
    pageNum: 1,
    pageSize: 10
})
const toAdd = () => {
    uni.navigateTo({
        url: '/pages/invoice/addInvoice',
    })
}
const toDetail = (item) => {
    uni.navigateTo({
        url: '/pages/invoice/invoiceDetail?id=' + item.id,
    })
}
const fetchList = () => {
    //         // if (loading.value || finished.value) return
    //         loading.value = true
    //         getMonitorList({
    //             nameOrCode: keyword.value || '',
    //             pageNum: searchParams.value.pageNum,
    //             pageSize: searchParams.value.pageSize
    //         }).then(res => {
    //             // PC 端类型定义:{ records, total, current, size }
    //             const data = res.data || res || {}
    //             const records = data.records || []
    //             const total = data.total || 0
    //             if (searchParams.value.pageNum === 1) {
    //                 list.value = records
    //             } else {
    //                 list.value = list.value.concat(records)
    //             }
    //             // 判断是否已全部加载
    //             if (!records.length || list.value.length >= total) {
    //                 finished.value = true
    //             } else {
    //                 searchParams.value.pageNum += 1
    //             }
    //         }).catch(() => {
    //             uni.showToast({
    //                 title: '获取巡检列表失败',
    //                 icon: 'none'
    //             })
    //         }).finally(() => {
    //             loading.value = false
    //         })
}
onReachBottom(() => {
})
</script>
<style>
    page{
        background-color: #FFFFFF;
    }
</style>
<style scoped lang="scss">
.container {
    width: 100%;
    height: 100%;
    position: relative;
    .footer {
        width: 100%;
        height: 96rpx;
        background: #FFFFFF;
        box-shadow: 0rpx 6rpx 6rpx 0rpx rgba(0, 0, 0, 0.05);
        position: sticky;
        bottom: 0;
        left: 0;
        padding: 0 27rpx;
        box-sizing: border-box;
        font-family: PingFangSC, PingFang SC;
        font-weight: 600;
        font-size: 31rpx;
        color: #303133;
        line-height: 42rpx;
        text-shadow: 0px 6px 6px rgba(0, 0, 0, 0.05);
        .invoice {
            font-family: PingFangSC, PingFang SC;
            font-weight: 500;
            font-size: 27rpx;
            color: #4F4F4F;
            line-height: 38rpx;
            text-shadow: 0px 6px 6px rgba(0, 0, 0, 0.05);
        }
        image {
            margin-left: 12rpx;
        }
    }
    .list-item {
        margin-top: 27rpx;
        width: 696rpx;
        height: 173rpx;
        background: #FFFFFF;
        border-radius: 19rpx;
        padding: 25rpx 31rpx;
        .time {
            font-family: PingFangSC, PingFang SC;
            font-weight: 500;
            font-size: 23rpx;
            color: #8C8C8C;
            line-height: 23rpx;
        }
        .status {
            width: 104rpx;
            height: 46rpx;
            background: #D9FFF2;
            border-radius: 12rpx;
            font-family: PingFangSC, PingFang SC;
            font-weight: 600;
            font-size: 25rpx;
            color: #06C584;
            line-height: 23rpx;
            letter-spacing: 1px;
            margin-bottom: 17rpx;
        }
        .name {
            font-family: PingFangSC, PingFang SC;
            font-weight: 600;
            font-size: 38rpx;
            color: #303133;
            line-height: 54rpx;
        }
        .price {
            font-family: PingFangSC, PingFang SC;
            font-weight: 600;
            font-size: 38rpx;
            color: #FF6257;
            line-height: 38rpx;
            text {
                font-size: 27rpx;
            }
        }
    }
}
</style>
miniprogram/pages/invoice/applyInvoice.vue
New file
@@ -0,0 +1,182 @@
<template>
    <view class="container">
        <view class="head flex a-center j-between">
            <view>开票记录</view>
            <view class="flex a-center invoice" @click="toAdd">我要开票 <image src="/static/image/mine/arrowRight.png" class="w-23 h-23">
                </image>
            </view>
        </view>
        <view class="px-27">
            <view class="list-item" v-for="(item, index) in invoiceList" :key="index"  @click="toDetail(item)">
                <view class="flex a-center j-between">
                    <view class="time">{{ item.time || '' }}</view>
                    <view class="status flex a-center j-center">开票中</view>
                </view>
                <view class="flex a-center j-between">
                    <view class="name">{{ item.name || '' }}</view>
                    <view class="price"><text>¥ </text>{{ item.price || '' }}</view>
                </view>
            </view>
        </view>
    </view>
</template>
<script setup lang="ts">
import { ref } from "vue";
import { onLoad, onUnload, onShow, onReachBottom } from "@dcloudio/uni-app";
const invoiceList = ref([
    {
        time: '2023-08-01 10:00:00',
        name: '成人票',
        price: '100.00'
    }
]);
const finished = ref(false);
const loading = ref(false);
const searchParams = ref({
    pageNum: 1,
    pageSize: 10
})
const toAdd = () => {
    uni.navigateTo({
        url: '/pages/invoice/addInvoice',
    })
}
const toDetail = (item) => {
    uni.navigateTo({
        url: '/pages/invoice/invoiceDetail?id=' + item.id,
    })
}
const fetchList = () => {
    //         // if (loading.value || finished.value) return
    //         loading.value = true
    //         getMonitorList({
    //             nameOrCode: keyword.value || '',
    //             pageNum: searchParams.value.pageNum,
    //             pageSize: searchParams.value.pageSize
    //         }).then(res => {
    //             // PC 端类型定义:{ records, total, current, size }
    //             const data = res.data || res || {}
    //             const records = data.records || []
    //             const total = data.total || 0
    //             if (searchParams.value.pageNum === 1) {
    //                 list.value = records
    //             } else {
    //                 list.value = list.value.concat(records)
    //             }
    //             // 判断是否已全部加载
    //             if (!records.length || list.value.length >= total) {
    //                 finished.value = true
    //             } else {
    //                 searchParams.value.pageNum += 1
    //             }
    //         }).catch(() => {
    //             uni.showToast({
    //                 title: '获取巡检列表失败',
    //                 icon: 'none'
    //             })
    //         }).finally(() => {
    //             loading.value = false
    //         })
}
onReachBottom(() => {
})
</script>
<style scoped lang="scss">
.container {
    width: 100%;
    height: 100%;
    position: relative;
    .head {
        width: 100%;
        height: 96rpx;
        background: #FFFFFF;
        box-shadow: 0rpx 6rpx 6rpx 0rpx rgba(0, 0, 0, 0.05);
        position: sticky;
        top: 0;
        left: 0;
        padding: 0 27rpx;
        box-sizing: border-box;
        font-family: PingFangSC, PingFang SC;
        font-weight: 600;
        font-size: 31rpx;
        color: #303133;
        line-height: 42rpx;
        text-shadow: 0px 6px 6px rgba(0, 0, 0, 0.05);
        .invoice {
            font-family: PingFangSC, PingFang SC;
            font-weight: 500;
            font-size: 27rpx;
            color: #4F4F4F;
            line-height: 38rpx;
            text-shadow: 0px 6px 6px rgba(0, 0, 0, 0.05);
        }
        image {
            margin-left: 12rpx;
        }
    }
    .list-item {
        margin-top: 27rpx;
        width: 696rpx;
        height: 173rpx;
        background: #FFFFFF;
        border-radius: 19rpx;
        padding: 25rpx 31rpx;
        .time {
            font-family: PingFangSC, PingFang SC;
            font-weight: 500;
            font-size: 23rpx;
            color: #8C8C8C;
            line-height: 23rpx;
        }
        .status {
            width: 104rpx;
            height: 46rpx;
            background: #D9FFF2;
            border-radius: 12rpx;
            font-family: PingFangSC, PingFang SC;
            font-weight: 600;
            font-size: 25rpx;
            color: #06C584;
            line-height: 23rpx;
            letter-spacing: 1px;
            margin-bottom: 17rpx;
        }
        .name {
            font-family: PingFangSC, PingFang SC;
            font-weight: 600;
            font-size: 38rpx;
            color: #303133;
            line-height: 54rpx;
        }
        .price {
            font-family: PingFangSC, PingFang SC;
            font-weight: 600;
            font-size: 38rpx;
            color: #FF6257;
            line-height: 38rpx;
            text {
                font-size: 27rpx;
            }
        }
    }
}
</style>
miniprogram/pages/invoice/invoice.vue
New file
@@ -0,0 +1,182 @@
<template>
    <view class="container">
        <view class="head flex a-center j-between">
            <view>开票记录</view>
            <view class="flex a-center invoice" @click="toAdd">我要开票 <image src="/static/image/mine/arrowRight.png" class="w-23 h-23">
                </image>
            </view>
        </view>
        <view class="px-27">
            <view class="list-item" v-for="(item, index) in invoiceList" :key="index"  @click="toDetail(item)">
                <view class="flex a-center j-between">
                    <view class="time">{{ item.time || '' }}</view>
                    <view class="status flex a-center j-center">开票中</view>
                </view>
                <view class="flex a-center j-between">
                    <view class="name">{{ item.name || '' }}</view>
                    <view class="price"><text>¥ </text>{{ item.price || '' }}</view>
                </view>
            </view>
        </view>
    </view>
</template>
<script setup lang="ts">
import { ref } from "vue";
import { onLoad, onUnload, onShow, onReachBottom } from "@dcloudio/uni-app";
const invoiceList = ref([
    {
        time: '2023-08-01 10:00:00',
        name: '成人票',
        price: '100.00'
    }
]);
const finished = ref(false);
const loading = ref(false);
const searchParams = ref({
    pageNum: 1,
    pageSize: 10
})
const toAdd = () => {
    uni.navigateTo({
        url: '/pages/invoice/addInvoice',
    })
}
const toDetail = (item) => {
    uni.navigateTo({
        url: '/pages/invoice/invoiceDetail?id=' + item.id,
    })
}
const fetchList = () => {
    //         // if (loading.value || finished.value) return
    //         loading.value = true
    //         getMonitorList({
    //             nameOrCode: keyword.value || '',
    //             pageNum: searchParams.value.pageNum,
    //             pageSize: searchParams.value.pageSize
    //         }).then(res => {
    //             // PC 端类型定义:{ records, total, current, size }
    //             const data = res.data || res || {}
    //             const records = data.records || []
    //             const total = data.total || 0
    //             if (searchParams.value.pageNum === 1) {
    //                 list.value = records
    //             } else {
    //                 list.value = list.value.concat(records)
    //             }
    //             // 判断是否已全部加载
    //             if (!records.length || list.value.length >= total) {
    //                 finished.value = true
    //             } else {
    //                 searchParams.value.pageNum += 1
    //             }
    //         }).catch(() => {
    //             uni.showToast({
    //                 title: '获取巡检列表失败',
    //                 icon: 'none'
    //             })
    //         }).finally(() => {
    //             loading.value = false
    //         })
}
onReachBottom(() => {
})
</script>
<style scoped lang="scss">
.container {
    width: 100%;
    height: 100%;
    position: relative;
    .head {
        width: 100%;
        height: 96rpx;
        background: #FFFFFF;
        box-shadow: 0rpx 6rpx 6rpx 0rpx rgba(0, 0, 0, 0.05);
        position: sticky;
        top: 0;
        left: 0;
        padding: 0 27rpx;
        box-sizing: border-box;
        font-family: PingFangSC, PingFang SC;
        font-weight: 600;
        font-size: 31rpx;
        color: #303133;
        line-height: 42rpx;
        text-shadow: 0px 6px 6px rgba(0, 0, 0, 0.05);
        .invoice {
            font-family: PingFangSC, PingFang SC;
            font-weight: 500;
            font-size: 27rpx;
            color: #4F4F4F;
            line-height: 38rpx;
            text-shadow: 0px 6px 6px rgba(0, 0, 0, 0.05);
        }
        image {
            margin-left: 12rpx;
        }
    }
    .list-item {
        margin-top: 27rpx;
        width: 696rpx;
        height: 173rpx;
        background: #FFFFFF;
        border-radius: 19rpx;
        padding: 25rpx 31rpx;
        .time {
            font-family: PingFangSC, PingFang SC;
            font-weight: 500;
            font-size: 23rpx;
            color: #8C8C8C;
            line-height: 23rpx;
        }
        .status {
            width: 104rpx;
            height: 46rpx;
            background: #D9FFF2;
            border-radius: 12rpx;
            font-family: PingFangSC, PingFang SC;
            font-weight: 600;
            font-size: 25rpx;
            color: #06C584;
            line-height: 23rpx;
            letter-spacing: 1px;
            margin-bottom: 17rpx;
        }
        .name {
            font-family: PingFangSC, PingFang SC;
            font-weight: 600;
            font-size: 38rpx;
            color: #303133;
            line-height: 54rpx;
        }
        .price {
            font-family: PingFangSC, PingFang SC;
            font-weight: 600;
            font-size: 38rpx;
            color: #FF6257;
            line-height: 38rpx;
            text {
                font-size: 27rpx;
            }
        }
    }
}
</style>
miniprogram/pages/invoice/invoiceDetail.vue
New file
@@ -0,0 +1,182 @@
<template>
    <view class="container">
        <view class="head flex a-center j-between">
            <view>开票记录</view>
            <view class="flex a-center invoice" @click="toAdd">我要开票 <image src="/static/image/mine/arrowRight.png" class="w-23 h-23">
                </image>
            </view>
        </view>
        <view class="px-27">
            <view class="list-item" v-for="(item, index) in invoiceList" :key="index"  @click="toDetail(item)">
                <view class="flex a-center j-between">
                    <view class="time">{{ item.time || '' }}</view>
                    <view class="status flex a-center j-center">开票中</view>
                </view>
                <view class="flex a-center j-between">
                    <view class="name">{{ item.name || '' }}</view>
                    <view class="price"><text>¥ </text>{{ item.price || '' }}</view>
                </view>
            </view>
        </view>
    </view>
</template>
<script setup lang="ts">
import { ref } from "vue";
import { onLoad, onUnload, onShow, onReachBottom } from "@dcloudio/uni-app";
const invoiceList = ref([
    {
        time: '2023-08-01 10:00:00',
        name: '成人票',
        price: '100.00'
    }
]);
const finished = ref(false);
const loading = ref(false);
const searchParams = ref({
    pageNum: 1,
    pageSize: 10
})
const toAdd = () => {
    uni.navigateTo({
        url: '/pages/invoice/addInvoice',
    })
}
const toDetail = (item) => {
    uni.navigateTo({
        url: '/pages/invoice/invoiceDetail?id=' + item.id,
    })
}
const fetchList = () => {
    //         // if (loading.value || finished.value) return
    //         loading.value = true
    //         getMonitorList({
    //             nameOrCode: keyword.value || '',
    //             pageNum: searchParams.value.pageNum,
    //             pageSize: searchParams.value.pageSize
    //         }).then(res => {
    //             // PC 端类型定义:{ records, total, current, size }
    //             const data = res.data || res || {}
    //             const records = data.records || []
    //             const total = data.total || 0
    //             if (searchParams.value.pageNum === 1) {
    //                 list.value = records
    //             } else {
    //                 list.value = list.value.concat(records)
    //             }
    //             // 判断是否已全部加载
    //             if (!records.length || list.value.length >= total) {
    //                 finished.value = true
    //             } else {
    //                 searchParams.value.pageNum += 1
    //             }
    //         }).catch(() => {
    //             uni.showToast({
    //                 title: '获取巡检列表失败',
    //                 icon: 'none'
    //             })
    //         }).finally(() => {
    //             loading.value = false
    //         })
}
onReachBottom(() => {
})
</script>
<style scoped lang="scss">
.container {
    width: 100%;
    height: 100%;
    position: relative;
    .head {
        width: 100%;
        height: 96rpx;
        background: #FFFFFF;
        box-shadow: 0rpx 6rpx 6rpx 0rpx rgba(0, 0, 0, 0.05);
        position: sticky;
        top: 0;
        left: 0;
        padding: 0 27rpx;
        box-sizing: border-box;
        font-family: PingFangSC, PingFang SC;
        font-weight: 600;
        font-size: 31rpx;
        color: #303133;
        line-height: 42rpx;
        text-shadow: 0px 6px 6px rgba(0, 0, 0, 0.05);
        .invoice {
            font-family: PingFangSC, PingFang SC;
            font-weight: 500;
            font-size: 27rpx;
            color: #4F4F4F;
            line-height: 38rpx;
            text-shadow: 0px 6px 6px rgba(0, 0, 0, 0.05);
        }
        image {
            margin-left: 12rpx;
        }
    }
    .list-item {
        margin-top: 27rpx;
        width: 696rpx;
        height: 173rpx;
        background: #FFFFFF;
        border-radius: 19rpx;
        padding: 25rpx 31rpx;
        .time {
            font-family: PingFangSC, PingFang SC;
            font-weight: 500;
            font-size: 23rpx;
            color: #8C8C8C;
            line-height: 23rpx;
        }
        .status {
            width: 104rpx;
            height: 46rpx;
            background: #D9FFF2;
            border-radius: 12rpx;
            font-family: PingFangSC, PingFang SC;
            font-weight: 600;
            font-size: 25rpx;
            color: #06C584;
            line-height: 23rpx;
            letter-spacing: 1px;
            margin-bottom: 17rpx;
        }
        .name {
            font-family: PingFangSC, PingFang SC;
            font-weight: 600;
            font-size: 38rpx;
            color: #303133;
            line-height: 54rpx;
        }
        .price {
            font-family: PingFangSC, PingFang SC;
            font-weight: 600;
            font-size: 38rpx;
            color: #FF6257;
            line-height: 38rpx;
            text {
                font-size: 27rpx;
            }
        }
    }
}
</style>
miniprogram/pages/notice/notice.vue
@@ -94,7 +94,7 @@
    const toDetail = (item) => {
        uni.navigateTo({
            url: 'pages/notice/detail'
            url: '/pages/notice/detail'
        })
    }
</script>
miniprogram/pages/order/order.vue
@@ -11,7 +11,7 @@
        <view class="order-List mt-46">
            <view class="list-item">
            <view class="list-item" @click="toDetail()">
                <view class="item-top flex j-between a-center">
                    <view class="name">青城后山成人票</view>
                    <view class="status">待支付</view>
@@ -77,6 +77,11 @@
    const changeTab = (item) => {
        activeTab.value = item.value
    }
    const toDetail = () => {
        uni.navigateTo({
            url: '/pages/orderDetail/orderDetail'
        })
    }
    onLoad((query) => {
        console.log('//////////////', query);
miniprogram/pages/strategy/detail.vue
@@ -1,7 +1,7 @@
<template>
    <view class="relative">
        <image @tap.stop="back" class="absolute w-19 h-34" src="/static/image/public/back.png"
            style="top: 104rpx;left: 27rpx;z-index: 99;" />
            style="top: 104rpx;left: 27rpx;z-index: 999;" />
        <banner :list="list" :height="700" v-if="type=='image'"></banner>
        <view class="h-700 videoContent" v-else>
            <video ref="videoPlayer" :show-center-play-btn="false" id="myVideo" :src="videoUrl" :autoplay="false"
miniprogram/pages/sure-order/sure-order.vue
@@ -3,22 +3,330 @@
        <u-navbar title="确认订单" background="transparent" :border="false" :title-bold="true" :title-size="32"
            :back-icon-size="32">
        </u-navbar>
        <image src="/static/image/ticket/orderBg.png" class="h-317" />
        <view class="pt-19">
            <view class="px-17">
                <view class="orderInfo">
                    <view class="flex a-center j-between mb-73">
                        <view class="flex flex-column">
                            <view class="title">{{ticketInfo.title}}</view>
                            <view class="time">有效期至{{ticketInfo.validDate}}</view>
                        </view>
                        <view class="flex a-center">
                            <image @tap.stop="reduce" src="/static/image/ticket/reduce.png" class="w-46 h-46"></image>
                            <view class="num">{{num}}</view>
                            <image @tap.stop="add" src="/static/image/ticket/add.png" class="w-46 h-46"></image>
                        </view>
                    </view>
                    <view class="flex a-center j-between">
                        <view class="priceText">门票价格</view>
                        <view class="priceNum">¥{{ticketInfo.price}}</view>
                    </view>
                </view>
            </view>
            <view class="px-19 pt-19">
                <view class="noticeCard">
                    <view class="flex a-center mb-4">
                        <image src="/static/image/ticket/notice.png" class="w-23 h-23 mr-15"></image>
                        <view class="txt">购票须知</view>
                    </view>
                    <view class="content">
                        {{ticketInfo.notice}}
                    </view>
                </view>
            </view>
            <view class="px-27 mt-34">
                <view class="flex a-center j-between mb-27">
                    <view class="touristTitle">游客信息</view>
                    <view class="need">需填写 <text style="color: rgba(25, 31, 63, 1);">{{num}}</text> 位游客</view>
                </view>
                <view class="visitorList">
                    <view class="visitor" v-for="(tourist, index) in touristList" :key="tourist.id || index">
                        <view class="flex a-center j-between mb-28">
                            <view class="flex a-center">
                                <view class="name">{{tourist.name}}</view>
                                <image @tap="editTourist(tourist)" src="/static/image/ticket/edit.png" class="w-23 h-23 ml-38">
                                </image>
                            </view>
                            <image @tap="deleteTourist(tourist)" src="/static/image/ticket/delete.png" class="w-28 h-27 ml-38">
                            </image>
                        </view>
                        <view class="flex a-center j-between">
                            <view class="idCard">身份证 {{formatIdCard(tourist.idCard)}}</view>
                            <view class="phone">电话 {{formatPhone(tourist.phone)}}</view>
                        </view>
                    </view>
                </view>
                <view class="flex a-center j-center mt-19" v-if="touristList.length < num">
                    <view class="add-visitor" @tap="addTourist()">
                        <image src="/static/image/ticket/addInfo.png" class="w-31 h-31 mr-13"></image>
                        <view class="add">添加游客信息</view>
                    </view>
                </view>
            </view>
            <view class="safe-card"></view>
            <view class="submit-info">
                <view class="flex a-center mb-38">
                    <image v-if="check" @tap.stop="check=!check" src="/static/image/ticket/checked.png"
                        class="w-34 h-34 mr-19"></image>
                    <image v-else @tap.stop="check=!check" src="/static/image/ticket/uncheck.png"
                        class="w-34 h-34 mr-19"></image>
                    <view class="flex a-center">
                        <text class="agree">阅读并同意</text>
                        <text class="aggreement" @tap="toAgreeMent(1)">《青城山票务预订条款》</text>
                        <text class="aggreement" @tap="toAgreeMent(2)">《用户隐私协议》</text>
                    </view>
                </view>
                <view class="flex a-center j-between">
                    <view class="flex a-center">
                        <view class="fs-38 lh-53 colorOrange">¥</view>
                        <view class="fs-57 lh-53 colorOrange">{{totalPrice}}</view>
                    </view>
                    <view class="sub-btn" @tap="submitOrder">提交订单</view>
                </view>
            </view>
        </view>
    </view>
</template>
<script setup lang="ts">
    import { onLoad } from "@dcloudio/uni-app";
    import { ref } from "vue";
    import { onLoad, onShow } from "@dcloudio/uni-app";
    import { ref, computed } from "vue";
    import { useStore } from "@/utils/store/index";
    const store = useStore();
    // 票信息
    const ticketInfo = ref({
        id: 1,
        title: '成人票',
        price: '20.00',
        validDate: '2025年12月31日',
        notice: '购票须知购票须知购票须知购票须知购票须知购票须知购票须知购票须知购票须知购票须知购票须知购票须知购票须知购票须知购票须知购票须知购票须知购票须知购票须知购票须知购票须知购票须知购票须知'
    });
    const num = ref(1)
    const check = ref(false)
    // 游客列表(在sure-order页面维护)
    const touristList = ref([])
    // 当前编辑的游客ID(用于区分是新增还是编辑)
    const editingTouristId = ref(null)
    const Back = () => {
        uni.navigateBack()
    // 计算总价
    const totalPrice = computed(() => {
        const price = parseFloat(ticketInfo.value.price) || 0;
        return (price * num.value).toFixed(2);
    });
    // 格式化身份证号(显示部分)
    const formatIdCard = (idCard: string) => {
        if (!idCard) return '';
        if (idCard.length <= 8) return idCard;
        return idCard.substring(0, 3) + '***********' + idCard.substring(idCard.length - 4);
    }
    // 格式化手机号(显示部分)
    const formatPhone = (phone: string) => {
        if (!phone) return '';
        if (phone.length !== 11) return phone;
        return phone.substring(0, 3) + '****' + phone.substring(7);
    }
    const add = () => {
        num.value++
    }
    const reduce = () => {
        if (num.value > 1) {
            num.value--
            // 如果减少数量后,游客数量超过票数量,需要提示
            if (touristList.value.length > num.value) {
                uni.showToast({
                    duration: 1500,
                    title: `请删除多余游客信息,当前需要${num.value}位游客`,
                    icon: 'none',
                    mask: true
                })
            }
        } else {
            uni.showToast({
                duration: 1500,
                title: '无法再减少了',
                icon: 'none',
                mask: true
            })
        }
    }
    const toAgreeMent = (type) => {
        // 跳转到协议页面,传递协议类型
        uni.navigateTo({
            url: `/pages/agreement/agreement?type=${type}`
        })
    }
    // 添加游客
    const addTourist = () => {
        // 检查是否已达到所需游客数量
        if (touristList.value.length >= num.value) {
            uni.showToast({
                duration: 1500,
                title: `最多只能添加${num.value}位游客`,
                icon: 'none',
                mask: true
            })
            return;
        }
        // 清空store中的游客信息,标记为新增模式
        store.clearTouristInfo();
        editingTouristId.value = null;
        uni.navigateTo({
            url: '/pages/tourist/tourist'
        })
    }
    // 编辑游客
    const editTourist = (tourist) => {
        if (!tourist) return;
        // 将游客信息放入store,供编辑页面使用
        store.setTouristInfo(tourist);
        editingTouristId.value = tourist.id;
        uni.navigateTo({
            url: `/pages/tourist/editTourist?id=${tourist.id}`
        })
    }
    // 删除游客
    const deleteTourist = (tourist) => {
        if (!tourist) return;
        uni.showModal({
            title: '提示',
            content: '确定要删除该游客信息吗?',
            success: (res) => {
                if (res.confirm) {
                    // 从列表中删除
                    touristList.value = touristList.value.filter(item => item.id !== tourist.id);
                }
            }
        })
    }
    // 处理从其他页面返回的游客信息
    const handleTouristReturn = () => {
        const touristInfo = store.getTouristInfo();
        if (touristInfo) {
            if (editingTouristId.value) {
                // 编辑模式:更新现有游客信息
                const index = touristList.value.findIndex(item => item.id === editingTouristId.value);
                if (index !== -1) {
                    // 如果没有id,使用原来的id
                    if (!touristInfo.id) {
                        touristInfo.id = editingTouristId.value;
                    }
                    touristList.value[index] = { ...touristInfo };
                }
                editingTouristId.value = null;
            } else {
                // 新增模式:添加到列表
                // 如果没有id,生成一个临时id
                if (!touristInfo.id) {
                    touristInfo.id = Date.now() + Math.random();
                }
                // 检查是否已存在(根据身份证号)
                const exists = touristList.value.find(item => item.idCard === touristInfo.idCard);
                if (!exists) {
                    touristList.value.push({ ...touristInfo });
                } else {
                    uni.showToast({
                        duration: 1500,
                        title: '该游客已添加',
                        icon: 'none',
                        mask: true
                    })
                }
            }
        }
    }
    // 提交订单
    const submitOrder = () => {
        // 检查是否同意协议
        if (!check.value) {
            uni.showToast({
                duration: 1500,
                title: '请先阅读并同意相关协议',
                icon: 'none',
                mask: true
            })
            return;
        }
        // 检查游客数量是否匹配
        if (touristList.value.length !== num.value) {
            uni.showToast({
                duration: 1500,
                title: `请添加${num.value}位游客信息`,
                icon: 'none',
                mask: true
            })
            return;
        }
        // 检查游客信息是否完整
        for (let i = 0; i < touristList.value.length; i++) {
            const tourist = touristList.value[i];
            if (!tourist.name || !tourist.phone || !tourist.idCard) {
                uni.showToast({
                    duration: 1500,
                    title: `第${i + 1}位游客信息不完整`,
                    icon: 'none',
                    mask: true
                })
                return;
            }
        }
        // 构建订单数据
        const orderData = {
            ticketInfo: ticketInfo.value,
            quantity: num.value,
            totalPrice: totalPrice.value,
            touristList: touristList.value,
            agreeProtocol: check.value
        };
        console.log('提交订单', orderData);
        // 这里可以调用API提交订单
        // 提交成功后,清理store中的游客信息
        store.clearTouristInfo();
        editingTouristId.value = null;
        uni.showToast({
            duration: 1500,
            title: '订单提交成功',
            icon: 'success',
            mask: true
        })
        // 可以跳转到订单详情或订单列表
        // uni.navigateTo({
        //     url: '/pages/orderDetail/orderDetail'
        // })
    }
    onLoad((params) => {
        // 如果从其他页面传入了票信息,可以在这里接收
        if (params.ticketId) {
            // 可以根据ticketId获取票信息
            // ticketInfo.value = getTicketInfo(params.ticketId);
        }
    });
    // 页面显示时处理从其他页面返回的游客信息
    onShow(() => {
        handleTouristReturn();
    });
</script>
@@ -37,4 +345,167 @@
        padding-bottom: constant(safe-area-inset-bottom);
        padding-bottom: env(safe-area-inset-bottom);
    }
    .orderInfo {
        background-image: url('/static/image/ticket/orderInfoBg.png');
        background-size: 100% 100%;
        padding: 36rpx 40rpx 32rpx 40rpx;
        .title {
            font-weight: 600;
            font-size: 46rpx;
            color: #303133;
            line-height: 63rpx;
        }
        .time {
            font-weight: 500;
            font-size: 23rpx;
            color: rgba(22, 19, 19, 0.65);
            line-height: 33rpx;
        }
        .num {
            font-weight: 600;
            font-size: 31rpx;
            color: rgba(0, 0, 0, 0.85);
            line-height: 42rpx;
            margin: 0 31rpx;
        }
        .priceText {
            font-weight: 500;
            font-size: 27rpx;
            color: rgba(22, 19, 19, 0.65);
            line-height: 38rpx;
        }
        .priceNum {
            font-weight: 600;
            font-size: 38rpx;
            color: #FF6257;
            line-height: 54rpx;
        }
    }
    .noticeCard {
        background: linear-gradient(270deg, rgba(247, 252, 247, 0) 0%, #ECF8ED 100%);
        border-radius: 19rpx;
        padding: 27rpx;
        .txt {
            font-weight: 600;
            font-size: 27rpx;
            color: #00AD72;
            line-height: 38rpx;
        }
        .content {
            font-weight: 500;
            font-size: 23rpx;
            color: #00AD72;
            line-height: 35rpx;
        }
    }
    .touristTitle {
        font-weight: 600;
        font-size: 31rpx;
        color: #191F3F;
        line-height: 42rpx;
    }
    .need {
        font-weight: 500;
        font-size: 23rpx;
        color: #8E92AA;
        line-height: 33rpx;
    }
    .visitorList {
        .visitor {
            padding: 27rpx;
            margin-bottom: 19rpx;
            background: linear-gradient(128deg, #FDFEFF 0%, #F4F8FF 100%);
            border-radius: 19rpx;
            border: 2rpx solid #F0F7FF;
            .name {
                font-weight: 600;
                font-size: 27rpx;
                color: #303133;
                line-height: 27rpx;
            }
            .idCard {
                font-weight: 500;
                font-size: 23rpx;
                color: rgba(0, 0, 0, 0.45);
                line-height: 33rpx;
            }
        }
    }
    .add-visitor {
        background: rgba(6, 197, 132, 0.1);
        border-radius: 58rpx;
        padding: 12rpx 62rpx;
        display: flex;
        align-items: center;
        .add {
            font-weight: 600;
            font-size: 23rpx;
            color: #000000;
            line-height: 33rpx;
        }
    }
    .safe-card {
        height: 238rpx;
    }
    .submit-info {
        padding: 27rpx 27rpx 40rpx 27rpx;
        position: fixed;
        bottom: 0;
        left: 0;
        width: 100vw;
        background: #FFFFFF;
        box-shadow: 0rpx -8rpx 15rpx 0rpx rgba(0, 0, 0, 0.06);
        .agree {
            font-weight: 500;
            font-size: 23rpx;
            color: #333333;
            line-height: 23rpx;
        }
        .aggreement {
            font-weight: 600;
            font-size: 23rpx;
            color: #06C584;
            line-height: 23rpx;
        }
        .colorOrange {
            color: rgba(255, 98, 87, 1);
        }
        .sub-btn {
            width: 387rpx;
            height: 96rpx;
            background: linear-gradient(270deg, #08C866 0%, #06C584 100%);
            box-shadow: 0rpx 4rpx 25rpx 0rpx rgba(6, 197, 132, 0.15), 0rpx 8rpx 19rpx 0rpx rgba(6, 197, 132, 0.19);
            border-radius: 67rpx;
            font-weight: 600;
            font-size: 35rpx;
            color: #FFFFFF;
            line-height: 96rpx;
            text-shadow: 0px 4px 25px rgba(6, 197, 132, 0.15);
            text-align: center;
        }
    }
</style>
miniprogram/pages/ticket/ticket.vue
@@ -9,10 +9,13 @@
                        <image v-if="activeDate==item.date" src="/static/image/ticket/active.png" class="active-date" />
                    </view>
                </view>
                <view class="choose-date">
                    <view>全部日期</view>
                    <image src="/static/image/ticket/more.png" class="w-13 h-7 mt-17" />
                </view>
                <wd-calendar :showPanelTitle="false" v-model="value" @confirm="handleConfirm">
                    <view class="choose-date">
                        <view>全部日期</view>
                        <image src="/static/image/ticket/more.png" class="w-13 h-7 mt-17" />
                    </view>
                </wd-calendar>
            </view>
            <view class="time-card">
                <view class="time-item" v-for="(item,index) in timeList" :key="index"
@@ -56,8 +59,53 @@
<script setup lang="ts">
    import { ref, reactive } from "vue";
    import { onLoad, onUnload, onShow, onReachBottom } from "@dcloudio/uni-app";
    const dateList = ref([{ date: '12-12', week: '今天' }, { date: '12-13', week: '今天' }, { date: '12-14', week: '今天' }, { date: '12-15', week: '今天' }, { date: '12-16', week: '今天' }])
    const activeDate = ref('12-13')
    // 格式化日期为 MM-DD
    const formatDate = (timestamp: number): string => {
        const date = new Date(timestamp);
        const month = String(date.getMonth() + 1).padStart(2, '0');
        const day = String(date.getDate()).padStart(2, '0');
        return `${month}-${day}`;
    }
    // 根据时间戳获取星期文本
    const getWeekText = (timestamp: number): string => {
        const today = new Date();
        const targetDate = new Date(timestamp);
        // 重置时间为0点,只比较日期
        today.setHours(0, 0, 0, 0);
        targetDate.setHours(0, 0, 0, 0);
        const diffTime = targetDate.getTime() - today.getTime();
        const diffDays = Math.floor(diffTime / (1000 * 60 * 60 * 24));
        if (diffDays === 0) {
            return '今天';
        } else if (diffDays === 1) {
            return '明天';
        } else {
            const weekDays = ['周日', '周一', '周二', '周三', '周四', '周五', '周六'];
            return weekDays[targetDate.getDay()];
        }
    }
    // 根据时间戳生成日期列表(当天+后4天)
    const generateDateList = (startTimestamp: number): Array<{ date: string; week: string; timestamp: number }> => {
        const list: Array<{ date: string; week: string; timestamp: number }> = [];
        for (let i = 0; i < 5; i++) {
            const timestamp = startTimestamp + i * 24 * 60 * 60 * 1000;
            list.push({
                date: formatDate(timestamp),
                week: getWeekText(timestamp),
                timestamp: timestamp
            });
        }
        return list;
    }
    const dateList = ref(generateDateList(Date.now()))
    const activeDate = ref(dateList.value[0].date)
    const timeList = ref(['08:00-08:30', '09:00-09:30', '10:00-10:30', '11:00-11:30', '12:00-12:30', '13:00-13:30'])
    const activeTime = ref('09:00-09:30')
    const ticketList = ref([
@@ -104,6 +152,7 @@
            residue: 300,
        }
    ])
    const value = ref<number>(Date.now())
    const changeDate = (e) => {
        activeDate.value = e.date
    }
@@ -114,6 +163,12 @@
        uni.navigateTo({
            url: '/pages/book-notice/book-notice'
        })
    }
    const handleConfirm = ({ value }: { value: number }) => {
        // 根据选择的时间戳生成日期列表
        dateList.value = generateDateList(value);
        // 设置第一个日期为选中状态
        activeDate.value = dateList.value[0].date;
    }
    const toDetail = () => {
        uni.navigateTo({
@@ -292,7 +347,6 @@
                color: #8C8C8C;
                line-height: 38rpx;
                text-align: center;
                z-index: 99;
                background-image: url(/static/image/ticket/numBg.png);
                background-size: 100% 100%;
            }
miniprogram/pages/tourist/editTourist.vue
@@ -45,7 +45,9 @@
<script setup lang="ts">
import { ref, reactive } from "vue";
import { onLoad } from "@dcloudio/uni-app";
import { useStore } from "@/utils/store/index";
const store = useStore();
const uFormRef = ref();
const form = reactive({
    name: '',
@@ -83,7 +85,16 @@
function submit() {
    uFormRef.value?.validate((valid: boolean) => {
        if (valid) {
            console.log('验证通过');
            // 将游客信息存到store
            const touristData = {
                id: id.value || Date.now() + Math.random(),
                name: form.name,
                phone: form.phone,
                idCard: form.idCard
            };
            store.setTouristInfo(touristData);
            // 返回上一页
            uni.navigateBack();
        } else {
            console.log('验证失败');
        }
@@ -91,7 +102,13 @@
}
onLoad((options) => {
    id.value = options.id;
    id.value = options.id || '';
    // 如果是编辑模式,从store中获取游客信息
    if (id.value && store.touristInfo) {
        form.name = store.touristInfo.name || '';
        form.phone = store.touristInfo.phone || '';
        form.idCard = store.touristInfo.idCard || '';
    }
})
</script>
<style>
miniprogram/pages/tourist/tourist.vue
@@ -5,10 +5,10 @@
            <text>添加游客信息</text>
        </view>
        <view class="list">
            <view v-for="(item, index) in list" :key="index" class="item">
            <view v-for="(item, index) in list" :key="index" class="item" @click="selectTourist(item)">
                <view class="flex a-center">
                    <view class="name">{{ item.name }}</view>
                    <image src="../../static/image/mine/edit.png" class="w-23 h-23 ml-38" @click="toAddTourist(item.id)"></image>
                    <image src="../../static/image/mine/modify.png" class="w-23 h-23 ml-38" @click.stop="toAddTourist(item.id)"></image>
                </view>
                <view class="flex a-center j-between info">
                    <view>身份证 {{ item.idCard }}</view>
@@ -23,22 +23,40 @@
<script setup lang="ts">
import { ref } from "vue";
import { useStore } from "@/utils/store/index";
const store = useStore();
const list = ref([
    {
        id: 1,
        name: '张三',
        phone: '138****0000',
        idCard: '440*********001X',
        phone: '13812340000',
        idCard: '440123199001011001',
        isDefault: true,
    },
    {
        id: 2,
        name: '李四',
        phone: '138****0000',
        idCard: '440*********002X',
        phone: '13812340001',
        idCard: '440123199001011002',
        isDefault: false,
    }
])
// 选择游客
const selectTourist = (tourist: any) => {
    // 将选中的游客信息存到store
    store.setTouristInfo({
        id: tourist.id,
        name: tourist.name,
        phone: tourist.phone,
        idCard: tourist.idCard
    });
    // 返回上一页
    uni.navigateBack();
}
const toAddTourist = (id?: any) => {
    uni.navigateTo({
        url: '/pages/tourist/editTourist?id=' + id,
miniprogram/static/image/good/add.png
miniprogram/static/image/good/bg.png
miniprogram/static/image/mine/arrowRight.png
miniprogram/static/image/mine/modify.png
miniprogram/static/image/ticket/orderInfoBg.png
miniprogram/static/image/ticket/uncheck.png
miniprogram/utils/store/index.js
@@ -3,12 +3,36 @@
export const useStore = defineStore("store", () => {
  
  const currentIndex = ref(0);
  // 单个游客信息(用于页面间传递,如添加或编辑游客时)
  const touristInfo = ref(null);
  const setCurrentIndex = (index) => {
    currentIndex.value = index;
  }
  // 设置游客信息(用于添加或编辑时传递)
  const setTouristInfo = (tourist) => {
    touristInfo.value = tourist ? { ...tourist } : null;
  }
  // 获取游客信息并清空
  const getTouristInfo = () => {
    const info = touristInfo.value;
    touristInfo.value = null;
    return info;
  }
  // 清空游客信息
  const clearTouristInfo = () => {
    touristInfo.value = null;
  }
  return {
    currentIndex,
    setCurrentIndex,
    touristInfo,
    setTouristInfo,
    getTouristInfo,
    clearTouristInfo,
  };
});