HarmonyOS鸿蒙Next中NavDestination组件内使用tabs点击tabBar切换后就自动恢复到初始状态,例如进入页面在推荐选项卡点击发现后一瞬间又回到了推荐这是怎么回事

HarmonyOS鸿蒙Next中NavDestination组件内使用tabs点击tabBar切换后就自动恢复到初始状态,例如进入页面在推荐选项卡点击发现后一瞬间又回到了推荐这是怎么回事

interface TabClass {
  text: string
  icon: ResourceStr
}

// 跳转页面入口函数
@Builder
export function LayoutBuilder() {
  Layout();
}

@ComponentV2
struct Layout {
  @Local currentIndex: number = 0
  pathStack: NavPathStack = new NavPathStack();
  tabData: TabClass[] = [
    { text: '推荐', icon: $r('app.media.ic_recommend') },
    { text: '发现', icon: $r('app.media.ic_find') },
    { text: '动态', icon: $r('app.media.ic_moment') },
    { text: '我的', icon: $r('app.media.ic_mine') }
  ]

  @Builder
  tabBuilder(item: TabClass, index: number) {
    Column({ space: 5 }) {
      Image(item.icon)
        .width(24)
        .fillColor(this.currentIndex == index ? '#E85A88' : '#63AAAA')
      Text(item.text)
        .fontSize(14)
        .fontColor(this.currentIndex == index ? '#E85A88' : '#63AAAA')
    }
  }

  build() {
    NavDestination() {
      Tabs({ barPosition: BarPosition.End, index: this.currentIndex }) {
        ForEach(this.tabData, (data: TabClass, index: number) => {
          TabContent() {
            Text(data.text)
              .fontColor(Color.White)
          }
          .tabBar(this.tabBuilder(data, index)) //菜单需要自定义函数
          .backgroundColor('#131215')
          //扩充组件安全区域
          .expandSafeArea([SafeAreaType.SYSTEM], [SafeAreaEdge.TOP, SafeAreaEdge.BOTTOM])
        })
      }
      .scrollable(false) //去掉左右滑动的效果
      .animationDuration(0) //去掉左右滑动的动画
      .backgroundColor('#3B3F42')
      .onChange((index: number) => {
        this.currentIndex = index
      })
      //扩充组件安全区域
      .expandSafeArea([SafeAreaType.SYSTEM], [SafeAreaEdge.TOP, SafeAreaEdge.BOTTOM])

    }
    //.title('布局页')
    .onReady((context: NavDestinationContext) => {
      this.pathStack = context.pathStack;
    })
  }
}

更多关于HarmonyOS鸿蒙Next中NavDestination组件内使用tabs点击tabBar切换后就自动恢复到初始状态,例如进入页面在推荐选项卡点击发现后一瞬间又回到了推荐这是怎么回事的实战教程也可以访问 https://www.itying.com/category-93-b0.html

10 回复

我滴天啊,终于找到问题所在了,重新创建个新项目一步一步写代码最后终于找到问题了

原来是在上一个页面跳转这个页面的时候 我用了定时器

原想着跳转后上一个页面会销毁的,再不济页面都跳转了定时器应该也失效了吧

万万没想到 那个定时器在一直运行,就造成了我在tab页面点击tab切换后 上个页面的定时器又继续跳这个页面,刷新很快看不出来是跳转,只能看到tab项又回到了初始状态,所以无论怎么点击切换都会回到初始状态。

上个页面跳转代码

setInterval(() => {
  this.sec--
  if (this.sec <= 0) {
    this.pathStack.replacePathByName("Layout", null, false)
  }
}, 1000)

修改后正常了下面是修改后代码 前面需要先定义个timer 因为我页面还有个按钮跳同一个页面,那个按钮跳转的时候 需要把定时器关掉

this.timer = setInterval(() => {
  this.sec--
  if (this.sec <= 0) {
    this.pathStack.replacePathByName("Layout", null, false)
    //停止定时器
    clearInterval(this.timer)
  }
}, 1000)

更多关于HarmonyOS鸿蒙Next中NavDestination组件内使用tabs点击tabBar切换后就自动恢复到初始状态,例如进入页面在推荐选项卡点击发现后一瞬间又回到了推荐这是怎么回事的实战系列教程也可以访问 https://www.itying.com/category-93-b0.html


好好好 给自己埋了个BUG,

主要上个页面是欢迎页 有个3秒的倒计时 倒计时结束就跳转的 哈哈 这个问题搞得我晚上都没睡好觉,

到底问题出在哪里

跟NavDestinaton应该没关系,可能是Tabs选项里的index绑定和.onChange回调起了冲突。现在不方便试,不太确定是不是,

  • 首页
  • 发现

这就奇怪了,看不出啥问题,

问题找到了,很悲哀。

在HarmonyOS中,NavDestination组件内使用tabs出现自动回退问题,通常与页面生命周期或状态管理有关。可能是tab切换时触发了页面重建,导致状态重置。检查是否在tab切换时意外调用了导航操作,或未正确保存tab状态。确保每个tab对应的组件使用@State@Link装饰器保持状态,避免使用临时变量。

这个问题是由于NavDestination和Tabs组件结合使用时状态管理不当导致的。关键点在于:

  1. NavDestination默认会重置内部组件状态,导致Tabs的currentIndex被重置。需要手动保存和恢复状态。

  2. 解决方案是在NavDestination的onBackPressed回调中保存当前状态:

.onBackPressed(() => {
  this.pathStack.push(this.currentIndex.toString());
  return false; // 阻止默认返回行为
}
  1. 然后在onReady回调中恢复状态:
.onReady((context: NavDestinationContext) => {
  this.pathStack = context.pathStack;
  const savedIndex = this.pathStack.findLast();
  if (savedIndex) {
    this.currentIndex = parseInt(savedIndex);
  }
}
  1. 确保Tabs的onChange回调正确更新currentIndex:
.onChange((index: number) => {
  this.currentIndex = index;
  this.pathStack.push(index.toString());
}

这样修改后,Tab切换状态就能正确保持了。核心思路是利用NavPathStack手动管理状态,避免NavDestination的自动重置行为。

回到顶部