蜂窝数据和wifi通道切换

蜂窝数据和wifi通道切换


import { BusinessError } from '@kit.BasicServicesKit';
import { connection } from '@kit.NetworkKit';
import { data } from '@kit.TelephonyKit';
import { ToastUtil } from '@pura/harmony-utils';
import { sim } from '@kit.TelephonyKit';

export class WifiConnectManager {
  private static instance?: WifiConnectManager;
  private isWifi: boolean = true;

  /**
   * Get singleton
   *
   * @returns Singleton object
   */
  public static getInstance(): WifiConnectManager {
    if (!WifiConnectManager.instance) {
      WifiConnectManager.instance = new WifiConnectManager();
    }
    return WifiConnectManager.instance;
  }

  /**
   * @description :移动数据是否开启
   */
  public async isMobileDataEnabled(): Promise<boolean> {
    return await data.isCellularDataEnabled() && this.isSimCardInserted();
  }

  /**
   * @description :SIM 1、2卡槽是否插卡
   */
  public isSimCardInserted(): boolean {
    // 1、获取卡槽数量
    const maxSimCount = sim.getMaxSimCount()
    console.info(' Sim Count:', maxSimCount);

    // 2、遍历所有卡槽,检查是否有 SIM 卡
    for (let i = 0; i < maxSimCount; i++) {
      try {
        const hasCard = sim.hasSimCardSync(i);
        if (hasCard) {
          console.info(`SIM card detected in slot ${i}`);
          return true;
        }
      } catch (error) {
        console.error(`Failed to check SIM card in slot ${i}: ${JSON.stringify(error)}`);
      }
    }

    // 3、所有卡槽都没有卡
    console.info('No SIM card detected in any slot');
    return false;
  }


  /**
   * @param: isWifi: true: wifi, false: 流量
   */
  public startListenNetChange(isWifi: boolean): void {
    console.info('registerNetListener');
    console.info('registerNetListener', `connect  type : + ${isWifi ? 'wifi' : '流量'}`);
    WifiConnectManager.getInstance().isWifi = isWifi;
    let netConnectionWifi = connection.createNetConnection({
      netCapabilities: {
        bearerTypes: [connection.NetBearType.BEARER_WIFI]
      }
    });

    netConnectionWifi.register((error: BusinessError) => {
      if (error) {
        console.error(`register error: ${error.code}`);
      }
    });
    netConnectionWifi.on('netAvailable', () => {
      console.info('netConnectionWifi netAvailable');
      if (WifiConnectManager.getInstance().isWifi) {
        this.bindWifiWhenConnected();
      } else {
        this.bindCellularWhenConnected();
      }
    });
    netConnectionWifi.on('netLost', () => {
      console.info('Wifi netLost');
      if (WifiConnectManager.getInstance().isWifi) {
        this.bindWifiWhenConnected();
      } else {
        this.bindCellularWhenConnected();
      }
    });
    let netConnectionCellular = connection.createNetConnection({
      netCapabilities: {
        bearerTypes: [connection.NetBearType.BEARER_CELLULAR]
      }
    });
    netConnectionCellular.register((error: BusinessError) => {
      if (error) {
        console.error(`register error: ${error.message}`);
      }
    });
    netConnectionCellular.on('netAvailable', () => {
      console.info('netConnectionCellular netAvailable');
      if (WifiConnectManager.getInstance().isWifi) {
        this.bindWifiWhenConnected();
      } else {
        this.bindCellularWhenConnected();
      }
    });
    netConnectionCellular.on('netLost', () => {
      console.info('Cellular netLost');
      if (WifiConnectManager.getInstance().isWifi) {
        this.bindWifiWhenConnected();
      } else {
        this.bindCellularWhenConnected();
      }
    });
  }

  /**
   * @Description: 绑定WiFi
   */
  private async bindWifiWhenConnected(): Promise<void> {
    await connection.setAppNet(connection.getDefaultNetSync()).then(() => {
      console.info('setAppNet default success');
    });

    connection.getAllNets().then((data: connection.NetHandle[]) => {
      data.forEach(net => {
        connection.getNetCapabilities(net).then((data: connection.NetCapabilities) => {
          if (data.bearerTypes.length > 0 && data.bearerTypes[0] === connection.NetBearType.BEARER_WIFI) {
            connection.setAppNet(net).then(() => {
              console.info('setAppNet wifi success');
              return;
            }).catch((error: Error) => {
              console.error(`setAppNet wifi failed, error = ${error.message}`);
            });
          }
        }).catch((error: Error) => {
          console.error(`getNetCapabilities error = ${error.message}`);
        });
      });
    }).catch((error: Error) => {
      console.error(`getAllNets error = ${error.message}`);
    });
  }

  /**
   * @Description: 绑定移动数据
   */
  private async bindCellularWhenConnected(): Promise<void> {
    // 先判断移动数据是否开启
    const isMobileDataEnabled = await this.isMobileDataEnabled()
    if (!isMobileDataEnabled) {
      ToastUtil.showToast($r('app.string.Telephony_error'));
      return
    }
    await connection.setAppNet(connection.getDefaultNetSync()).then(() => {
      console.info('setAppNet default success');
    });
    connection.getAllNets().then((data: connection.NetHandle[]) => {
      data.forEach(net => {
        connection.getNetCapabilities(net).then((data: connection.NetCapabilities) => {
          if (data.bearerTypes.length > 0 && data.bearerTypes[0] === connection.NetBearType.BEARER_CELLULAR) {
            connection.setAppNet(net).then(() => {
              console.info('setAppNet cellular success');
              return;
            }).catch((error: Error) => {
              console.error(`setAppNet cellular failed, error = ${error.message}`);
            });
          }
        }).catch((error: Error) => {
          console.error(`getNetCapabilities error = ${error.message}`);
        });
      });
    }).catch((error: Error) => {
      console.error(`getAllNets error = ${error.message}`);
    });
  }

  /**
   * @Description: 取消当了绑定
   */
  public cancelBind(): void {
    console.info('cancelBind');
    connection.getDefaultNet().then((netHandle: connection.NetHandle) => {
      netHandle.netId = 0;
      connection.setAppNet(netHandle).then(() => {
        console.info("cancelBind success");
      }).catch((error: BusinessError) => {
        console.error(`Failed to setAppNet. Code:${error.code}, message:${error.message}`);
      })
    });
  }

}

检查网络是否可用

import { connection } from '@kit.NetworkKit';
import { LogUtils } from './LogUtils';

const TAG = '[mine_cloud] [NetworkUtils]';

/** 网络类型明细(相机WiFi 场景需要区分) */
export class NetworkStatus {
  /** 任一网络 NET_CAPABILITY_VALIDATED = true */
  hasValidated: boolean = false
  /** 有可用蜂窝网络 */
  hasCellular: boolean = false
  /** 有可用 WiFi(已 VALIDATED) */
  hasWifi: boolean = false
}

/**
 * 网络工具类
 * 统一封装网络可用性检测,避免在多处重复实现 connection.getAllNets() + NET_CAPABILITY_VALIDATED 检查
 */
export class NetworkUtils {
  /**
   * 异步检测当前是否有可用网络(WiFi / 蜂窝,任一 NET_CAPABILITY_VALIDATED 即视为可用)
   * @returns true=有可用网络, false=无网络或检测失败
   */
  static async isAvailable(): Promise<boolean> {
    const status = await NetworkUtils.getStatus()
    return status.hasValidated
  }

  /**
   * 获取详细网络状态(WiFi/蜂窝 分开,用于相机WiFi 等需要排除特定网络的场景)
   */
  static async getStatus(): Promise<NetworkStatus> {
    const status = new NetworkStatus()
    try {
      const nets: connection.NetHandle[] = await connection.getAllNets()
      for (let i = 0; i < nets.length; i++) {
        const netCap: connection.NetCapabilities = await connection.getNetCapabilities(nets[i])
        const isValid: boolean = netCap?.networkCap?.includes(connection.NetCap.NET_CAPABILITY_VALIDATED) ?? false
        const bearerTypes: connection.NetBearType[] = netCap?.bearerTypes ?? []
        if (isValid) {
          status.hasValidated = true
          if (bearerTypes.includes(connection.NetBearType.BEARER_CELLULAR)) {
            status.hasCellular = true
          }
          if (bearerTypes.includes(connection.NetBearType.BEARER_WIFI)) {
            status.hasWifi = true
          }
        }
      }
    } catch (e) {
      LogUtils.warn(TAG, `[getStatus] 检查网络失败: ${(e as Error).message}`)
    }
    return status
  }
}

posted @ 2026-06-16 20:02  带头大哥d小弟  阅读(10)  评论(0)    收藏  举报