img

目录

  • 案例介绍
  • 代码实现
  • 代码详解
  • 状态管理
  • 预览触发实现
  • 预览界面实现
  • 总结

案例介绍

在图片墙应用中,大图预览是一个重要的功能,它允许用户查看图片的完整细节。本案例将展示如何实现图片的大图预览功能,包括预览界面和相关操作。

代码实现

@Entry
@Component
struct PhotoAlbumPage {
  @State showDetail: boolean = false
  @State selectedPhoto: string = ''
  @State screenWidth: number = 0
  
  // 照片数据
  private photos: Map<string, string[]> = new Map([
    ['全部', [
      '/assets/photo1.jpg',
      '/assets/photo2.jpg',
      '/assets/photo3.jpg',
      '/assets/photo4.jpg'
    ]]
  ])

  build() {
    Stack({ alignContent: Alignment.Center }) {
      Column() {
        // 图片墙
        Scroll() {
          Flow() {
            ForEach(this.photos.get('全部'), (photo: string) => {
              FlowItem() {
                Image(photo)
                  .width(this.getPhotoWidth())
                  .height(this.getPhotoWidth())
                  .objectFit(ImageFit.Cover)
                  .borderRadius(8)
                  .onClick(() => {
                    this.selectedPhoto = photo
                    this.showDetail = true
                  })
              }
              .margin(4)
            })
          }
          .width('100%')
          .padding(4)
        }
        .width('100%')
        .layoutWeight(1)
      }
      .width('100%')
      .height('100%')
      
      // 大图查看弹窗
      if (this.showDetail) {
        Column() {
          // 顶部操作栏
          Flex({ justifyContent: FlexAlign.SpaceBetween, alignItems: ItemAlign.Center }) {
            Image('/assets/close.png')
              .width(24)
              .height(24)
              .onClick(() => {
                this.showDetail = false
              })
            
            Row() {
              Image('/assets/share.png')
                .width(24)
                .height(24)
                .margin({ right: 20 })
              
              Image('/assets/download.png')
                .width(24)
                .height(24)
            }
          }
          .width('100%')
          .height(50)
          .padding({ left: 15, right: 15 })
          
          // 大图
          Image(this.selectedPhoto)
            .width('100%')
            .layoutWeight(1)
            .objectFit(ImageFit.Contain)
          
          // 底部操作栏
          Flex({ justifyContent: FlexAlign.SpaceAround, alignItems: ItemAlign.Center }) {
            Image('/assets/like.png')
              .width(24)
              .height(24)
            
            Image('/assets/comment.png')
              .width(24)
              .height(24)
            
            Image('/assets/edit.png')
              .width(24)
              .height(24)
            
            Image('/assets/delete.png')
              .width(24)
              .height(24)
          }
          .width('100%')
          .height(60)
          .padding({ left: 15, right: 15 })
        }
        .width('100%')
        .height('100%')
        .backgroundColor(Color.Black)
      }
    }
    .width('100%')
    .height('100%')
  }

  // 计算图片宽度
  private getPhotoWidth(): number {
    const margin = 4
    const columns = this.screenWidth <= 320 ? 2 : (this.screenWidth <= 600 ? 3 : 4)
    return (this.screenWidth - (columns + 1) * margin * 2) / columns
  }
}

代码详解

状态管理

  1. 预览相关状态:
    @State showDetail: boolean = false
    @State selectedPhoto: string = ''
    
    • showDetail控制预览弹窗的显示
    • selectedPhoto记录当前选中的照片

预览触发实现

  1. 图片点击事件:
    Image(photo)
      .onClick(() => {
        this.selectedPhoto = photo
        this.showDetail = true
      })
    
    • 点击图片时记录选中的照片
    • 显示预览弹窗

预览界面实现

  1. 布局结构:

    Stack({ alignContent: Alignment.Center }) {
      Column() {
        // 图片墙内容
      }
      
      if (this.showDetail) {
        Column() {
          // 预览界面内容
        }
      }
    }
    
    • 使用Stack实现预览界面的覆盖效果
    • 通过条件渲染控制预览界面的显示
  2. 预览界面组成:

    Column() {
      // 顶部操作栏
      Flex() {
        // 关闭按钮
        // 分享和下载按钮
      }
      
      // 大图显示
      Image(this.selectedPhoto)
        .width('100%')
        .layoutWeight(1)
        .objectFit(ImageFit.Contain)
      
      // 底部操作栏
      Flex() {
        // 点赞、评论、编辑、删除按钮
      }
    }
    
    • 顶部操作栏:包含关闭、分享、下载按钮
    • 中间显示大图,使用Contain模式保持比例
    • 底部操作栏:包含常用操作按钮
  3. 关闭预览:

    Image('/assets/close.png')
      .onClick(() => {
        this.showDetail = false
      })
    
    • 点击关闭按钮隐藏预览界面

总结

本案例展示了如何在图片墙中实现大图预览功能。通过Stack布局和条件渲染,实现了预览界面的覆盖效果。预览界面的设计包含了完整的操作功能,提供了良好的用户体验。合理的状态管理确保了预览功能的正常工作,使用户能够方便地查看和操作图片。

Logo

讨论HarmonyOS开发技术,专注于API与组件、DevEco Studio、测试、元服务和应用上架分发等。

更多推荐