Overview
Many apps need a second device: a camera and a viewer, a phone and a tablet, a kiosk and an admin phone. Signing in on that second device is where users give up: they have to remember a username, type a password, or wait for an e-mail code.
KlugRegister turns that step into one camera shot. The first device creates a QR code; the second device scans it with a native scanner and the app signs in. The QR code carries whatever your app needs, typically a one-time code from your server, never the password itself.
Both parts are native: QR codes are generated by the system (sharp at any size, as an AIR BitmapData ready to show), and the scanner is native: a full-screen camera view with your own hint text on iOS, and Google's code scanner on Android, which needs no camera permission at all.
KlugRegister runs in the current release of our apps, our proof of concept: after registration the app shows a QR code, and the second device is paired in seconds, even right after installing the app from the store.
Features
- Self-contained: one ANE, no core library or dependency ANEs to add
- Create QR codes from any text or URL, returned as BitmapData with a proper quiet zone
- Choose the size in pixels per module, crisp on any screen
- Native full-screen camera scanner with your own hint text and cancel button
- Asks for camera permission and reports when it is denied
- Android: Google code scanner from Play services, no camera permission needed
- Works in portrait and landscape, on phones and tablets
- iOS and macOS: only the system frameworks; Android: ZXing and the Google code scanner, resolved automatically when the app is packaged
Supported platforms
Where a feature is not available, isSupported and isScanSupported return false, so the same code can stay in every app.
Getting started
Add the extension to your application descriptor:
<extensions>
<extensionID>com.klug.register.KlugRegister</extensionID>
</extensions>
For scanning on iOS, add a camera usage description to the InfoAdditions:
<key>NSCameraUsageDescription</key> <string>Scan the QR code of your first device</string>
Code examples
Four complete flows for pairing a second device. Creating a code is immediate; the scanner result arrives as a KlugRegisterEvent. Full documentation →
import com.klug.register.KlugRegister; import com.klug.register.KlugRegisterEvent; import flash.display.Bitmap; import flash.display.BitmapData; var reg:KlugRegister = KlugRegister.getInstance(); if ( reg.isSupported ) // Android, iOS, macOS { // a short-lived one-time code from your server, never the password var bmp:BitmapData = reg.createQRCode( "https://your.server/pair?t=" + oneTimeCode, 10 ); if ( bmp != null ) // null: no code could be made from the text { var qr:Bitmap = new Bitmap( bmp ); // black on white, 4-module quiet zone included qr.x = ( stage.stageWidth - qr.width ) / 2; qr.y = 120; addChild( qr ); } }
reg.addEventListener( KlugRegisterEvent.SCANNED, onScanned ); reg.addEventListener( KlugRegisterEvent.CANCELED, onScanCanceled ); reg.addEventListener( KlugRegisterEvent.ERROR, onScanError ); function startScan():void { if ( !reg.isScanSupported ) { showCodeEntry(); // your app function: type the one-time code instead return; } // iOS: full-screen scanner with your hint and button; macOS 13+: a sheet on the app window; // Android: Google's own localized scanner, hint and cancel title are not used if ( !reg.scanQRCode( "Point the camera at the code on your first device", "Cancel" ) ) trace( "a scanner is already open" ); }
function onScanned( e:KlugRegisterEvent ):void { var prefix:String = "https://your.server/pair?t="; if ( e.text.indexOf( prefix ) != 0 ) { showMessage( "This is not a pairing code." ); // your app function return; } var vars:URLVariables = new URLVariables(); vars.t = e.text.substr( prefix.length ); var req:URLRequest = new URLRequest( "https://your.server/pair" ); req.method = URLRequestMethod.POST; req.data = vars; var loader:URLLoader = new URLLoader(); loader.addEventListener( Event.COMPLETE, function( ev:Event ):void { signInWith( String( loader.data ) ); // your app function: the server's answer }); loader.load( req ); }
function onScanCanceled( e:KlugRegisterEvent ):void { showPairingScreen(); // the user closed the scanner: back to the screen, no message } function onScanError( e:KlugRegisterEvent ):void { switch ( e.errorCode ) { case "denied": // iOS, macOS: camera permission refused showMessage( "Allow camera access in Settings to scan the code." ); break; case "nocamera": // iOS, macOS: no usable camera showCodeEntry(); break; default: // Android: "scanner" (e.g. scanner not ready yet) or "empty" showMessage( "The scanner could not start: " + e.errorMessage ); } }
API overview
| KlugRegister.getInstance() | Returns the single instance. |
| isSupported | True where QR codes can be created (Android, iOS, macOS). |
| isScanSupported | True where the scanner is available: Android, iOS, and macOS 13 or later with a camera. |
| createQRCode(text, modulePx) | Returns the QR code as BitmapData, black on white, with a 4-module quiet zone; modulePx pixels per module (default 8). Null if no code could be made. |
| scanQRCode(hint, cancelTitle) | Opens the scanner: full screen on iOS, a sheet on the Mac, Google's scanner on Android (hint and title not used there). The result arrives as an event. Returns false if a scanner is already open. |
| KlugRegisterEvent | text, errorCode, errorMessage. |
Events
| KlugRegisterEvent.SCANNED | A code was read; e.text holds its content. |
| KlugRegisterEvent.CANCELED | The user closed the scanner. |
| KlugRegisterEvent.ERROR | e.errorCode: denied (no camera permission) · nocamera on iOS and macOS; scanner · empty on Android. Details in e.errorMessage. |
Buy KlugRegister
A yearly licence for one AIR application, with all updates for 12 months. After payment you receive the extension, the ActionScript library and the documentation by e-mail, usually within one business day. Licence and terms
- Licence for one AIR application
- All updates for 12 months
- Answer by e-mail within 7 days
- Licence for one AIR application
- All updates for 12 months
- Answer by e-mail within 48 hours
Requirements
| AIR SDK | 51.x (HARMAN) |
| Android | Android 6 or later, Google Play services (scanner) |
| iOS | iOS 13 or later |
| macOS | macOS 10.15 or later (creating QR codes); macOS 13 or later for scanning |
| Permissions | iOS and macOS: camera, for scanning (NSCameraUsageDescription); Android: none |