HarmonyOS ArkUI Image组件完全指南:从入门到精通

本文基于 HarmonyOS NEXT(API 23+)开发环境,全面讲解 ArkUI Image 组件的使用方法,帮助开发者快速掌握图片加载、裁剪、缩放及高级技巧。


效果

一、前言

在移动端应用开发中,图片展示是最基础也最重要的UI能力之一。HarmonyOS ArkUI 提供了功能强大的 Image 组件,支持本地资源加载、网络图片加载、多种缩放模式、圆角裁剪、SVG渲染等丰富特性。

本文将从基础到进阶,通过大量代码示例,带你全面掌握 Image 组件的使用。


二、Image 组件基础

2.1 基本语法

Image(src: PixelMap | ResourceStr)

Image 组件接收一个图片源参数,支持以下类型:

参数类型 说明 示例
Resource 应用资源引用 $r('app.media.logo')
string 网络URL或本地路径 'https://example.com/img.png'
PixelMap 像素图对象 通过 ImageKit 解码得到

2.2 加载本地资源图片

将图片放入 src/main/resources/base/media/ 目录,通过 $r() 引用:

@Entry
@Component
struct ImageBasicDemo {
  build() {
    Column({ space: 20 }) {
      // 加载 media 目录下的图片
      Image($r('app.media.app_logo'))
        .width(200)
        .height(200)
    }
    .width('100%')
    .height('100%')
    .justifyContent(FlexAlign.Center)
  }
}

2.3 加载网络图片

直接传入URL字符串即可加载网络图片,Image组件会自动异步下载并缓存:

Image('https://images.example.com/banner.jpg')
  .width('100%')
  .height(250)
  .objectFit(ImageFit.Cover)

注意:网络图片需要在 module.json5 中声明 ohos.permission.INTERNET 权限。


三、核心属性详解

3.1 图片缩放模式(objectFit)

objectFit 控制图片在容器中的缩放方式,是最常用的属性之一:

Image($r('app.media.photo'))
  .width(200)
  .height(200)
  .objectFit(ImageFit.Cover)  // 裁剪填满
枚举值 效果说明
ImageFit.Contain 保持宽高比缩放,确保图片完全显示(默认值)
ImageFit.Cover 保持宽高比缩放,填满容器,可能裁剪
ImageFit.Fill 拉伸填满容器,不保持宽高比
ImageFit.None 保持原始尺寸显示
ImageFit.ScaleDown 图片大于容器时按Contain缩放,小于时保持原始尺寸
ImageFit.Auto 根据图片原始尺寸自动选择

3.2 图片位置(objectRepeat)

设置图片的重复方式:

Image($r('app.media.pattern'))
  .width('100%')
  .height(300)
  .objectRepeat({ x: ImageRepeat.NoRepeat, y: ImageRepeat.NoRepeat })

3.3 圆角与裁剪

Column({ space: 20 }) {
  // 统一圆角
  Image($r('app.media.avatar'))
    .width(100)
    .height(100)
    .borderRadius(50)  // 圆形头像

  // 不同角设置不同圆角
  Image($r('app.media.card_bg'))
    .width('100%')
    .height(200)
    .borderRadius({
      topLeft: 16,
      topRight: 16,
      bottomLeft: 0,
      bottomRight: 0
    })
}

3.4 替代内容(alt)

当图片加载失败时显示替代内容:

Image('https://invalid-url.com/image.png')
  .width(200)
  .height(200)
  .alt($r('app.media.placeholder'))  // 加载失败时显示占位图
  .objectFit(ImageFit.Contain)

3.5 插值效果(interpolation)

控制图片缩放时的插值算法,影响画质:

Image($r('app.media.photo'))
  .width(300)
  .height(300)
  .interpolation(ImageInterpolation.High)  // 高质量插值
枚举值 说明
ImageInterpolation.None 不使用插值
ImageInterpolation.Low 低质量快速插值
ImageInterpolation.Medium 中等质量插值
ImageInterpolation.High 高质量插值(适合放大场景)

四、事件回调

4.1 加载完成(onComplete)

Image($r('app.media.large_photo'))
  .width('100%')
  .height(300)
  .onComplete((event) => {
    if (event) {
      console.info(`图片加载成功: ${event.width} x ${event.height}`);
    }
  })

4.2 加载错误(onError)

Image('https://example.com/photo.png')
  .width(200)
  .height(200)
  .onError((event) => {
    console.error(`图片加载失败,错误码: ${event.error}`);
  })

五、实战示例:图片画廊卡片

下面通过一个完整的示例,综合演示 Image 组件的各项能力:

@Entry
@Component
struct ImageGalleryDemo {
  @State imageList: string[] = [
    'https://picsum.photos/400/300?random=1',
    'https://picsum.photos/400/300?random=2',
    'https://picsum.photos/400/300?random=3'
  ];
  @State currentIndex: number = 0;

  build() {
    Column() {
      // 标题
      Text('图片画廊')
        .fontSize(24)
        .fontWeight(FontWeight.Bold)
        .margin({ top: 20, bottom: 16 });

      // 主图展示区
      Stack() {
        Image(this.imageList[this.currentIndex])
          .width('100%')
          .height(280)
          .objectFit(ImageFit.Cover)
          .borderRadius(16)
          .alt($r('app.media.placeholder'))
          .animation({ duration: 300, curve: Curve.EaseInOut });

        // 图片序号标签
        Text(`${this.currentIndex + 1} / ${this.imageList.length}`)
          .fontSize(12)
          .fontColor(Color.White)
          .padding({ left: 8, right: 8, top: 4, bottom: 4 })
          .borderRadius(8)
          .backgroundColor('#80000000')
          .position({ right: 12, bottom: 12 });
      }
      .width('90%')

      // 缩略图列表
      Row({ space: 12 }) {
        ForEach(this.imageList, (url: string, index: number) => {
          Image(url)
            .width(80)
            .height(60)
            .objectFit(ImageFit.Cover)
            .borderRadius(8)
            .border({
              width: index === this.currentIndex ? 2 : 0,
              color: '#4361ee'
            })
            .onClick(() => {
              this.currentIndex = index;
            })
        }, (url: string, index: number) => `${index}`)
      }
      .margin({ top: 20 })
    }
    .width('100%')
    .height('100%')
  }
}

示例要点解析:

  1. 网络图片加载:使用URL字符串直接加载网络图片
  2. objectFit 裁剪ImageFit.Cover 确保图片填满容器且保持比例
  3. 圆角效果borderRadius(16) 实现圆角卡片
  4. 动态切换:通过 @State 状态变量驱动图片切换动画
  5. 边框高亮:选中状态使用 border 属性标记

六、SVG 图片支持

ArkUI 的 Image 组件原生支持 SVG 格式,可以直接加载 .svg 文件:

// 加载 SVG 资源
Image($r('app.media.ic_arrow_back'))
  .width(24)
  .height(24)
  .fillColor('#ffffff')  // 修改 SVG 填充颜色

fillColor 属性可以动态修改 SVG 图标的颜色,非常适合深色/浅色主题适配。


七、最佳实践总结

场景 推荐做法
头像展示 borderRadius('50%') + objectFit(ImageFit.Cover)
轮播图/Banner objectFit(ImageFit.Cover) + 固定高度
图标按钮 SVG 资源 + fillColor 适配主题
加载失败兜底 alt() 设置占位图 + onError 日志
大图展示 interpolation(ImageInterpolation.High) 提升画质
性能优化 使用合适的图片尺寸,避免加载过大的原始图片

八、总结

Image 组件是 ArkUI 中最常用的基础组件之一,掌握其核心属性和使用模式对于开发高质量应用至关重要。本文覆盖了图片加载、缩放、裁剪、事件处理等关键知识点,并通过实战示例展示了综合应用场景。

关键要点回顾:

  • 使用 $r() 加载本地资源,URL字符串加载网络图片
  • objectFit 控制缩放模式,CoverContain 最常用
  • borderRadius 实现圆角和圆形裁剪
  • alt 提供加载失败的兜底展示
  • SVG 图标使用 fillColor 适配主题色
Logo

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

更多推荐