温馨提示:本篇博客的详细代码已发布到 git : https://gitcode.com/nutpi/HarmonyosNext 可以下载运行哦!

HarmonyOS NEXT Layout布局组件系统详解(十):实际应用案例

效果演示

1. 实际应用案例概述

在前面的文章中,我们详细介绍了HarmonyOS Layout布局组件系统的各个方面,包括基础概念、AutoRow和AutoCol组件、间距处理、对齐方式、偏移功能、响应式设计、自定义样式和嵌套布局等。本文将通过实际应用案例,展示如何在实际项目中综合运用这些知识,帮助开发者更好地理解和应用HarmonyOS的布局系统。

2. 常见页面布局实现

2.1 经典三段式布局

三段式布局是最常见的页面结构,包括顶部导航栏、中间内容区和底部导航/信息栏:

AutoRow() {
    // 顶部导航栏
    AutoCol({ span: 12 }) {
        Row() {
            Text('Logo').fontSize(20).fontWeight(FontWeight.Bold)
            Blank()
            Text('菜单').margin({ right: 20 })
            Text('用户').margin({ right: 20 })
            Text('设置')
        }
        .width('100%')
        .height(60)
        .padding({ left: 20, right: 20 })
        .backgroundColor('#1890ff')
        .justifyContent(FlexAlign.SpaceBetween)
    }
    
    // 中间内容区
    AutoCol({ span: 12 }) {
        // 使用嵌套布局实现内容区的复杂结构
        AutoRow({ gutter: [16, 16], autoMargin: { top: 16, bottom: 16 } }) {
            // 左侧边栏
            AutoCol({ span: screenWidth >= 768 ? 4 : 12 }) {
                Column() {
                    Text('侧边导航').fontSize(16).fontWeight(FontWeight.Bold).margin({ bottom: 16 })
                    Text('菜单项1').margin({ bottom: 12 })
                    Text('菜单项2').margin({ bottom: 12 })
                    Text('菜单项3').margin({ bottom: 12 })
                    Text('菜单项4')
                }
                .width('100%')
                .padding(16)
                .backgroundColor('#f0f0f0')
                .borderRadius(8)
            }
            
            // 右侧内容
            AutoCol({ span: screenWidth >= 768 ? 8 : 12 }) {
                Column() {
                    Text('内容区域').fontSize(16).fontWeight(FontWeight.Bold).margin({ bottom: 16 })
                    
                    // 内容卡片网格
                    AutoRow({ gutter: [16, 16] }) {
                        // 生成多个卡片
                        ForEach([1, 2, 3, 4], (item) => {
                            AutoCol({ span: screenWidth >= 1200 ? 6 : 12 }) {
                                Column() {
                                    Text(`卡片 ${item}`)
                                        .width('100%')
                                        .height(120)
                                        .textAlign(TextAlign.Center)
                                        .backgroundColor('#e6f7ff')
                                }
                                .width('100%')
                                .borderRadius(8)
                                .backgroundColor('#f5f5f5')
                            }
                        })
                    }
                }
                .width('100%')
                .padding(16)
                .backgroundColor('#f9f9f9')
                .borderRadius(8)
            }
        }
        .padding({ left: 16, right: 16 })
    }
    
    // 底部信息栏
    AutoCol({ span: 12 }) {
        Row() {
            Text('© 2023 HarmonyOS Layout Demo')
            Blank()
            Text('关于').margin({ right: 20 })
            Text('隐私政策').margin({ right: 20 })
            Text('联系我们')
        }
        .width('100%')
        .height(60)
        .padding({ left: 20, right: 20 })
        .backgroundColor('#f0f0f0')
        .justifyContent(FlexAlign.SpaceBetween)
    }
}

2.2 仪表盘布局

仪表盘布局通常包含多个数据卡片,适合展示数据概览:

AutoRow({ gutter: [16, 16], autoMargin: { top: 16, bottom: 16 } }) {
    // 顶部统计卡片
    AutoCol({ span: 6 }) {
        Column() {
            Text('总用户').fontSize(14).fontColor('#666')
            Text('1,286').fontSize(24).fontWeight(FontWeight.Bold).margin({ top: 8 })
            Text('+12.5%').fontSize(12).fontColor('#52c41a').margin({ top: 4 })
        }
        .width('100%')
        .padding(16)
        .borderRadius(8)
        .backgroundColor('#fff')
        .justifyContent(FlexAlign.Center)
    }
    
    AutoCol({ span: 6 }) {
        Column() {
            Text('总收入').fontSize(14).fontColor('#666')
            Text('¥15,834').fontSize(24).fontWeight(FontWeight.Bold).margin({ top: 8 })
            Text('+8.2%').fontSize(12).fontColor('#52c41a').margin({ top: 4 })
        }
        .width('100%')
        .padding(16)
        .borderRadius(8)
        .backgroundColor('#fff')
        .justifyContent(FlexAlign.Center)
    }
    
    AutoCol({ span: 6 }) {
        Column() {
            Text('订单数').fontSize(14).fontColor('#666')
            Text('2,534').fontSize(24).fontWeight(FontWeight.Bold).margin({ top: 8 })
            Text('-2.1%').fontSize(12).fontColor('#f5222d').margin({ top: 4 })
        }
        .width('100%')
        .padding(16)
        .borderRadius(8)
        .backgroundColor('#fff')
        .justifyContent(FlexAlign.Center)
    }
    
    AutoCol({ span: 6 }) {
        Column() {
            Text('转化率').fontSize(14).fontColor('#666')
            Text('32.8%').fontSize(24).fontWeight(FontWeight.Bold).margin({ top: 8 })
            Text('+4.6%').fontSize(12).fontColor('#52c41a').margin({ top: 4 })
        }
        .width('100%')
        .padding(16)
        .borderRadius(8)
        .backgroundColor('#fff')
        .justifyContent(FlexAlign.Center)
    }
    
    // 图表区域
    AutoCol({ span: 12 }) {
        Column() {
            Text('销售趋势').fontSize(16).fontWeight(FontWeight.Bold).margin({ bottom: 16 })
            // 图表内容(实际项目中可以使用图表组件)
            Row() {
                // 模拟图表
                ForEach([30, 50, 70, 40, 60, 80, 45], (item) => {
                    Column() {
                        Column()
                            .width(30)
                            .height(item)
                            .backgroundColor('#1890ff')
                            .borderRadius({ topLeft: 4, topRight: 4 })
                    }
                    .width(40)
                    .height(100)
                    .justifyContent(FlexAlign.End)
                })
            }
            .width('100%')
            .justifyContent(FlexAlign.SpaceAround)
        }
        .width('100%')
        .padding(16)
        .backgroundColor('#fff')
        .borderRadius(8)
    }
    
    // 左侧详细数据
    AutoCol({ span: screenWidth >= 768 ? 8 : 12 }) {
        Column() {
            Text('详细数据').fontSize(16).fontWeight(FontWeight.Bold).margin({ bottom: 16 })
            // 数据列表
            ForEach([1, 2, 3, 4, 5], (item) => {
                Row() {
                    Text(`数据项 ${item}`)
                    Text(`${Math.floor(Math.random() * 1000)}`)
                }
                .width('100%')
                .justifyContent(FlexAlign.SpaceBetween)
                .padding({ top: 12, bottom: 12 })
                .border({ width: { bottom: 1 }, color: '#f0f0f0', style: BorderStyle.Solid })
            })
        }
        .width('100%')
        .padding(16)
        .backgroundColor('#fff')
        .borderRadius(8)
    }
    
    // 右侧活动信息
    AutoCol({ span: screenWidth >= 768 ? 4 : 12 }) {
        Column() {
            Text('最新活动').fontSize(16).fontWeight(FontWeight.Bold).margin({ bottom: 16 })
            // 活动列表
            ForEach([1, 2, 3], (item) => {
                Column() {
                    Text(`活动标题 ${item}`).fontWeight(FontWeight.Medium)
                    Text('2023-06-15').fontSize(12).fontColor('#999').margin({ top: 4 })
                    Text('活动描述信息...').fontSize(14).margin({ top: 8 })
                }
                .width('100%')
                .padding({ top: 12, bottom: 12 })
                .border({ width: { bottom: 1 }, color: '#f0f0f0', style: BorderStyle.Solid })
            })
        }
        .width('100%')
        .padding(16)
        .backgroundColor('#fff')
        .borderRadius(8)
    }
}

3. 常见组件布局实现

3.1 表单布局

AutoRow({ gutter: [0, 16] }) {
    // 表单标题
    AutoCol({ span: 12 }) {
        Text('用户信息表单').fontSize(18).fontWeight(FontWeight.Bold)
    }
    
    // 用户名输入
    AutoCol({ span: 12 }) {
        Column() {
            Text('用户名').fontSize(14).margin({ bottom: 8 })
            TextInput({ placeholder: '请输入用户名' })
                .width('100%')
                .height(40)
                .borderRadius(4)
                .backgroundColor('#f5f5f5')
        }
    }
    
    // 两列布局的表单项
    AutoCol({ span: 6 }) {
        Column() {
            Text('姓氏').fontSize(14).margin({ bottom: 8 })
            TextInput({ placeholder: '请输入姓氏' })
                .width('100%')
                .height(40)
                .borderRadius(4)
                .backgroundColor('#f5f5f5')
        }
    }
    
    AutoCol({ span: 6 }) {
        Column() {
            Text('名字').fontSize(14).margin({ bottom: 8 })
            TextInput({ placeholder: '请输入名字' })
                .width('100%')
                .height(40)
                .borderRadius(4)
                .backgroundColor('#f5f5f5')
        }
    }
    
    // 电子邮件
    AutoCol({ span: 12 }) {
        Column() {
            Text('电子邮件').fontSize(14).margin({ bottom: 8 })
            TextInput({ placeholder: '请输入电子邮件' })
                .width('100%')
                .height(40)
                .borderRadius(4)
                .backgroundColor('#f5f5f5')
        }
    }
    
    // 地址信息
    AutoCol({ span: 12 }) {
        Column() {
            Text('地址').fontSize(14).margin({ bottom: 8 })
            TextInput({ placeholder: '请输入详细地址' })
                .width('100%')
                .height(40)
                .borderRadius(4)
                .backgroundColor('#f5f5f5')
        }
    }
    
    // 三列布局的表单项
    AutoCol({ span: 4 }) {
        Column() {
            Text('城市').fontSize(14).margin({ bottom: 8 })
            TextInput({ placeholder: '城市' })
                .width('100%')
                .height(40)
                .borderRadius(4)
                .backgroundColor('#f5f5f5')
        }
    }
    
    AutoCol({ span: 4 }) {
        Column() {
            Text('省份').fontSize(14).margin({ bottom: 8 })
            TextInput({ placeholder: '省份' })
                .width('100%')
                .height(40)
                .borderRadius(4)
                .backgroundColor('#f5f5f5')
        }
    }
    
    AutoCol({ span: 4 }) {
        Column() {
            Text('邮编').fontSize(14).margin({ bottom: 8 })
            TextInput({ placeholder: '邮编' })
                .width('100%')
                .height(40)
                .borderRadius(4)
                .backgroundColor('#f5f5f5')
        }
    }
    
    // 提交按钮
    AutoCol({ span: 12 }) {
        Row() {
            Button('取消')
                .width(100)
                .height(40)
                .backgroundColor('#f5f5f5')
                .fontColor('#333')
                .margin({ right: 16 })
            
            Button('提交')
                .width(100)
                .height(40)
                .backgroundColor('#1890ff')
                .fontColor('#fff')
        }
        .width('100%')
        .margin({ top: 16 })
       .justifyContent(FlexAlign.End)
    }
}

表单布局是应用中常见的交互界面,使用AutoRow和AutoCol可以轻松实现不同宽度的表单项布局。上述代码展示了如何创建响应式表单,包括单列、双列和三列布局的表单项,以及如何对齐和样式化表单元素。

3.2 卡片列表布局

卡片列表是展示多条相似信息的常用方式,以下是一个商品列表的实现:

AutoRow({ gutter: [16, 16] }) {
    // 标题区域
    AutoCol({ span: 12 }) {
        Row() {
            Text('商品列表').fontSize(20).fontWeight(FontWeight.Bold)
            Blank()
            Text('查看全部 >').fontColor('#1890ff')
        }
        .width('100%')
        .justifyContent(FlexAlign.SpaceBetween)
        .margin({ bottom: 16 })
    }
    
    // 商品卡片
    ForEach([1, 2, 3, 4, 5, 6], (item) => {
        AutoCol({ 
            span: screenWidth >= 1200 ? 4 : (screenWidth >= 768 ? 6 : 12) 
        }) {
            Column() {
                // 商品图片
                Column()
                    .width('100%')
                    .height(160)
                    .backgroundColor('#e6f7ff')
                    .borderRadius({ topLeft: 8, topRight: 8 })
                
                // 商品信息
                Column() {
                    Text(`商品名称 ${item}`)
                        .fontSize(16)
                        .fontWeight(FontWeight.Medium)
                        .margin({ bottom: 8 })
                    
                    Text('商品描述信息,简短介绍商品特点和亮点...')
                        .fontSize(14)
                        .fontColor('#666')
                        .margin({ bottom: 12 })
                        .maxLines(2)
                        .textOverflow({ overflow: TextOverflow.Ellipsis })
                    
                    Row() {
                        Text('¥199.00')
                            .fontSize(18)
                            .fontColor('#f5222d')
                            .fontWeight(FontWeight.Bold)
                        
                        Blank()
                        
                        Button('加入购物车')
                            .height(32)
                            .fontSize(14)
                            .backgroundColor('#1890ff')
                            .fontColor('#fff')
                    }
                    .width('100%')
                }
                .width('100%')
                .padding(12)
            }
            .width('100%')
            .backgroundColor('#fff')
            .borderRadius(8)
        }
    })
}

4. 总结

本文通过实际应用案例,展示了如何使用HarmonyOS Layout布局组件系统实现各种常见的页面布局和组件布局。我们详细介绍了:

  1. 经典三段式布局:包括顶部导航栏、中间内容区和底部信息栏的页面结构。
  2. 仪表盘布局:适合数据可视化和管理后台的数据概览展示。
  3. 表单布局:实现各种表单元素的排列和对齐。
  4. 卡片列表布局:展示多条相似信息的常用方式。

通过这些案例,我们可以看到HarmonyOS Layout布局组件系统的强大和灵活性,它能够帮助开发者快速构建出美观、响应式的用户界面。在下一篇文章中,我们将继续探讨更多高级应用场景和最佳实践。


全栈若城
1 声望1 粉丝