鸿蒙OS开发--初级计算器实例

"成功不是将来才有的,而是从决定去做的那一刻起,持续累积而成。”
—— 保罗·柯艾略(Paulo Coelho)

前言

学习完成本次实例需要运用的知识:

  1. 栈的基本操作,将中缀表达式变成后缀表达式并计算结果
  2. 首选项数据存储的应用,将上次程序留下的表达式进行保存
  3. ArkUI的基础布局知识,用于布局数字和符号的按钮,以及表达式字体的大小。

本实例需要对上述知识有一定的了解,接下来是代码的实现目标:

  1. 通过按钮输入表达式,点击等于能够计算出结果,其中,当操作表达式的时候表达式字体较大,点击等于显示结果的时候字体较大,另外可以继续操作结果
  2. 首选项数据存储的应用,将上次程序留下的表达式进行保存。
  3. 识别括号和‘-’号,优先计算括号里的内容,能够进行加减乘除的运算。
  4. 实现清零和‘<’的功能。

注:本篇文章用于个人学习总结

代码实现

根据以上功能可以将代码分为两大块,第一模块就是实现布局并且能将表达式正确输入上去,第二模块就是处理表达式并计算出结果。

布局

按钮部分

按钮大体分为两种,一种是按下之后把自己的值附上去的,比如数字和加减乘除括号,另一种是按下去之后可以实现某种功能的,比如说等于号,清理以及删除。

按照上述功能我们可以将其封装成如下类:

export default  class PressKeysBean {
   
  flag: number;
  value: string;
  ability?:number

  constructor(flag: number, value: string,ability?:number) {
   
    this.flag = flag;
    this.value = value;
    this.ability=ability
  }
}

flag用来区分是否为功能键,而value用来存放值,ability就是功能键的功能加以区分。

import PressKeysBean from './PressKeysItem'

 class PressKeysBeanViewModel{
   
  public getPressKeys():Array<Array<PressKeysBean>>{
   
    return [
      [
        new PressKeysBean(1,'C',0),
        new PressKeysBean(0,'7'),
        new PressKeysBean(0,'4'),
        new PressKeysBean(0,'1'),
        new PressKeysBean(1,'<',1)
      ],
      [
        new PressKeysBean(1,'('),
        new PressKeysBean(0,'8'),
        new PressKeysBean(0,'5'),
        new PressKeysBean(0,'2'),
        new PressKeysBean(0,'0')
      ],
      [
        new PressKeysBean(1,')'),
        new PressKeysBean(0,'9'),
        new PressKeysBean(0,'6'),
        new PressKeysBean(0,'3'),
        new PressKeysBean(0,'.')
      ],
      [
        new PressKeysBean(1,'÷'),
        new PressKeysBean(1,'×'),
        new PressKeysBean(1,'-'),
        new PressKeysBean(1,'+'),
        new PressKeysBean(2,'=')
      ]
    ]
  }
}
let keysModel = new PressKeysBeanViewModel();
export default keysModel as PressKeysBeanViewModel;

至此,我们的十六个键按照功能划分封装好了,接下来就是布局了!

布局可以用Grid布局,也可以用线性布局进行两层循环,这里使用后者。

Row({
   space:10}){
   
        ForEach(keysModel.getPressKeys(),(columnItem:Array<PressKeysBean>)=>{
   
          Column({
   space:30}){
   
            ForEach(columnItem,(Item:PressKeysBean)=> {
   
            //flag==0,表示是数字键,按下后直接将数字压进栈中
              if (Item.flag == 0) {
   
                Button(Item.value).style('#ffffffff','#000000').onClick(()=>{
   
                  this.expressions.push(Item.value)
                })
                //以下是加减乘除键和功能键
              } else if (Item.flag == 1) {
   
                Button(Item.value).style('#66ffffff','#000000').onClick(()=>{
   
                //等于0,是清除键,把表达式的值变成空,这里的flag,和flag1初始化。
                //flag和flag1是用来控制表达式和字体大小的,可以先不管
                  if(Item.ability==0){
   
                    this.expressions=[]
                    this.flag=0
                    this.flag1=0
                    //这里是删除键,点击一次在栈中弹出一个元素
                  }else if(Item.ability==1){
   
                    this.expressions.pop()
                    //加减乘除直接赋值
                  }else {
   
                    this.expressions.push(Item.value)
                    if(this.flag1==1){
   
                      this.expressions=[]
                      this.expressions.push(this.result.toString())
                      this.expressions.push(Item.value)
                      this.flag1=0
                    }
                  }
                })
                //这里是等于键,执行的功能是将表达式的结果进行解析赋值出结果
              }else if(Item.flag==2){
   
                Button(Item.value).style('#ff20b4cf','#ffffffff').onClick(()=>{
   
                  this.result=getCalculate(this.expressions.join(''))
                  if(Number.isNaN(this.result)){
   
                    this.result='表达式有误'
                  }
                  this.flag=1
                  this.flag1=1
                })
              }
            })
          }.justifyContent(FlexAlign.SpaceAround)
        })
      }.justifyContent(FlexAlign.SpaceAround)
      .width(350)
      .height(310)
      .alignItems(VerticalAlign.Bottom)
      .margin({
   top:280})

表达式和结果部分

情况1:表达式过长

Column({
   space:20}){
   
        TextInput({
   text:this.expressions.join('')})
          .minFontSize(15)
          .maxFontSize(this.flag1==1?30:50)
          .heightAdaptivePolicy(TextH
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值