绿满眶商城微信小程序-uniapp
peng
2025-09-08 700e7d3bc6cec38610b2ee85139c4d6506102ff6
pages/ActivityPopup/ActivityPopup.vue
@@ -14,15 +14,43 @@
      </view>
      
      <!-- 活动图片 -->
      <view class="activity-img">
        <image :src="activityImage" mode="widthFix" class="popup-img"></image>
      <scroll-view
        scroll-y="true"
        class="activity-img-scroll"
        :show-scrollbar="false"
        :enhanced="true">
        <view class="activity-img">
          <image
            :src="activityImage"
            mode="widthFix"
            class="popup-img"
            :style="{ width: '100%' }"
            @load="onImageLoad"
            @error="onImageError">
          </image>
        </view>
      </scroll-view>
      <!-- 活动标题(固定显示) -->
      <view class="activity-title-fixed">
        <h3 class="activity-title">{{ activityTitle }}</h3>
      </view>
      
      <!-- 活动信息 -->
      <view class="activity-info">
        <h3 class="activity-title">{{ activityTitle }}</h3>
        <p class="activity-desc">{{ activityDesc }}</p>
      <!-- 可滚动的活动描述 -->
      <scroll-view
        scroll-y="true"
        class="activity-content-scroll"
        :show-scrollbar="false"
        :enhanced="true">
        
        <view class="activity-content">
          <p class="activity-desc">{{ activityDesc }}</p>
        </view>
      </scroll-view>
      <!-- 固定底部:倒计时和参与按钮 -->
      <view class="activity-bottom">
        <!-- 倒计时(如果需要) -->
        <view class="countdown" v-if="showCountdown">
          <text class="countdown-text">活动剩余时间:</text>
@@ -100,14 +128,28 @@
      hours: '00',
      minutes: '00',
      seconds: '00',
      countdownTimer: null
      countdownTimer: null,
      // 图片相关数据
      imageWidth: 600, // 动态计算的宽度(rpx)
      imageHeight: 300, // 动态计算的高度(rpx)
      originalImageWidth: 0, // 原图宽度(px)
      originalImageHeight: 0, // 原图高度(px)
      containerWidth: 600, // 弹窗容器宽度(rpx)
      maxImageHeight: 500 // 图片最大高度限制(rpx)
    };
  },
  watch: {
    show(newVal) {
      console.log("弹窗监听变化",newVal)
      if (newVal && this.showCountdown) {
        this.startCountdown();
      if (newVal) {
        // 弹窗显示时重新获取容器宽度并计算图片尺寸
        this.$nextTick(() => {
          this.getContainerWidth();
        });
        if (this.showCountdown) {
          this.startCountdown();
        }
      } else if (!newVal && this.countdownTimer) {
        clearInterval(this.countdownTimer);
        this.countdownTimer = null;
@@ -117,9 +159,77 @@
  mounted() {
      console.log('组件已挂载,此时可以访问 props 和 DOM');
      console.log('当前 show 状态:', this.show); // 可以打印 props 中的 show
      // 获取容器宽度
      this.getContainerWidth();
   },
  methods: {
    // 获取容器宽度
    getContainerWidth() {
      this.$nextTick(() => {
        // 创建查询对象
        const query = uni.createSelectorQuery().in(this);
        query.select('.popup-content').boundingClientRect((data) => {
          if (data && data.width) {
            // 将px转换为rpx(考虑设备像素比)
            const systemInfo = uni.getSystemInfoSync();
            const screenWidth = systemInfo.screenWidth;
            const rpxRatio = 750 / screenWidth; // rpx与px的转换比例
            this.containerWidth = Math.round(data.width * rpxRatio);
            console.log(`容器宽度获取成功: ${data.width}px -> ${this.containerWidth}rpx`);
            // 如果图片已经加载,重新计算尺寸
            if (this.originalImageWidth > 0 && this.originalImageHeight > 0) {
              this.calculateImageSize();
            }
          } else {
            console.warn('无法获取容器宽度,使用默认值');
            this.containerWidth = 600; // 默认宽度
          }
        }).exec();
      });
    },
    // 图片加载完成事件
    onImageLoad(e) {
      console.log('图片加载完成', e.detail);
      // 获取图片原始尺寸
      this.originalImageWidth = e.detail.width;
      this.originalImageHeight = e.detail.height;
      // 计算等比例缩放后的尺寸
      this.calculateImageSize();
    },
    // 图片加载失败事件
    onImageError(e) {
      console.error('图片加载失败', e.detail);
      // 设置默认尺寸
      this.imageWidth = this.containerWidth;
      this.imageHeight = 300;
    },
    // 计算图片等比例缩放尺寸
    calculateImageSize() {
      if (this.originalImageWidth > 0 && this.originalImageHeight > 0) {
        // 计算图片的宽高比
        const imageRatio = this.originalImageHeight / this.originalImageWidth;
        // 图片使用100%宽度填充容器,widthFix模式会自动计算高度
        this.imageWidth = this.containerWidth;
        this.imageHeight = Math.round(this.imageWidth * imageRatio);
        console.log(`图片尺寸计算完成:`);
        console.log(`- 原始尺寸: ${this.originalImageWidth}px × ${this.originalImageHeight}px`);
        console.log(`- 计算尺寸: ${this.imageWidth}rpx × ${this.imageHeight}rpx`);
        console.log(`- 容器宽度: ${this.containerWidth}rpx`);
        console.log(`- 宽高比: ${imageRatio.toFixed(3)}`);
        console.log(`- 实际显示: 宽度100%,高度自适应,无高度限制`);
      }
    },
     onpan(){
        
     },
@@ -230,6 +340,7 @@
.popup-content {
  width: 100%;
  max-width: 600rpx;
  max-height: 85vh; /* 提高最大高度限制,给图片更多空间 */
  background-color: #ffffff;
  border-radius: 24rpx;
  box-shadow: 0 10rpx 30rpx rgba(0, 0, 0, 0.2);
@@ -237,6 +348,8 @@
  transform: translateY(50rpx) scale(0.9);
  opacity: 0;
  transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
  display: flex;
  flex-direction: column; /* 竖向布局 */
}
.content-enter {
@@ -247,6 +360,32 @@
.content-leave {
  transform: translateY(50rpx) scale(0.9);
  opacity: 0;
}
/* 活动标题固定区域 */
.activity-title-fixed {
  padding: 30rpx 30rpx 20rpx 30rpx;
  background-color: #ffffff;
  border-bottom: 1rpx solid #f5f5f5;
}
/* 活动内容滚动区域 */
.activity-content-scroll {
  flex: 1; /* 占据剩余空间 */
  min-height: 0; /* 重要:确保 flex 子元素可以收缩 */
  max-height: 150rpx; /* 适当减少活动内容区域的最大高度,给图片更多空间 */
}
/* 活动内容 */
.activity-content {
  padding: 30rpx 30rpx 20rpx 30rpx;
}
/* 固定底部区域 */
.activity-bottom {
  padding: 20rpx 30rpx 30rpx 30rpx;
  background-color: #ffffff;
  border-top: 1rpx solid #f5f5f5; /* 添加分割线 */
}
/* 关闭按钮 */
@@ -264,41 +403,49 @@
  z-index: 10;
}
/* 活动图片滚动区域 */
.activity-img-scroll {
    max-height: 50vh; /* 限制图片区域最大高度为屏幕的50% */
    width: 100%;
    border-top-left-radius: 24rpx;
    border-top-right-radius: 24rpx;
    overflow: hidden;
}
/* 活动图片 */
.activity-img {
    position: relative;
    width: 100%; /* 容器宽度铺满弹窗内容区 */
    display: block; /* 改为block确保完全填充宽度 */
    /* 可选:添加背景色,避免图片加载前显示空白 */
    background-color: #f5f5f5;
    border-top-left-radius: 24rpx; /* 与图片圆角一致,避免容器露白 */
    border-top-right-radius: 24rpx;
}
.popup-img {
   width: 100%;
   /* 核心:用 max-height 限制最大高度,不限制 min-height(保留比例) */
   max-height: 300rpx; /* 图片最大高度(超过则按比例缩小,保证完整显示) */
    display: block;
    width: 100%; /* 确保图片宽度完全填充容器 */
    border-top-left-radius: 24rpx;
    border-top-right-radius: 24rpx;
    /* 使用 widthFix 模式,让图片根据设定的宽度自动计算高度 */
    /* 图片尺寸通过动态计算的style控制 */
}
/* 活动信息 */
.activity-info {
  padding: 30rpx;
  text-align: center;
}
.activity-title {
  font-size: 32rpx;
  font-weight: bold;
  color: #333333;
  margin-bottom: 20rpx;
  line-height: 1.3;
  text-align: center;
}
.activity-desc {
  font-size: 26rpx;
  color: #666666;
  margin-bottom: 30rpx;
  line-height: 1.5;
  text-align: left; /* 左对齐 */
  text-indent: 2em; /* 首行缩进两个字符 */
}
/* 倒计时样式 */