payfrit-user/ios/Runner/AppDelegate.swift
John Mizerek 56f1e1cf63 Add native iOS beacon scanner with CoreBluetooth
- BeaconScanner.swift: Native scanner using CBCentralManager
- AppDelegate.swift: Wire up MethodChannel (same API as Android)
- beacon_channel.dart: Support iOS in isSupported check
- beacon_scanner_service.dart: Use native scanner on both platforms

iOS now gets the same fast 2-second scan as Android.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
2026-01-27 08:36:40 -08:00

62 lines
2.1 KiB
Swift

import Flutter
import UIKit
@main
@objc class AppDelegate: FlutterAppDelegate {
private let channelName = "com.payfrit.app/beacon"
private var beaconScanner: BeaconScanner?
override func application(
_ application: UIApplication,
didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?
) -> Bool {
GeneratedPluginRegistrant.register(with: self)
// Set up beacon scanner method channel
guard let controller = window?.rootViewController as? FlutterViewController else {
return super.application(application, didFinishLaunchingWithOptions: launchOptions)
}
beaconScanner = BeaconScanner()
let channel = FlutterMethodChannel(name: channelName, binaryMessenger: controller.binaryMessenger)
channel.setMethodCallHandler { [weak self] (call: FlutterMethodCall, result: @escaping FlutterResult) in
guard let self = self, let scanner = self.beaconScanner else {
result(FlutterError(code: "UNAVAILABLE", message: "Beacon scanner not initialized", details: nil))
return
}
switch call.method {
case "hasPermissions":
result(scanner.hasPermissions())
case "isBluetoothEnabled":
result(scanner.isBluetoothEnabled())
case "startScan":
var regions: [String] = []
if let args = call.arguments as? [String: Any],
let regionList = args["regions"] as? [String] {
regions = regionList
}
scanner.startScan(regions: regions) { beacons in
result(beacons)
} onError: { error in
result(FlutterError(code: "SCAN_ERROR", message: error, details: nil))
}
case "stopScan":
scanner.stopScan()
result(nil)
default:
result(FlutterMethodNotImplemented)
}
}
return super.application(application, didFinishLaunchingWithOptions: launchOptions)
}
}