iOS 版智能生活 App SDK 开发入门教程【超详细代码步骤说明】_ios. 涂鸦sdk如何接入-程序员宅基地

技术标签: 云开发  App  objective-c  github  API  物联网  SDK  ios  

涂鸦智能生活 App SDK iOS 版提供了即全面又灵活的 IoT App 开发模式,大家可以通过本教程在两小时内快速开发出一款自己的 IoT App,并实现如下功能:

  •  使用手机号码注册并登录一个用户账号。
  •  在登录状态下创建一个家庭,并查看和修改家庭信息
  •  以智能灯泡为例,通过 App 连接一个智能设备。
  •  使用这款创建的 App 控制灯泡的开关和亮度。

大家可以前往App 开发平台查看本教程中的示例代码,本次教程按功能模块进行分类,方便大家可以快速找到对应的代码参考学习。

效果展示

学习完本教程,并且结合一定的面板开发后,大家可以创建出一个类似以下 iOS App 的 Demo。

准备工作

在开始本教程前,请先确保已经完成以下内容 :

  1. 涂鸦 IoT 开发平台注册账号并创建 App,获取 SDK 的 AppKey,AppSecret。
  2. 准备一个涂鸦赋能的智能产品,本教程以智能灯泡为例。
  3. 使用 CocoaPods 将涂鸦智能生活App SDK 集成到您的项目中。

第一步:注册用户账号

本模块中,仅演示使用手机号注册登录。除此以外,涂鸦智能生活 App SDK 还提供了邮箱、第三方、匿名等多种注册登录方式。

注册用户账号时:

  • 需要提供 countryCode 参数来区分注册地区,用于就近选择涂鸦 IoT 开发平台的可用区。如中国大陆为 86,美国为 1

  • 之后将频繁地调用对象 TuyaSmartUser。它是一个单例,存储了当前用户的所有信息及相关的登录注册方法。

查询验证码服务可用地区

为了加强用户信息的数据安全,涂鸦优化了验证码和添加了账号限制。只有验证码服务可用的地区,才可以发送验证码。大家需要先查询自己的开发者账号是否已经在从涂鸦 IoT 开发平台开通验证码服务的可用地区列表。

[[TuyaSmartUser sharedInstance] getWhiteListWhoCanSendMobileCodeSuccess:^(NSString *regions) {

} failure:^(NSError *error) {

}];

返回值 regions 表示一个或多个国家或地区,以 , 隔开的字符串,例如 86 和 01。可用区编号列表。

获取注册账号的验证码

与大部分注册流程类似,用户必须先获取验证码。无论是手机或是邮箱,都可以使用统一的获取验证码接口在注册及后续密码修改,验证码登录,信息完善等操作中获取相应的验证码。

NSString * region = [[TuyaSmartUser sharedInstance] getDefaultRegionWithCountryCode:countryCode];

[[TuyaSmartUser sharedInstance] sendVerifyCodeWithUserName:userName // phone number or email address
											region:region
										countryCode:countryCode // NSString ,like 86 or 01
												type:1     // code type , 1: verification code register,
											success:^{
											// request success
											} failure:^(NSError *error) {
										// request fail
										// get error details  from   error.localizedDescription
	}];

使用手机号码注册账号

使用手机号码注册账号需要上传国家码、手机号码、密码、获取到的验证码等信息。

[[TuyaSmartUser sharedInstance] registerByPhone:countryCode //country code ,like 86 or 1
							phoneNumber:phone
								password:password
									code:code  // VerifyCode
								success:^{

								// register success

								} failure:^(NSError *error) {

						// register fail
							// get error details  from   error.localizedDescription
										}

];

使用手机号码登录账号

账号注册成功后,用户就可以使用手机号码登录账号。

[[TuyaSmartUser sharedInstance] loginByPhone:countryCode
							phoneNumber:phone
							password:password
								success:^{

							// login successfully

							} failure:^(NSError *error) {

							// login fail

	}];

第二步:创建和管理家庭

家庭是智能生活 App SDK 开发下实际场景的最大单位。IoT 设备的添加、编辑、移除、状态变化的监听基于家庭下。用户可以在用户账号下创建任意多个家庭,在指定家庭下,用户还可以添加并管理多个房间和家庭成员。

操作家庭模块时,大家将频繁调用对象 TuyaSmartHomeModel 和 TuyaSmartHome

对象 说明
TuyaSmartHomeModel 存放了家庭的基本信息,如 ID、名字、位置等。
TuyaSmartHome 存放了家庭相关的所有功能,如单个家庭信息管理、家庭下的家庭成员管理、房间管理等。TuyaSmartHome 需要使用正确的 homeId 进行初始化。

创建家庭

在登录状态下,用户可以创建家庭,之后对于房间、成员、设备等对象的管理都基于家庭下。创建家庭需要通过 TuyaSmartHomeManager 调用 创建家庭 接口。

[self.homeManager addHomeWithName:name
                  geoName:city
                  rooms:@[@""]  // we could add rooms after creating the home , so pass a null list firstly .
                  latitude:self.latitude
                  longitude:self.longitude
                  success:^(long long result) {

                       //add success, result here is the homeID .

                  } failure:^(NSError *error) {

                        //add failed

                  }];

 创建家庭接口说明

- (void)addHomeWithName:(NSString *)homeName
                geoName:(NSString *)geoName
                  rooms:(NSArray <NSString *>*)rooms
               latitude:(double)latitude
              longitude:(double)longitude
                success:(TYSuccessLongLong)success
                failure:(TYFailureError)failure;

参数说明

参数 说明
homeName 家庭的名称
geoName 家庭的地址
rooms 家庭下房间的名称列表
latitude 家庭地址纬度
longitude 家庭地址经度
success 成功回调
failure 失败回调

示例代码

Objc:

- (void)addHome {
    [self.homeManager addHomeWithName:@"you_home_name"
                          geoName:@"city_name"
                            rooms:@[@"room_name"]
                         latitude:lat
                        longitude:lon
                          success:^(double homeId) {

        // homeId 创建的家庭的 homeId
        NSLog(@"add home success");
    } failure:^(NSError *error) {
        NSLog(@"add home failure: %@", error);
    }];
}

Swift:

 func addHome() {
    homeManager.addHome(withName: "you_home_name",
                         geoName: "city_name",
                           rooms: ["room_name"],
                        latitude: lat,
                       longitude: lon,
                         success: { (homeId) in
        // homeId 创建的家庭的 homeId
        print("add home success")
    }) { (error) in
        if let e = error {
            print("add home failure: \(e)")
        }
    }
}

查询家庭列表

在登录状态下大家可以直接获取家庭列表。如还没创建过家庭,将返回 空数组

    //get home list and refresh the TableView
    [self.homeManager getHomeListWithSuccess:^(NSArray<TuyaSmartHomeModel *> *homes) {
      // get success , refresh UI
      //  [self.tableView reloadData];
    } failure:^(NSError *error) {

    // get failed

    }];

最佳实践

在创建了家庭后,后续房间成员、用户配网等相关操作均需要基于某一特定家庭,因此建议将这一特定家庭作为 App 的全局变量存储。当然,大家也可以在本地随时切换当前家庭,涂鸦 IoT 开发平台并不会记录这一信息。

在本教程和配套的 Sample 中,默认将列表的第一个家庭设为当前家庭。

+ (TuyaSmartHomeModel *)getCurrentHome {

    NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
    if (![defaults valueForKey:@"CurrentHome"]) {
        return nil;
    }

    long long homeId = [[defaults valueForKey:@"CurrentHome"] longLongValue];

    if (![TuyaSmartHome homeWithHomeId:homeId]) {
        return nil;
    }

    return [TuyaSmartHome homeWithHomeId:homeId].homeModel;
}

+ (void)setCurrentHome:(TuyaSmartHomeModel *)homeModel {

    NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
    [defaults setValue:[NSString stringWithFormat:@"%lld", homeModel.homeId] forKey:@"CurrentHome"];

}

实现以上逻辑后,家庭的操作就可以被简化:

  • 查询家庭列表:

    self.home = [TuyaSmartHome homeWithHomeId:[TYHome getCurrentHome].homeId];
    
  • 设置家庭 ID:

    [TYHome setCurrentHome:xxx];
    

第三步:设备配网

简单来说,配网就是将设备连接并注册到云端,使其拥有与云端远程通信的能力。涂鸦智能生活 App SDK 提供了丰富的配网方式以支持大部分智能设备。如 Wi-Fi 连接,蓝牙连接等。

配网方式介绍

本模块以 Wi-Fi 配网为例介绍如何使用SDK 将设备配置到云端。

Wi-Fi 配网方式包括 EZ、AP、扫 App 二维码三种方式,在之后的 iOS 版本 SDK 中,推荐使用 AP 热点模式 代替 Wi-Fi 快连模式(即EZ模式)。主要原因如下:

  • 相比 EZ 模式,AP 模式成功率高、可靠性好,对手机和路由器有兼容性要求小。AP 模式配网成功率高于 EZ 模式。
  • 当 Xcode 升级至 12.5 版本后,编译出来的 App 无法在大于等于 14.5 版本的 iOS 系统的设备上发出 EZ 配网的数据包。此时,App 需要额外开启一个 com.apple.developer.networking.multicast 的权限。这个权限需要向苹果额外申请,等审批通过后才能够使用。目前临时的解决方案是降低 Xcode 版本,但仍推荐使用 AP 模式。

获取配网 Token

开始配网之前,SDK 需要在联网状态下从涂鸦 获取配网Token,然后才可以开始热点模式配网。Token 的有效期为 10 分钟,且配置成功后就会失效,再次配网需要重新获取。

获取 Token 需要上传当前的 homeId,因此大家需要确保处于登录状态并至少创建了一个家庭。

[[TuyaSmartActivator sharedInstance] getTokenWithHomeId:homeId
                                                success:^(NSString *token) {
		                                    //  NSLog(@"getToken success: %@", token);
		                                   // you could start ConfigWiFi now
	                                      } failure:^(NSError *error) {
		                                 //NSLog(@"getToken failure: %@", error.localizedDescription);
	                                     }
];

获取Token 接口说明

- (void)getTokenWithHomeId:(long long)homeId
                   success:(TYSuccessString)success
                   failure:(TYFailureError)failure;

参数说明

参数 说明
homeId 设备将要绑定到的家庭的 ID
success 成功回调,返回配网 Token
failure 失败回调,返回失败原因

示例代码

Objc:

- (void)getToken {
	[[TuyaSmartActivator sharedInstance] getTokenWithHomeId:homeId success:^(NSString *token) {
		NSLog(@"getToken success: %@", token);
		// TODO: startConfigWiFi
	} failure:^(NSError *error) {
		NSLog(@"getToken failure: %@", error.localizedDescription);
	}];
}

Swift:

func getToken() {
    TuyaSmartActivator.sharedInstance()?.getTokenWithHomeId(homeId, success: { (token) in
        print("getToken success: \(token)")
        // TODO: startConfigWiFi
    }, failure: { (error) in
        if let e = error {
            print("getToken failure: \(e)")
        }
    })
}

iOS 版本适配

iOS 14 版本适配

从 iOS 14 版本开始,在设备配网、局域网本地控制时会触发 本地网络 权限弹窗。

  • 如果用户点击了允许,App 才能够向本地局域网发送数据。
  • 如果用户点击了拒绝,将无法使用相关功能。

目前苹果没有提供任何 API 对此权限进行判断,建议在相关功能无法正常使用时提示、引导用户检查 系统设置 中的 app设置,确认是否开启了 本地网络 权限。

iOS 13 版本适配

从 iOS 13 版本开始,如果用户没有开启地理位置权限,在已开启 Wi-Fi 权限的前提下,[[TuyaSmartActivator sharedInstance] currentWifiSSID] 将获取不到有效的 Wi-Fi SSID 或 BSSID。

在此情况下,iOS 会返回下列默认值:

  • SSID:WLAN 或 Wi-Fi,针对中国大陆地区则是 WLAN
  • BSSID:“00:00:00:00:00:00”

开始设备配网

开始配网前,请确保设备处于待配网状态。操作方法可参考设备的使用说明书。

调用 配网接口,需要提供路由器的 SSID(即 Wi-Fi 名称)、密码、从云端获取的 Token 等。

[TuyaSmartActivator sharedInstance].delegate = self;
[[TuyaSmartActivator sharedInstance] startConfigWiFi:TYActivatorModeAP
                                                ssid:ssid
                                            password:password
                                               token:token
                                             timeout:100];

开始配网 接口说明

- (void)startConfigWiFi:(TYActivatorMode)mode
                   ssid:(NSString *)ssid
               password:(NSString *)password
                  token:(NSString *)token
                timeout:(NSTimeInterval)timeout;

参数说明

参数 说明
mode 配网模式
ssid Wi-Fi 名称
password Wi-Fi 密码
token 配网 Token
timeout 超时时间,默认 100 秒

示例代码

Objc :

- (void)startConfigWiFi:(NSString *)ssid password:(NSString *)password token:(NSString *)token {
	// 设置 TuyaSmartActivator 的 delegate,并实现 delegate 方法
	[TuyaSmartActivator sharedInstance].delegate = self;

	// 开始配网,快连模式对应 mode 为 TYActivatorModeEZ
	[[TuyaSmartActivator sharedInstance] startConfigWiFi:TYActivatorModeEZ ssid:ssid password:password token:token timeout:100];
}

#pragma mark - TuyaSmartActivatorDelegate
- (void)activator:(TuyaSmartActivator *)activator didReceiveDevice:(TuyaSmartDeviceModel *)deviceModel error:(NSError *)error {

	if (!error && deviceModel) {
		//配网成功
    }

    if (error) {
        //配网失败
    }
}

Swift :

func startConfigWiFi(withSsid ssid: String, password: String, token: String) {
    // 设置 TuyaSmartActivator 的 delegate,并实现 delegate 方法
    TuyaSmartActivator.sharedInstance()?.delegate = self

    // 开始配网
    TuyaSmartActivator.sharedInstance()?.startConfigWiFi(TYActivatorModeEZ, ssid: ssid, password: password, token: token, timeout: 100)
}

#pragma mark - TuyaSmartActivatorDelegate
func activator(_ activator: TuyaSmartActivator!, didReceiveDevice deviceModel: TuyaSmartDeviceModel!, error: Error!) {
    if deviceModel != nil && error == nil {
        //配网成功
    }

    if let e = error {
        //配网失败
        print("\(e)")
    }
}

使用 AP 模式配网时,需要先实现 TuyaSmartActivatorDelegate 协议,以监听配网结果的回调。

@interface xxxViewController () <TuyaSmartActivatorDelegate>
- (void)activator:(TuyaSmartActivator *)activator didReceiveDevice:(TuyaSmartDeviceModel *)deviceModel error:(NSError *)error {
    if (deviceModel && error == nil) {
             //success
            // NSLog(@"connected success: %@", deviceModel.name);
    }

    if (error) {
        //fail
    }

   // stop config
}

(可选)停止配网

开始配网操作后,App 会持续广播配网信息,直到配网成功或是超时才停止。如果需要中途取消操作或配网完成,需要调用 停止配网 接口。

 [TuyaSmartActivator sharedInstance].delegate = nil;
 [[TuyaSmartActivator sharedInstance] stopConfigWiFi];

停止配网接口说明

- (void)stopConfigWiFi;

示例代码

Objc:

- (void)stopConfigWifi {
	[TuyaSmartActivator sharedInstance].delegate = nil;
	[[TuyaSmartActivator sharedInstance] stopConfigWiFi];
}

Swift:

func stopConfigWifi() {
    TuyaSmartActivator.sharedInstance()?.delegate = nil
    TuyaSmartActivator.sharedInstance()?.stopConfigWiFi()
}

第四步:控制设备

本章节主要操作对象包含 TuyaSmartDeviceModel 和 TuyaSmartDevice

对象 说明
TuyaSmartDeviceModel
  • TuyaSmartHomeModel 和 TuyaSmartHome 类似,TuyaSmartDeviceModel 存放了设备的基本信息,如 ID、名字、图标等。
  • TuyaSmartDeviceModel 类的 dps 属性(NSDictionary 类型)定义了当前设备的状态,称作数据点(DP,Data Point)或功能点。每个 DP 都存储了了一个设备的功能信息。如开关(布尔值),灯泡的亮度(数值型)等。对于设备的控制都通过获取和修改 DP 值实现。
TuyaSmartDevice TuyaSmartDevice 存放了设备相关的所有功能,如功能控制,设备固件管理等。您需要用正确的 deviceId 初始化一个 TuyaSmartDevice

查询设备列表

设备成功配网后,可以在对应的家庭下查看对应的设备列表。

self.home = [TuyaSmartHome homeWithHomeId:#your homeId];
self.deviceList = [self.home.deviceList copy];

查看设备信息

  • 设备的功能点信息存放在 deviceModel 的 schemaArray 中。

    TuyaSmartDevice *device = self.device;
    NSArray *schemas = device.deviceModel.schemaArray;
    
  • schemaArray 存放了该设备的所有功能点信息,每个功能点被封装成一个TuyaSmartSchemaModel 对象。

  • 对于部分功能点信息复杂的设备,涂鸦将功能点再一次封装在 TuyaSmartSchemaModel 的 property 属性中。具体判断方式如下:

    NSString *type = [schema.type isEqualToString:@"obj"] ? schema.property.type : schema.type;
    
    	if ([type isEqualToString:@"bool"]) {
    
    		SwitchTableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"switchCell"];
    		if (cell == nil){
    			cell = [[[NSBundle mainBundle] loadNibNamed:@"SwitchTableViewCell" owner:self options:nil] lastObject];
    
    			cell.label.text = schema.name;
    			[cell.switchButton setOn:[dps[schema.dpId] boolValue]];
    
    			};
    
    		}
    		return cell;
    
    	}
    
    else if ([type isEqualToString:@"value"]) {
    
    		SliderTableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"valueCell"];
    		if (cell == nil){
    			cell = [[[NSBundle mainBundle] loadNibNamed:@"SliderTableViewCell" owner:self options:nil] lastObject];
    
    			cell.label.text = schema.name;
    			cell.detailLabel.text = [dps[schema.dpId] stringValue];
    			cell.slider.minimumValue = schema.property.min;
    			cell.slider.maximumValue = schema.property.max;
    			cell.slider.value = [dps[schema.dpId] floatValue];
    
    			};
    		};
    		return cell;
    
    	}
    
    	else if ([type isEqualToString:@"enum"]) {
    		//...
    	}
    
    	//...
    

在上述代码中,以智能灯泡为例将其功能点信息展示在 TableView 上。其中:

  • type 为 bool 的 cell 展示了开关的信息。
  • type 为 value 的 cell 展示了其亮度的信息。

控制设备

控制设备需要将对应的 DP 以 NSDictionary 形式通过 设备控制 接口改变设备状态或功能。

 同样以灯泡为例,以下代码分别修改了其开关状态和亮度值。

if ([type isEqualToString:@"bool"]) {

        SwitchTableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"switchCell"];
        if (cell == nil){
            cell = [[[NSBundle mainBundle] loadNibNamed:@"SwitchTableViewCell" owner:self options:nil] lastObject];

            cell.label.text = schema.name;
            [cell.switchButton setOn:[dps[schema.dpId] boolValue]];
            cell.isReadOnly = isReadOnly;
           // turn on/off when click the UISwitch
            cell.switchAction = ^(UISwitch *switchButton) {
                [weakSelf publishMessage:@{schema.dpId: [NSNumber numberWithBool:switchButton.isOn]}];
            };

        }
        return cell;

    }

else if ([type isEqualToString:@"value"]) {

        SliderTableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"valueCell"];
        if (cell == nil){
            cell = [[[NSBundle mainBundle] loadNibNamed:@"SliderTableViewCell" owner:self options:nil] lastObject];

            cell.label.text = schema.name;
            cell.detailLabel.text = [dps[schema.dpId] stringValue];
            cell.slider.minimumValue = schema.property.min;
            cell.slider.maximumValue = schema.property.max;
            [cell.slider setContinuous:NO];
            cell.slider.value = [dps[schema.dpId] floatValue];

            // change the value when tap the UISlider
            cell.sliderAction = ^(UISlider * _Nonnull slider) {
                float step = schema.property.step;
                float roundedValue = round(slider.value / step) * step;
                [weakSelf publishMessage:@{schema.dpId : [NSNumber numberWithInt:(int)roundedValue]}];
            };
         };
        return cell;

    }
- (void)publishMessage:(NSDictionary *) dps {
    [self.device publishDps:dps success:^{
            // change success
    }
    failure:^(NSError *error) {
         // change failed
    }];
}

如果需要监听设备状态的改变,如在线状态、移除通知、功能点状态改变等。需要实现 TuyaSmartDeviceDelegate 协议。

self.device = [TuyaSmartDevice deviceWithDeviceId:## your deviceId];
self.device.delegate = self;
#pragma mark - TuyaSmartDeviceDelegate

/// Device information updates, such as the name and online status.
/// @param device The device instance.
- (void)deviceInfoUpdate:(TuyaSmartDevice *)device;

/// Device online status updates
/// @param device The device instance.
- (void)deviceOnlineUpdate:(TuyaSmartDevice *)device;

/// Indicates whether the device is removed.
/// @param device The device instance.
- (void)deviceRemoved:(TuyaSmartDevice *)device;

/// The DP data updates.
/// @param device The device instance.
/// @param dps The command dictionary.
- (void)device:(TuyaSmartDevice *)device dpsUpdate:(NSDictionary *)dps;

/// The DP data updates.
/// @param device The device instance.
/// @param dpCodes The DP codes.
- (void)device:(TuyaSmartDevice *)device dpCommandsUpdate:(NSDictionary *)dpCodes;

/// The group OTA task progress.
/// @param device The gateway instance.
/// @param groupId group OTA task id.
/// @param type The firmware type.
/// @param progress The update progress.
- (void)device:(TuyaSmartDevice *)device groupOTAId:(long)groupId firmwareType:(NSInteger)type progress:(double)progress;

/// The group OTA task status.
/// @param device The gateway device instance.
/// @param upgradeStatusModel The model of the update status.
- (void)device:(TuyaSmartDevice *)device
    groupOTAStatusModel:(TuyaSmartFirmwareUpgradeStatusModel *)upgradeStatusModel;

/// The callback of Wi-Fi signal strength.
/// @param device The device instance.
/// @param signal The signal strength.
- (void)device:(TuyaSmartDevice *)device signal:(NSString *)signal;

/// Receives MQTT custom messages.
/// @param device The device instance.
/// @param message The custom message.
- (void)device:(TuyaSmartDevice *)device didReceiveCustomMessage:(TuyaSmartMQTTMessageModel *)message;

/// Receives LAN custom messages.
- (void)device:(TuyaSmartDevice *)device didReceiveLanMessage:(TuyaSmartLanMessageModel *)message;

/// The delegate of warning information updates.
/// @param device The device instance.
/// @param warningInfo The warning information.
- (void)device:(TuyaSmartDevice *)device warningInfoUpdate:(NSDictionary *)warningInfo;

/// The delegate of changes in device normal firmware/pid version update's status/progress
/// Notice: sometimes the progress may <0, when it occured please ignore the progress.
/// @param device The device instance.
/// @param statusModel status/progress model.
- (void)device:(TuyaSmartDevice *)device otaUpdateStatusChanged:(TuyaSmartFirmwareUpgradeStatusModel *)statusModel;

/// The thing message data update.
/// Example:
///     type == property:
///         payload = {
///           "code_name1": {
///             "value": "code_value1",
///             "time": 1234567890
///           },
///           "code_name2": {
///             "value": 50,
///             "time": 1234567890
///           }
///         }
///     type == action:
///         payload = {
///            "actionCode": "testAction",
///            "outputParams": {
///              "outputParam1":"outputValue1",
///              "outputParam2":50
///            }
///         }
///     type == event:
///         payload = {
///            "eventCode": "testEvent",
///            "outputParams": {
///              "outputParam1":["outputValue1", "outputValue2"],
///              "outputParam2":false
///            }
///         }
/// @param device The device instance.
/// @param thingMessageType The message type.
/// @param payload The message payload.
- (void)device:(TuyaSmartDevice *)device didReceiveThingMessageWithType:(TuyaSmartThingMessageType)thingMessageType payload:(NSDictionary *)payload;

(可选)移除设备

调用 移除设备 接口,可以将当前设备从对应家庭下移除。

[self.device remove:^{
		NSLog(@"remove success");
	  } failure:^(NSError *error) {
		NSLog(@"remove failure: %@", error);
	  }];

移除设备 接口说明

- (void)remove:(nullable TYSuccessHandler)success failure:(nullable TYFailureError)failure;

参数说明

参数 说明
success 成功回调
failure 失败回调

示例代码

Objective-C:

- (void)removeDevice {
	// self.device = [TuyaSmartDevice deviceWithDeviceId:@"your_device_id"];

	[self.device remove:^{
		NSLog(@"remove success");
	} failure:^(NSError *error) {
		NSLog(@"remove failure: %@", error);
	}];
}

Swift:

func removeDevice() {
	device?.remove({
		print("remove success")
	}, failure: { (error) in
		if let e = error {
			print("remove failure: \(e)")
		}
	})
}

(推荐)集成设备面板

为了减少客户的开发成本,涂鸦针对特定设备提供了一系列的设备控制面板。详情请登录 涂鸦IoT开发平台 参考 全品类控制面板空调品类控制面板

实践结果

学习完本次教程,相信大家已经创建出了一个自己的 App,它可以进行用户账号注册、家庭创建、家庭查询、设备配网、设备控制等。

下一步

为了降低开发者的开发成本,涂鸦将 SDK 中按模块进行了功能抽离和 UI 封装,为大家提供了一整套一键接入的 UI业务包,可以根据需要自由选择需要的业务模块。

版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://blog.csdn.net/Ms_Smart/article/details/127667144

智能推荐

【学习ios之路:Objective-C】NSArray和NSMutableArray_ios 角标越界判断-程序员宅基地

文章浏览阅读1.2k次。1.不可变数组(NSArray)1).不可变数组(NSArray)*数组中只能存放对象.但是对于对象的类型没有限制.* 实例化的时候以nil表示结束* 通过下标索引对象* NSArray无法添加.删除.修改元素.2).创建对象,数组初始化赋值方法. //通过初始化添加数组元素 NSArray *array = [[NSArray alloc_ios 角标越界判断

树莓派的3D模型在STEP格式。SolidWorks、AutoCAD,fusion360可用_树莓派step-程序员宅基地

文章浏览阅读439次,点赞5次,收藏12次。树莓派的3D模型在STEP格式。SolidWorks、AutoCAD,fusion360可用。_树莓派step

Glide-自定义缓存_glide自定义缓存图片名-程序员宅基地

文章浏览阅读1.6w次,点赞9次,收藏11次。前言:在前面的文章中,我们介绍了如何对Glide进行默认配置的基础知识,现在我们就来介绍如何配置自定义缓存1.如何使用GlideModule首先我们要对Glide进行默认配置,需要了解如何使用GlideModule,前面文章已经做了详细介绍了,这边就不再介绍了如何使用GlideModulehttp://blog.csdn.net/yulyu/article/details/55194237前面还介绍_glide自定义缓存图片名

98dx166switch交换芯片接口移植(一):SMI接口以及MII接口_stmmac适配switch芯片-程序员宅基地

文章浏览阅读3.2k次。一:交换机的原理机制信号转发的网络设备,介入交换机的任意两个节点共享信号通路,工作与OSI的数据链路层,同事可以进行多个端口的数据传输,交换机上电后会自动创建一个端口地址表,叫做MAC地址表,,会记录mac地址和哪个端口连接,然后自动学习,每次进到交换机的信息,都会记录下穿送过来的设备地址的mac地址,过程就是,学习mac地址,广播mac地址,查找mac地址,配对mac地址。二:switc..._stmmac适配switch芯片

华为勇敢星实习生招聘面试经历和华为优招面试经历_华为勇敢星实习生面试-程序员宅基地

文章浏览阅读2.7w次,点赞7次,收藏23次。我参加的是华为2017年(针对18年毕业的应届生)武长地区的华为优招,面试之前也在网上搜了很长时间的关于优招的面试经验贴,没有搜到多少相关的资料。所以写下这篇帖子,希望能够帮到后续参加华为优招的同学。  先说下我参加华为勇敢星实习招聘的经历吧(因为过了实习可以省很多事情):  华为发出招聘勇敢星实习计划后,在官网注册简历,投递简历。这里要说明一下,找人内推没什么用,至今也没听说谁需要找华为的员工内推_华为勇敢星实习生面试

(四)嵌入式 Linux驱动程序设计之杂项设备驱动_qemu misc-程序员宅基地

文章浏览阅读206次。(四)嵌入式 Linux驱动程序设计之杂项设备驱动接上篇:(三)嵌入式 Linux驱动程序设计之驱动编译进内核linux三大设备驱动字符设备:IO的传输过程是以字符为单位的,没有缓冲,如:I2C,SPI;块设备:IO传输过程以块为单位,根存储相关的都是块设备,如:tf卡,EMMC;网络设备:以套接字来访问的.1.杂项设备驱动属于字符设备,杂项设备可以自动生成设备节点.我们系统里有很多杂项设备,开发板可以使用cat /proc/misc/查看;虚拟机在/dev/下;2.杂项设备除了比字符设备代_qemu misc

随便推点

corn表达式详解_corn下午2点如何表达-程序员宅基地

文章浏览阅读3.2k次。cornexpression表达式详解:1、格式cron一共有7位,但是最后一位是年,可以留空,所以我们可以写6位:字段允许值允许特殊字符秒0-59, - * /分0-59, - * /小时0-23, - * /日1-31, - * ? / L W C月1-12或JAN-DEC, - * /周1-7或SUN-SAT,..._corn下午2点如何表达

运用java反射机制获取实体方法报错,java.lang.NoSuchMethodException: int.<init>(java.lang.String)...-程序员宅基地

文章浏览阅读471次。错误的原因是我的Student实体,成员变量数据类型,使用了int基本数据类型,改成Integer包装类型即可。转载于:https://www.cnblogs.com/pandaQQQ/p/9693033.html..._(java.lang.string)

ZYNQ-UART串口中断测试_zynq 串口中断-程序员宅基地

文章浏览阅读4.9k次,点赞10次,收藏66次。学习内容本文主要介绍关于ZYNQ芯片的串口中断功能,并编写相关测试代码开发环境vivado 18.3&SDK,PYNQ-Z2开发板。UART控制器简介UART控制器是一个全双工异步接收和发送,支持可编程波特率和I/O信号格式。 该控制器可实现奇偶校验自动生成和多主检测模式。UART操作由配置和模式寄存器控制。FIFO、调制解调器信号和其他控制器功能的状态是使用状态、中断状态和调制解调器状态寄存器读取的。UART控制器有独立的RX和TX数据路径。每个路径包括一个64字节的FIFO。 控制_zynq 串口中断

linux_centos安装openslide_libopenjp2-程序员宅基地

文章浏览阅读2.6k次。开发十年,就只剩下这套Java开发体系了&gt;&gt;&gt; ..._libopenjp2

利用swagger组件测试excel下载,打开文件乱码。-程序员宅基地

文章浏览阅读1.4w次,点赞9次,收藏36次。最近项目遇到个问题,就是利用swagger下载excel时,得到的文件打开总是乱码,首先怀疑是response的content-type有问题,将application试遍了,“x-msdownload”,“vnd.ms-excel”,“vnd.openxmlformats-officedocument.spreadsheetml.sheet”,“octet-stream”这些试了都不行,具体的类...

Linux 安装telnet_linux telnet安装-程序员宅基地

文章浏览阅读3.5w次,点赞8次,收藏62次。Linux 安装telnet_linux telnet安装

推荐文章

热门文章

相关标签