【Delphi】中使用消息Messages(七)Android 系统消息

19 篇文章 0 订阅
9 篇文章 1 订阅

前面6节介绍了Delphi中消息机制的基本原理,并通过一个演示程序进行实际演示。本节开始,我讲介绍Delphi开发Android系统时需要使用的一些特殊消息。以下所说系统,泛指Android系统。

一、问题的提出:

  1. App中主动调用android系统中蓝牙打开功能,如何知道用户是否真的打开了蓝牙?
  2. App运行的过程中,如何自动感知用户的某些操作,例如:打开或者关闭蓝牙功能、打开或者关闭WIFI功能等?

二、问题的解决:

首先我们解决第一个问题,App中主动调用android系统中蓝牙打开功能,如何知道用户是否真的打开了蓝牙?如下图,程序检测到系统没有打开蓝牙功能,用户按下【立即打开蓝牙功能】,系统会启动打开蓝牙功能的界面,就是下图中最下面的“APP_BOX应用,想要打开蓝牙”白色部分,因为打开蓝牙需要用户同意,所以系统会显示如下选择界面。请注意,下面的白色部分不是我们App显示的,是系统自己提示的。用户可以选择拒绝或者允许问题来了,我们App如何获取用户的选择?如果我们能够获取到用户的选择结果,那么我们会根据用户的不同选择进行提示,这样是不是我们的App就会非常的友好?答案是当然的!(这个界面是小米手机 android 10版本的显示,不同的的android版本,界面可能略有不同,应该一看就明白)。

在解决第一个问题的时候,必须首先要解决的是如何在我们的App中发起系统打开蓝牙的功能,这个不是重点,所以只列出代码。

App打开蓝牙功能的代码:

uses
   ...
   Androidapi.JNI.Bluetooth,
   Androidapi.JNI.GraphicsContentViewText;

  Intent := TJIntent.JavaClass.init(TJBluetoothAdapter.JavaClass.ACTION_REQUEST_ENABLE);
  //打开设置界面
  TAndroidHelper.Activity.startActivityForResult(intent, FS_BlueTooth_Code);
//TAndroidHelper.Activity.startActivity(Intent);

需要注意以上代码,我们使用的是startActivityForResult而不是startActivity,如果使用startActivity我们的App将无法获取到用户选择的结果。这两个函数有一个区别就是startActivityForResult 需要一个消息代码参数FS_BlueTooth_Code,这个参数就是我们需要接收android系统通知消息的关键,从这个参数我们就知道是打开蓝牙功能。

如果我们通过 startActivityForResult发起打开蓝牙调用,Android系统将会按照广播消息的机制把用户选择的结果通知到App,使用的是我们前面讲的RTL消息机制。非常关键的就是Android系统使用的一个在Androidapi.Helpers.pas单元中定义的专用消息类TMessageResultNotification

{ TMessageResultNotification }
type
  TMessageResultNotification = class(TMessage<JIntent>)
  public
    RequestCode: Integer;
    ResultCode: Integer;
  end;

其中RequestCode就是我们调用蓝牙打开功能时使用的FS_BlueTooth_Code。

//打开设置界面
  TAndroidHelper.Activity.startActivityForResult(intent, FS_BlueTooth_Code);

ResultCode就表示用户最终选择的结果。通过以上的分析,现在如果需要获取用户的选择就很清楚了,我们注册一个TMessageResultNotification消息接收器,就可以接收到用户的选择了。

var
  Intent : JIntent;
begin
  //1. 注册消息接收
  FS_FMessageSubscriptionID := TMessageManager.DefaultManager.SubscribeToMessage
    (TMessageResultNotification, FS_HandleActivityMessage);

  Intent := TJIntent.JavaClass.init(TJBluetoothAdapter.JavaClass.ACTION_REQUEST_ENABLE);
  //2. 打开设置界面
  TAndroidHelper.Activity.startActivityForResult(intent, FS_BlueTooth_Code);
//TAndroidHelper.Activity.startActivity(Intent);
end;

监听接收器处理函数:FS_HandleActivityMessage调用实际的处理函数FS_OnActivityResult

procedure TClassic_BlueTooth.FS_HandleActivityMessage(
  const Sender: TObject; const M: TMessage);
begin
  if M is TMessageResultNotification then
  begin
    FS_OnActivityResult(TMessageResultNotification(M).RequestCode,
      TMessageResultNotification(M).ResultCode,
      TMessageResultNotification(M).Value);
  end;
end;

实际的处理函数:FS_OnActivityResult

function TClassic_BlueTooth.FS_OnActivityResult(RequestCode,
  ResultCode: Integer; Data: JIntent): Boolean;
begin
  //解除消息接收,因为已经得到结果了
  TMessageManager.DefaultManager.Unsubscribe(TMessageResultNotification, FS_FMessageSubscriptionID);
  FS_FMessageSubscriptionID := 0;
  //这一句用来判断是不是我们发起的 Intent
  if RequestCode <> FS_BlueTooth_Code then
    Exit(False);

  Result := ResultCode = TJActivity.JavaClass.RESULT_OK;   //表示蓝牙打开

  try
    FBlueProc(Result);
  except on E: Exception do
  end;

end;

函数FS_OnActivityResult的执行结果True表示用户打开了蓝牙功能,False表示用户拒绝打开蓝牙功能。无论用户时选择拒绝还是不进行任何选择,结果都是False,只有用户点允许才会返回True。

总结:

  1. 调用系统功能使用startActivityForResult函数;
  2. 必须订阅(注册)TMessageResultNotification专用消息(用于Intent);
  3. 通过ResultCode = TJActivity.JavaClass.RESULT_OK来判断用户选择结果;
  4. 蓝牙功能是比较典型的,这里演示的是一个Intent消息;
  5. 只要系统的选择界面出现,如果用户不进行任何选择,我们的程序是失活的。

下一节:【Delphi】中使用消息Messages(八)Android 系统消息2​​​​​​​

如果本文对你有帮助,请点赞👍👍! 如果有不明白的地方,可以与我交流,共同学习。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

海纳老吴

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值