HarmonyOS 鸿蒙Next获取验证码倒计时功能实现示例

发布于 1周前 作者 vueper 来自 鸿蒙OS

HarmonyOS 鸿蒙Next获取验证码倒计时功能实现示例

@Entry
@Component
struct Page33 {
// 验证码按钮显示信息状态
@State captchaButtonText: string = ‘获取验证码’;

// 滑块验证显示/隐藏状态 @State sliderVisibility: Visibility = Visibility.None;

// 页面即将消失时的回调函数 aboutToDisappear() { // 清除验证码倒计时定时器 clearInterval(globalThis.captchaTimerId); }

// 构建组件树 build() { // 主要布局 Column() { // 验证码按钮 Text(this.captchaButtonText) .fontSize(‘32lpx’) .fontColor(’#FF1919’) .width(‘50%’) .onClick(() => { // 判断是否开始倒计时 if (this.captchaButtonText === ‘获取验证码’) { // 设置初始倒计时时间为60秒 globalThis.remainingSeconds = 60; // 更新验证码按钮文本为剩余秒数 this.captchaButtonText = globalThis.remainingSeconds + ‘s’;

        <span class="hljs-comment"><span class="hljs-comment">// 清除已存在的定时器</span></span>
        clearInterval(globalThis.captchaTimerId);

        <span class="hljs-comment"><span class="hljs-comment">// 创建新的倒计时定时器</span></span>
        globalThis.captchaTimerId = setInterval(() =&gt; {
          console.log(<span class="hljs-string"><span class="hljs-string">'==== 定时器执行:'</span></span>, <span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.captchaButtonText);
          <span class="hljs-comment"><span class="hljs-comment">// 减少一秒</span></span>
          globalThis.remainingSeconds--;
          <span class="hljs-comment"><span class="hljs-comment">// 更新验证码按钮文本</span></span>
          <span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.captchaButtonText = globalThis.remainingSeconds + <span class="hljs-string"><span class="hljs-string">'s'</span></span>;

          <span class="hljs-comment"><span class="hljs-comment">// 倒计时结束,恢复初始状态</span></span>
          <span class="hljs-keyword"><span class="hljs-keyword">if</span></span> (globalThis.remainingSeconds &lt;= <span class="hljs-number"><span class="hljs-number">0</span></span>) {
            <span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.captchaButtonText = <span class="hljs-string"><span class="hljs-string">'获取验证码'</span></span>;
            <span class="hljs-comment"><span class="hljs-comment">// 清除定时器</span></span>
            clearInterval(globalThis.captchaTimerId);
          }
        }, <span class="hljs-number"><span class="hljs-number">1000</span></span>);
      }
    });
}
.width(<span class="hljs-string"><span class="hljs-string">'100%'</span></span>);

} }<button style="position: absolute; padding: 4px 8px 0px; cursor: pointer; top: 8px; right: 8px; font-size: 14px;">复制</button>

13 回复

你调接口接数据试试看,我的使用定时器直接报错了

我调接口也没问题,你那边的代码是什么样的?

cke_156.png

cke_556.pngcke_795.png

帮我看看我发送验证码哪里写的有问题呢?加了下面的定时器就报错,不加就是好的。

没看出来你这边哪里错了,我自己昨天晚上写了两个例子放到3楼和4楼了,但是到现在还在审核中,估计你看不到。或许你可以试着换个网络请求框架,比如Axios试试

模拟网络请求并发送验证码,网络请求工具类参考:https://developer.huawei.com/consumer/cn/blog/topic/03146488303249019

import { MyHttpUtil } from '../MyHttpUtil';

@Entry @Component struct Page33 { // 验证码按钮显示信息状态 @State captchaButtonText: string = ‘获取验证码’;

// 滑块验证显示/隐藏状态 @State sliderVisibility: Visibility = Visibility.None;

// 页面即将消失时的回调函数 aboutToDisappear() { // 清除验证码倒计时定时器 clearInterval(globalThis.captchaTimerId); }

// 构建组件树 build() { // 主要布局 Column() { // 验证码按钮 Text(this.captchaButtonText) .fontSize(‘32lpx’) .fontColor(’#FF1919’) .width(‘50%’) .onClick(() => { this.sendCode() }); } .width(‘100%’); }

async sendCode() {

<span class="hljs-comment">// 判断是否开始倒计时</span>
<span class="hljs-keyword">if</span> (<span class="hljs-keyword">this</span>.captchaButtonText === <span class="hljs-string">'获取验证码'</span>) {

  <span class="hljs-keyword">let</span> request = await MyHttpUtil.request(<span class="hljs-string">'https://api.oioweb.cn/api/weather/GetWeather'</span>, <span class="hljs-string">'GET'</span>, {}, <span class="hljs-literal">true</span>);
  <span class="hljs-built_in">JSON</span>.stringify(<span class="hljs-string">'响应结果'</span>,request)

  <span class="hljs-comment">// 设置初始倒计时时间为60秒</span>
  globalThis.remainingSeconds = <span class="hljs-number">60</span>;
  <span class="hljs-comment">// 更新验证码按钮文本为剩余秒数</span>
  <span class="hljs-keyword">this</span>.captchaButtonText = globalThis.remainingSeconds + <span class="hljs-string">'s'</span>;

  <span class="hljs-comment">// 清除已存在的定时器</span>
  clearInterval(globalThis.captchaTimerId);

  <span class="hljs-comment">// 创建新的倒计时定时器</span>
  globalThis.captchaTimerId = setInterval(() =&gt; {
    console.log(<span class="hljs-string">'==== 定时器执行:'</span>, <span class="hljs-keyword">this</span>.captchaButtonText);
    <span class="hljs-comment">// 减少一秒</span>
    globalThis.remainingSeconds--;
    <span class="hljs-comment">// 更新验证码按钮文本</span>
    <span class="hljs-keyword">this</span>.captchaButtonText = globalThis.remainingSeconds + <span class="hljs-string">'s'</span>;

    <span class="hljs-comment">// 倒计时结束,恢复初始状态</span>
    <span class="hljs-keyword">if</span> (globalThis.remainingSeconds &lt;= <span class="hljs-number">0</span>) {
      <span class="hljs-keyword">this</span>.captchaButtonText = <span class="hljs-string">'获取验证码'</span>;
      <span class="hljs-comment">// 清除定时器</span>
      clearInterval(globalThis.captchaTimerId);
    }
  }, <span class="hljs-number">1000</span>);
}

} }<button style="position: absolute; padding: 4px 8px 0px; cursor: pointer; top: 8px; right: 8px; font-size: 14px;">复制</button>

cke_158.png

import { MyHttpUtil } from '../MyHttpUtil';

@Entry @Component struct Page33 { // 验证码按钮显示信息状态 @State captchaButtonText: string = ‘获取验证码’;

// 滑块验证显示/隐藏状态 @State sliderVisibility: Visibility = Visibility.None;

timer = undefined @State second:number = 60

// 页面即将消失时的回调函数 aboutToDisappear() { // 清除验证码倒计时定时器 clearInterval(globalThis.captchaTimerId); }

// 构建组件树 build() { // 主要布局 Column() { // 验证码按钮 Text(this.second == 60 ?this.captchaButtonText:’’+this.second) .fontSize(‘32lpx’) .fontColor(’#FF1919’) .width(‘50%’) .onClick(() => { this.sendCode() }); } .width(‘100%’); }

async sendCode() {

<span class="hljs-comment">// 判断是否开始倒计时</span>
<span class="hljs-keyword">if</span> (<span class="hljs-keyword">this</span>.captchaButtonText === <span class="hljs-string">'获取验证码'</span>) {

  <span class="hljs-keyword">let</span> request = await MyHttpUtil.request(<span class="hljs-string">'https://api.oioweb.cn/api/weather/GetWeather'</span>, <span class="hljs-string">'GET'</span>, {}, <span class="hljs-literal">true</span>);
  <span class="hljs-built_in">JSON</span>.stringify(<span class="hljs-string">'响应结果'</span>,request)

  <span class="hljs-keyword">this</span>.timer = setInterval(()=&gt;{
    <span class="hljs-keyword">if</span>(<span class="hljs-keyword">this</span>.second == <span class="hljs-number">0</span>){
      <span class="hljs-keyword">this</span>.second = <span class="hljs-number">60</span>;
      clearInterval(<span class="hljs-keyword">this</span>.timer)
    }
    <span class="hljs-keyword">this</span>.second -= <span class="hljs-number">1</span>;

    console.info(<span class="hljs-string">'=======this.second'</span>,<span class="hljs-keyword">this</span>.second)
  },<span class="hljs-number">1000</span>);
}

} }<button style="position: absolute; padding: 4px 8px 0px; cursor: pointer; top: 8px; right: 8px; font-size: 14px;">复制</button>

if(this.second == 0){ this.second = 60; clearInterval(this.timer) } this.second -= 1; }这个写法有bug,重复点击的话会导致倒计时不准。 this.intervalID = setInterval(() => { if (this.countdown === 0) { this.verifyTxt = ‘重新获取’ this.countdown = 10 clearInterval(this.intervalID) return } this.countdown– }, 1000) 我小改了一下 自测没啥问题了

这个有用吗?

我这儿怎么显示"globalThis" is not supported (arkts-no-globalthis) <ArkTSCheck>

开发工具升级后就不让用globalThis了,在外面声明变量用this.调用吧。

我用的api12。虽然IDE中提示““globalThis” is not supported (arkts-no-globalthis) <ArkTSCheck>”,但编译运行并没问题,app能正常跑。 同时问下,你说的“在外面声明变量用this.调用”,具体怎么编写代码呢?

=========globlThis用法 //声明 globalThis.myName = “张三” globalThis.myAge = 20 //使用 console.info(${globalThis.myName}) console.info(${globalThis.myAge})

=============自己声明用法 //声明 export class MyGlobalThis { static myName: string = “张三” static myAge: number = 20 } //使用 console.info(${MyGlobalThis.myName}) console.info(${MyGlobalThis.myAge})

在HarmonyOS中实现验证码倒计时功能,你可以使用TimerHandler结合Runnable来实现。基本思路是:在用户点击获取验证码后,启动一个倒计时,同时禁用获取验证码按钮,并在UI上更新倒计时显示。每次倒计时结束,重新启用按钮并重置倒计时显示。

示例代码片段(使用Handler):

private Handler handler = new Handler();
private Runnable runnable = new Runnable() {
    int timeLeft = 60;
    @Override
    public void run() {
        if (timeLeft > 0) {
            textView.setText("重新获取(" + timeLeft + "s)");
            timeLeft--;
            handler.postDelayed(this, 1000);
        } else {
            // 重新启用按钮
            button.setEnabled(true);
            textView.setText("获取验证码");
        }
    }
};

// 在点击事件中
button.setOnClickListener(v -> {
    button.setEnabled(false);
    textView.setText("重新获取(60s)");
    handler.postDelayed(runnable, 1000);
});

如果问题依旧没法解决请加我微信,我的微信是itying888。
回到顶部