Developing a Wi-Fi QR Code Scanner and Generator
Tags: scan, wifi, hms
Published: 2022-03-16 09:21:15

Let's be honest: We can't function without the Internet. No matter where we go, we're always looking for ways to hook up the net.

Although more and more public places are offering free Wi-Fi networks, connecting to them remains a tiresome process. Many free Wi-Fi networks require users to register on a web page, click on an ad, or download a certain app, before granting Internet access.

As a developer, I have been scratching my head over an easier way for connecting to Wi-Fi networks. And then I came across the barcode-scanning feature of Scan Kit, which allows business owner to create a QR code that customers can scan with their phones to quickly connect to a Wi-Fi network. What's more, customers can even share the QR code with people around them. This speeds up the Wi-Fi connection process with customers' personal data properly protected.

## Technical Principles
The barcode-scanning Wi-Fi connection solution requires only two capabilities: barcode generation and barcode scanning.

## Development Procedure
### Building Scanning Capabilities
1.Configure the Huawei Maven repository address.
Go to **buildscript > repositories** and configure the Maven repository address for the HMS Core SDK. Repeat this step for **allprojects > repositories**.
```
buildscript {
    repositories {
        google()
        jcenter()
        // Configure the Maven repository address for the HMS Core SDK.
        maven {url 'https://developer.huawei.com/repo/'}
    }
}

allprojects {
    repositories {
        google()
        jcenter()
        // Configure the Maven repository address for the HMS Core SDK.
        maven {url 'https://developer.huawei.com/repo/'}
    }
}
```
In Gradle 7.0 or later, configuration under **allprojects > repositories** is migrated to the project-level **settings.gradle** file. The following is a configuration example of the **settings.gradle** file:
```
dependencyResolutionManagement {
    ...
    repositories {
        google()
        jcenter() 
        maven {url 'https://developer.huawei.com/repo/'}
    }
}
```
2.Add build dependencies
```
dependencies{
 // Scan SDK.
    implementation 'com.huawei.hms:scan:2.3.0.300'
}
```
3.Configure obfuscation scripts.
Open the obfuscation configuration file **proguard-rules.pro** in the app's root directory of the project, and add configurations to exclude the HMS Core SDK from obfuscation.
```
-ignorewarnings
-keepattributes *Annotation*
-keepattributes Exceptions
-keepattributes InnerClasses
-keepattributes Signature
-keepattributes SourceFile,LineNumberTable
-keep class com.huawei.hianalytics.**{*;}
-keep class com.huawei.updatesdk.**{*;}
-keep class com.huawei.hms.**{*;}
```
4.Add permissions to the **AndroidManifest.xml** file
```
<!-- Camera permission -->
<uses-permission android:name="android.permission.CAMERA" />
<!-- File read permission -->
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
```
5.Dynamically request the permissions
```
ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.CAMERA, Manifest.permission.READ_EXTERNAL_STORAGE}, requestCode);
```
6.Check the permission request result
```
@Override
    public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
        super.onRequestPermissionsResult(requestCode, permissions, grantResults);
		
  if (permissions == null || grantResults == null) {
            return;
        }
        // The permissions are successfully requested or have been assigned.
        if (requestCode == CAMERA_REQ_CODE) {
   // Scan barcodes in Default View mode.
   // Parameter description:
   // activity: activity that requests barcode scanning.
   // requestCode: request code, which is used to check whether the scanning result is obtained from Scan Kit.
            ScanUtil.startScan(this, REQUEST_CODE_SCAN_ONE, new HmsScanAnalyzerOptions.Creator().create());
        }
    }
```
7.Receive the barcode scanning result through the callback API, regardless of whether it is captured by the camera or from an image
```
@Override
    protected void onActivityResult(int requestCode, int resultCode, Intent data) {
        super.onActivityResult(requestCode, resultCode, data);

        if (resultCode != RESULT_OK || data == null) {
            return;
        }

        if (requestCode == REQUEST_CODE_SCAN_ONE) {
            // Input an image for scanning and return the result.
            HmsScan hmsScan = data.getParcelableExtra(ScanUtil.RESULT);
            if (hmsScan != null) {
                // Show the barcode parsing result.
                showResult(hmsCan);
            }
        }

    }
```
### Building the Barcode Generation Function
1.Repeat the first three steps for building scanning capabilities
2.Declare the necessary permission in the **AndroidManifest.xml** file
```
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
```
3.Dynamically request the permission
```
ActivityCompat.requestPermissions(this,new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE},requestCode);
```
4.Check the permission request result
```
@Override
    public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
        if (permissions == null || grantResults == null) {
            return;
        }

        if (grantResults[0] == PackageManager.PERMISSION_GRANTED && requestCode == GENERATE_CODE) {
            Intent intent = new Intent(this, GenerateCodeActivity.class);
            this.startActivity(intent);
        }
 }
```
5.Generate a QR code
```
public void generateCodeBtnClick(View v) {

        try {
            
            HmsBuildBitmapOption options = new HmsBuildBitmapOption.Creator()
                    .setBitmapMargin(margin)
                    .setBitmapColor(color)
                    .setBitmapBackgroundColor(background)
                    .create();
            resultImage = ScanUtil.buildBitmap(content, type, width, height, options);
            barcodeImage.setImageBitmap(resultImage);

        } catch (WriterException e) {
            Toast.makeText(this, "Parameter Error!", Toast.LENGTH_SHORT).show();
        }

    }
```
6.Save the QR code
```
public void saveCodeBtnClick(View v) {
        if (resultImage == null) {
            Toast.makeText(GenerateCodeActivity.this, "Please generate barcode first!", Toast.LENGTH_LONG).show();
            return;
        }
        try {
            String fileName = System.currentTimeMillis() + ".jpg";
            String storePath = Environment.getExternalStorageDirectory().getAbsolutePath();
            File appDir = new File(storePath);
            if (!appDir.exists()) {
                appDir.mkdir();
            }
            File file = new File(appDir, fileName);
            FileOutputStream fileOutputStream = new FileOutputStream(file);
            boolean isSuccess = resultImage.compress(Bitmap.CompressFormat.JPEG, 70, fileOutputStream);
            fileOutputStream.flush();
            fileOutputStream.close();
            Uri uri = Uri.fromFile(file);
            GenerateCodeActivity.this.sendBroadcast(new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, uri));
            if (isSuccess) {
                Toast.makeText(GenerateCodeActivity.this, "Barcode has been saved locally", Toast.LENGTH_LONG).show();
            } else {
                Toast.makeText(GenerateCodeActivity.this, "Barcode save failed", Toast.LENGTH_SHORT).show();
            }
        } catch (Exception e) {
            Toast.makeText(GenerateCodeActivity.this, "Unknown Error", Toast.LENGTH_SHORT).show();
        }
    }
```
## Result
![Result](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/xghax89x8do2e7s56ukm.gif)
Wi-Fi QR Code Demo is a test program showing how to generate QR Code that contains Wi-Fi information and scan the QR Code for connecting to Wi-Fi networks. 

## References
[HMS Core Scan Kit](https://developer.huawei.com/consumer/en/doc/development/HMSCore-Guides/service-introduction-0000001050041994?ha_source=hms1)
HMS Core [Official Website](https://developer.huawei.com/consumer/en/hms?ha_source=hms1)
[Reddit](https://www.reddit.com/r/HMSCore/) for discussion with other developers
[GitHub](https://github.com/HMS-Core) for demos and sample codes
[Stack Overflow](https://stackoverflow.com/questions/tagged/huawei-mobile-services?tab=Newest) for solutions to integration issues