From d28306b1725e0568f434dff8f84cdb1ad862c46d Mon Sep 17 00:00:00 2001 From: denggaofeng <1139968554@qq.com> Date: Mon, 20 Apr 2026 15:55:15 +0800 Subject: [PATCH] =?UTF-8?q?=E9=87=8D=E5=86=99NFCHelper?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Platforms/Android/MainActivity.cs | 135 ++++++++++++++---- .../Platforms/Android/NFCCallbacks.cs | 22 +-- .../Platforms/Android/NFCLockHelper.cs | 125 ++++++++++++++++ 3 files changed, 245 insertions(+), 37 deletions(-) create mode 100644 NFCLockDemoV2/Platforms/Android/NFCLockHelper.cs diff --git a/NFCLockDemoV2/Platforms/Android/MainActivity.cs b/NFCLockDemoV2/Platforms/Android/MainActivity.cs index 0db7612..8a72280 100644 --- a/NFCLockDemoV2/Platforms/Android/MainActivity.cs +++ b/NFCLockDemoV2/Platforms/Android/MainActivity.cs @@ -7,55 +7,138 @@ using Android.OS; using Com.Lvcheng.Lock.Shared.Nfc.Example.Java; using NFCLockDemoV2; using NFCLockDemoV2.Platforms.Android; -using NFCLockDemoV2.ViewModels; -using Microsoft.Maui; -using Microsoft.Maui.Controls; +using System.Diagnostics; namespace NFCLockAppV2; [Activity(Theme = "@style/Maui.SplashTheme", MainLauncher = true, LaunchMode = LaunchMode.SingleTop, ConfigurationChanges = ConfigChanges.ScreenSize | ConfigChanges.Orientation | ConfigChanges.UiMode | ConfigChanges.ScreenLayout | ConfigChanges.SmallestScreenSize | ConfigChanges.Density, Exported = true)] [IntentFilter(new[] { Intent.ActionMain }, Categories = new[] { Intent.CategoryLauncher })] -[IntentFilter(new[] { NfcAdapter.ActionNdefDiscovered }, Categories = new[] { Intent.CategoryDefault }, DataMimeType = "text/plain")] +[IntentFilter(new[] { NfcAdapter.ActionNdefDiscovered, NfcAdapter.ActionTechDiscovered, NfcAdapter.ActionTagDiscovered }, Categories = new[] { Intent.CategoryDefault }, DataMimeType = "text/plain")] public class MainActivity : MauiAppCompatActivity { - private NFCHelper? nfcHelper; - private NFCCallbacks? NFCCallbacks; + private NFCLockHelper nfcHelper; + private NFCCallbacks _callbacks; + + //private NfcAdapter _nfcAdapter; + //private PendingIntent _pendingIntent; + //private string[][] _techLists = [[typeof(NfcA).FullName, typeof(NdefFormatable).FullName, typeof(MifareUltralight).FullName]]; + //private IntentFilter[] _intentFilters = [new(NfcAdapter.ActionNdefDiscovered), new(NfcAdapter.ActionTechDiscovered), new(NfcAdapter.ActionTagDiscovered)]; + //private volatile bool _processing = false; protected override void OnCreate(Bundle savedInstanceState) { base.OnCreate(savedInstanceState); + _callbacks = new NFCCallbacks(); + nfcHelper = new NFCLockHelper(this, _callbacks); + //_nfcAdapter = NfcAdapter.GetDefaultAdapter(this); + //_pendingIntent = PendingIntent.GetActivity(this, 0, new Intent(this, typeof(MainActivity)).AddFlags(ActivityFlags.ReceiverReplacePending), PendingIntentFlags.Mutable); + } - - private void InitializeNFC() - { - if (Microsoft.Maui.Controls.Application.Current?.Handler?.MauiContext?.Services != null) - { - NFCCallbacks = Microsoft.Maui.Controls.Application.Current.Handler.MauiContext.Services.GetService(); - } - - if (NFCCallbacks != null) - { - nfcHelper = new NFCHelper(this, NFCCallbacks); - } - } - + protected override void OnResume() { base.OnResume(); - // 确保NFC功能在每次恢复时都已初始化 - InitializeNFC(); - nfcHelper?.OnResume(); + nfcHelper.OnResume(); + //if (_nfcAdapter != null) + //{ + // _nfcAdapter.EnableForegroundDispatch(this, _pendingIntent, _intentFilters, _techLists); + //} } - + protected override void OnPause() { base.OnPause(); - nfcHelper?.OnPause(); + nfcHelper.OnPause(); + //if (_nfcAdapter != null) + //{ + // _nfcAdapter.DisableForegroundDispatch(this); + //} } protected override void OnNewIntent(Intent intent) { base.OnNewIntent(intent); - nfcHelper?.OnNewIntent(intent); + nfcHelper.OnNewIntent(intent); + //if (!_processing) + //{ + + // if (intent != null && (intent.Action == NfcAdapter.ActionNdefDiscovered || + // intent.Action == NfcAdapter.ActionTechDiscovered || + // intent.Action == NfcAdapter.ActionTagDiscovered)) + // { + + // Task.Run(async () => + // { + // try + // { + // _processing = true; + // Tag? tag = intent.GetParcelableExtra(NfcAdapter.ExtraTag) as Tag; + // if (tag != null) + // { + // NfcA? nfcA = NfcA.Get(tag); + // if (nfcA != null) + // { + // nfcA.Connect(); + // nfcA.Timeout = 1000; + // Process(nfcA); + // } + // } + // } + // catch (Exception e) + // { + // _callbacks.OnLost(); + // Console.WriteLine(e); + // } + // finally + // { + // await Task.Delay(2000); + // _processing = false; + // _callbacks.OnFinished(); + // } + // }); + // } + //} + + } + + private void Process(NfcA nfcA) + { + DeviceManagerWrapper wrapper = new DeviceManagerWrapper(nfcA); + + try + { + Com.Lvcheng.Lock.Shared.Nfc.Result initRes = wrapper.Init(); + if (initRes.Equals(Com.Lvcheng.Lock.Shared.Nfc.Result.Ok)) + { + long? id; + bool? isNew; + int? mRssi; + + // ѭ do-while + while (true) + { + Com.Lvcheng.Lock.Shared.Nfc.Result getInfoRes = wrapper.Info; + if (!getInfoRes.Equals(Com.Lvcheng.Lock.Shared.Nfc.Result.Ok)) + return; + + _ = wrapper.Rssi; + id = wrapper.MGetId().LongValue(); + isNew = wrapper.MGetIsNew().BooleanValue(); + mRssi = wrapper.MGetRssi().IntValue(); + + // жǷѭ + bool continueLoop = _callbacks.OnLoop(wrapper, id, isNew, mRssi); + System.Diagnostics.Debug.WriteLine("continueLoop:" + continueLoop); + + // ˳ѭ + if (!continueLoop) + break; + } + } + } + catch (Exception e) + { + Console.WriteLine(e); + } } } \ No newline at end of file diff --git a/NFCLockDemoV2/Platforms/Android/NFCCallbacks.cs b/NFCLockDemoV2/Platforms/Android/NFCCallbacks.cs index 14accc1..eb9b8ac 100644 --- a/NFCLockDemoV2/Platforms/Android/NFCCallbacks.cs +++ b/NFCLockDemoV2/Platforms/Android/NFCCallbacks.cs @@ -6,13 +6,13 @@ using Exception = System.Exception; namespace NFCLockDemoV2.Platforms.Android { - public class NFCCallbacks : Java.Lang.Object, INFCCallbacks + public class NFCCallbacks { private readonly MainViewModel mainViewModel; private ViewModels.OperationType? Operation => mainViewModel.Operation; - public NFCCallbacks(MainViewModel mainViewModel) + public NFCCallbacks() { - this.mainViewModel = mainViewModel; + mainViewModel = Application.Current?.Handler?.MauiContext?.Services.GetService(); } public void OnFinished() @@ -24,7 +24,7 @@ namespace NFCLockDemoV2.Platforms.Android mainViewModel.ArcProgress = 0; } - public Java.Lang.Boolean? OnLoop(DeviceManagerWrapper? wrapper, Long? id, Java.Lang.Boolean? isNew, Integer? rssi) + public bool OnLoop(DeviceManagerWrapper? wrapper, long? id, bool? isNew, int? rssi) { try { @@ -63,12 +63,12 @@ namespace NFCLockDemoV2.Platforms.Android { mainViewModel.UpdateMessage("验证失败"); // 返回 false 手动结束 NFC 连接 - return new Java.Lang.Boolean(false); + return false; } else { mainViewModel.UpdateMessage("充电失败"); - return new Java.Lang.Boolean(false); + return false; } // 添加短暂延迟以避免过度频繁的循环 @@ -89,7 +89,7 @@ namespace NFCLockDemoV2.Platforms.Android { mainViewModel.UpdateMessage("开锁失败"); } - return new Java.Lang.Boolean(false); + return false; case ViewModels.OperationType.LOCK: if (wrapper.Control(password, true) == Com.Lvcheng.Lock.Shared.Nfc.Result.Ok) @@ -100,7 +100,7 @@ namespace NFCLockDemoV2.Platforms.Android { mainViewModel.UpdateMessage("关锁失败"); } - return new Java.Lang.Boolean(false); + return false; case ViewModels.OperationType.SET_PASSWORD: if (wrapper.SetKey(password, "") == Com.Lvcheng.Lock.Shared.Nfc.Result.Ok) @@ -111,17 +111,17 @@ namespace NFCLockDemoV2.Platforms.Android { mainViewModel.UpdateMessage("设置密码失败"); } - return new Java.Lang.Boolean(false); + return false; } } - return new Java.Lang.Boolean(true); + return true; } catch (Exception ex) { Log.Error("NFCCallbacks", "Error in OnLoop: " + ex.Message); mainViewModel.UpdateMessage("操作异常: " + ex.Message); - return new Java.Lang.Boolean(false); + return false; } } diff --git a/NFCLockDemoV2/Platforms/Android/NFCLockHelper.cs b/NFCLockDemoV2/Platforms/Android/NFCLockHelper.cs new file mode 100644 index 0000000..e678198 --- /dev/null +++ b/NFCLockDemoV2/Platforms/Android/NFCLockHelper.cs @@ -0,0 +1,125 @@ +using Android.App; +using Android.Content; +using Android.Nfc; +using Android.Nfc.Tech; +using AndroidX.Activity; +using Com.Lvcheng.Lock.Shared.Nfc.Example.Java; +using NFCLockAppV2; +using NFCLockDemoV2.Platforms.Android; + +namespace NFCLockDemoV2; + +public class NFCLockHelper +{ + private readonly MainActivity _activity; + private readonly NFCCallbacks _callbacks; + + private readonly NfcAdapter _nfcAdapter; + private readonly PendingIntent _pendingIntent; + private string[][] _techLists = [[typeof(NfcA).FullName, typeof(NdefFormatable).FullName, typeof(MifareUltralight).FullName]]; + private IntentFilter[] _intentFilters = [new(NfcAdapter.ActionNdefDiscovered), new(NfcAdapter.ActionTechDiscovered), new(NfcAdapter.ActionTagDiscovered)]; + private volatile bool _processing = false; + + public NFCLockHelper(MainActivity activity, NFCCallbacks callbacks) + { + _activity = activity; + _callbacks = callbacks; + _nfcAdapter = NfcAdapter.GetDefaultAdapter(_activity); + _pendingIntent = PendingIntent.GetActivity(_activity, 0, new Intent(_activity, typeof(MainActivity)).AddFlags(ActivityFlags.ReceiverReplacePending), PendingIntentFlags.Mutable); + } + + public void OnResume() + { + if (_nfcAdapter != null) + { + _nfcAdapter.EnableForegroundDispatch(_activity, _pendingIntent, _intentFilters, _techLists); + } + } + + public void OnPause() + { + if (_nfcAdapter != null) + { + _nfcAdapter.DisableForegroundDispatch(_activity); + } + } + + public void OnNewIntent(Intent intent) + { + if (!_processing) + { + + if (intent != null && (intent.Action == NfcAdapter.ActionNdefDiscovered || + intent.Action == NfcAdapter.ActionTechDiscovered || + intent.Action == NfcAdapter.ActionTagDiscovered)) + { + Task.Run(async() => + { + try + { + _processing = true; + Tag? tag = intent.GetParcelableExtra(NfcAdapter.ExtraTag) as Tag; + if (tag != null) + { + NfcA? nfcA = NfcA.Get(tag); + if (nfcA != null) + { + nfcA.Connect(); + nfcA.Timeout = 1000; + Process(nfcA); + } + } + } + catch (Exception e) + { + _callbacks.OnLost(); + Console.WriteLine(e); + } + finally + { + await Task.Delay(2000); + _processing = false; + _callbacks.OnFinished(); + } + }); + } + } + } + + private void Process(NfcA nfcA) + { + DeviceManagerWrapper wrapper = new DeviceManagerWrapper(nfcA); + + try + { + Com.Lvcheng.Lock.Shared.Nfc.Result initRes = wrapper.Init(); + if (initRes.Equals(Com.Lvcheng.Lock.Shared.Nfc.Result.Ok)) + { + long? id; + bool? isNew; + int? mRssi; + + while (true) + { + Com.Lvcheng.Lock.Shared.Nfc.Result getInfoRes = wrapper.Info; + if (!getInfoRes.Equals(Com.Lvcheng.Lock.Shared.Nfc.Result.Ok)) + return; + + _ = wrapper.Rssi; + id = wrapper.MGetId().LongValue(); + isNew = wrapper.MGetIsNew().BooleanValue(); + mRssi = wrapper.MGetRssi().IntValue(); + + bool continueLoop = _callbacks.OnLoop(wrapper, id, isNew, mRssi); + + if (!continueLoop) + break; + } + } + } + catch (Exception e) + { + Console.WriteLine(e); + } + } +} \ No newline at end of file