27 March 2014

ใส่รหัสลับสำหรับเปิดแอปพลิเคชันด้วย Secret Code

Updated on


       ขอเปลี่ยนมาเป็นบทความแปลกๆแหวกแนวกันบ้างอะไรบ้าง เดี๋ยวจะเบื่อกันเสียก่อน

        ผู้ที่หลงเข้ามาอ่านหลายๆคนคงจะรู้จักกับวิธีกดรหัสบนอุปกรณ์แอนดรอยด์เพื่อเช็ค IMEI หรือเช็คนู่นนั่นนี่ และสำหรับเครื่องรุ่นเรือธงมักจะมีโปรแกรมทดสอบการทำงานของเครื่องให้ด้วย อย่างเช่น Note 2 ที่สามารถกด *#0*# เพื่อเปิดแอปพลิเคชันทดสอบเครื่องได้

        รู้หรือไม่ว่าผู้ที่หลงเข้ามาอ่านก็สามารถเขียนให้แอปพลิเคชันสามารถเปิดขึ้นมาด้วยการพิมพ์รหัสแบบนี้ได้เช่นกัน ซึ่งทาง Android ได้รองรับไว้ให้แล้ว เรียกว่า Secret Code โดยจะต้องเรียกด้วยการพิมพ์ *#*# [หมายเลข] #*#*

        ซึ่งการทำให้แอปพลิเคชันของเรามี Secret Code นั้น กลับไม่มีพูดถึงใน Reference ของ Android Developer เลยซักนิด แต่พอดีเจ้าของบล็อกไปนั่งส่องข้อมูลใน Moto X เล่นๆแล้วไปพบคำสั่งนี้ขึ้นมา แล้วไปค้นหาต่อดูก็พบว่ามันเป็นลูกเล่นที่ซ่อนไว้นั่นเอง


        ในการทำให้กด Secret Code ไม่ใช่การกดแล้วไปเปิดแอปพลิเคชันทันทีแต่อย่างใด แต่จริงๆแล้วมันคือการใช้ Broadcast Receiver เข้ามาช่วย โดยจะให้ Broadcast Receiver ทำงานเมื่อผู้ใช้กด Secret Code ตามที่กำหนดไว้ แล้วก็จะให้ Broadcast Receiver ทำการเรียก Activity ของแอปพลิเคชันขึ้นมาแสดง จึงทำให้ดูเหมือนว่ากด Secret Code ปุป แล้วเปิดแอปพลิเคชันขึ้นมาทันที



        เริ่มจากสร้าง Broadcast Receiver ขึ้นมาก่อนดังนี้

CallReceiver.java
package app.akexorcist.secretcode;

import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.pm.PackageManager;

public class CallReceiver extends BroadcastReceiver {
    public void onReceive(Context context, Intent intent) {
     String action = intent.getAction();
        if(action.equals("android.provider.Telephony.SECRET_CODE")) {
            PackageManager pm = context.getPackageManager(); 
            Intent i = pm.getLaunchIntentForPackage(context.getPackageName());
            context.startActivity(i);
        }
    }
}

         จากตัวอย่างนี้ก็คือเช็คว่า Broadcast Receiver ถูกเรียกขึ้นมาจากอะไร ถ้าถูกเรียกขึ้นมาจาก Secret Code ก็จะให้ทำการ Intent ไปยัง Activity โดยเช็คจาก Package Name ของแอปพลิเคชันตัวนี้ว่า Activity แรกคือตัวไหน แล้วก็ให้ทำการเปิดขึ้นมา

        ในกรณีที่อยากให้ Intent ไปหน้าอื่นก็สามารถทำได้เช่นกัน โดยเปลี่ยนคำสั่งเป็น

Intent i = new Intent(context, ActivityName.class);
i.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
context.startActivity(i);

        โดย ActivityName คือชื่อ Activity ที่ต้องการให้เรียกเปิดขึ้นมา

        สำหรับ Layout ใน Main.java ของตัวอย่างนี้ไม่มีอะไรนะ เพราะแค่ยกตัวอย่างในเรื่อง Secret Code เป็นเรื่อง

main.xml
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent" >

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_centerHorizontal="true"
        android:layout_centerVertical="true"
        android:text="@string/hello_world"
        android:textSize="25sp" />

</RelativeLayout>


        สิ่งหนึ่งที่สำคัญสำหรับ Broadcast Receiver ก็คือการประกาศใน Android Manifest ซึ่งจะคล้ายกับ Activity ที่ต้องประกาศใน Android Manifest ทุกครั้ง ไม่เช่นนั้นจะใช้งานไม่ได้ แต่สำหรับ Broadcast Receiver จะมีการประกาศแบบนี้

<receiver android:name="app.akexorcist.secretcode.CallReceiver" >
    <intent-filter>
        <action android:name="android.provider.Telephony.SECRET_CODE" />
                
        <data android:scheme="android_secret_code" android:host="555" />
    </intent-filter>
</receiver>

        จะสังเกตเห็นว่าเจ้าของบล็อกกำหนด Action ให้กับ Broadcast Receiver ตัวนี้เป็น android.provider.Telephony.SECRET_CODE โดยมีการกำหนดข้อมูลเป็น 555 นั่นก็หมายความว่าเวลาเรียกใช้งานก็จะต้องกด *#*#555#*#* นั่นเอง ซึ่งผู้ที่หลงเข้ามาอ่านสามารถเปลี่ยนเป็นหมายเลขอื่นก็ได้


        ดังนั้น Android Manifest ของแอปพลิเคชันตัวอย่างนี้ก็จะเป็นดังนี้

AndroidManifest.xml
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="app.akexorcist.secretcode"
    android:versionCode="1"
    android:versionName="1.0" >

    <uses-sdk
        android:minSdkVersion="8"
        android:targetSdkVersion="19" />

    <application
        android:allowBackup="true"
        android:icon="@drawable/ic_launcher"
        android:label="@string/app_name"
        android:theme="@style/AppTheme" >
        <activity
            android:name="app.akexorcist.secretcode.Main"
            android:label="@string/app_name" >
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
        
        <receiver android:name="app.akexorcist.secretcode.CallReceiver" >
            <intent-filter>
                <action android:name="android.provider.Telephony.SECRET_CODE" />
                
                <data android:scheme="android_secret_code" android:host="555" />
            </intent-filter>
        </receiver>
    </application>

</manifest>

        จากนั้นก็ติดตั้งลงในเครื่องแล้ว ก็ให้ลองกดโทรออกเป็นรหัสตามที่กำหนดไว้เลย อย่างเช่นเจ้าของบล็อกกำหนดไว้เป็น 555 ดังนั้นจะต้องกด *#*#555#*#* ก็จะเปิดแอปพลิเคชันขึ้นมาทันที



        สำหรับ Secret Code อาจจะดูเหมือนเรื่องไร้สาระ แต่หลายๆแอปพลิเคชันมักจะใส่ไว้เป็นลูกเล่นที่ซ่อนไว้ (Easter Egg) และที่สำคัญยังประยุกต์ใช้ร่วมกับแอปพลิเคชันเกมด้วย จำพวกสูตรลับเมื่อกดรหัสดังกล่าวจะปลดล็อคไอเท็มบางอย่าง เป็นต้น