URL轉換成二維碼,url

來源:互聯網
上載者:User

URL轉換成二維碼,url

轉載請註明出處:http://www.cnblogs.com/cnwutianhao/p/6685804.html 

 

二維碼已經成為我們日常生活中的一個不可擷取的產物,火車票上,景區門票,超市付款等等都會有二維碼的身影。

本文將實現由URL轉換成二維碼的過程。

先看一下樣本圖

從樣本圖中我們可以清晰地看到,URL被轉換成了二維碼。

下面跟隨我來一起實現這個功能。

 

匯入Google提供的開源庫

compile 'com.google.zxing:core:3.3.0'

來講解一下核心的部分:二維碼轉換

①產生二維碼Bitmap

public static boolean createQRImage(String content, int widthPix, int heightPix, Bitmap logoBm, String filePath) {        try {            if (content == null || "".equals(content)) {                return false;            }            //配置參數            Map<EncodeHintType, Object> hints = new HashMap<>();            hints.put(EncodeHintType.CHARACTER_SET, "utf-8");            //容錯層級            hints.put(EncodeHintType.ERROR_CORRECTION, ErrorCorrectionLevel.H);            //設定空白邊距的寬度           hints.put(EncodeHintType.MARGIN, 2); //default is 4            // 映像資料轉換,使用了矩陣轉換            BitMatrix bitMatrix = new QRCodeWriter().encode(content, BarcodeFormat.QR_CODE, widthPix, heightPix, hints);            int[] pixels = new int[widthPix * heightPix];            // 下面這裡按照二維碼的演算法,逐個產生二維碼的圖片,            // 兩個for迴圈是圖片橫列掃描的結果            for (int y = 0; y < heightPix; y++) {                for (int x = 0; x < widthPix; x++) {                    if (bitMatrix.get(x, y)) {                        pixels[y * widthPix + x] = 0xff000000;                    } else {                        pixels[y * widthPix + x] = 0xffffffff;                    }                }            }            // 產生二維碼圖片的格式,使用ARGB_8888            Bitmap bitmap = Bitmap.createBitmap(widthPix, heightPix, Bitmap.Config.ARGB_8888);            bitmap.setPixels(pixels, 0, widthPix, 0, 0, widthPix, heightPix);            if (logoBm != null) {                bitmap = addLogo(bitmap, logoBm);            }            //必須使用compress方法將bitmap儲存到檔案中再進行讀取。直接返回的bitmap是沒有任何壓縮的,記憶體消耗巨大!            return bitmap != null && bitmap.compress(Bitmap.CompressFormat.JPEG, 100, new FileOutputStream(filePath));        } catch (WriterException | IOException e) {            e.printStackTrace();        }        return false;    }

②在二維碼中間添加Logo圖案

private static Bitmap addLogo(Bitmap src, Bitmap logo) {        if (src == null) {            return null;        }        if (logo == null) {            return src;        }        //擷取圖片的寬高        int srcWidth = src.getWidth();        int srcHeight = src.getHeight();        int logoWidth = logo.getWidth();        int logoHeight = logo.getHeight();        if (srcWidth == 0 || srcHeight == 0) {            return null;        }        if (logoWidth == 0 || logoHeight == 0) {            return src;        }        //logo大小為二維碼整體大小的1/5        float scaleFactor = srcWidth * 1.0f / 5 / logoWidth;        Bitmap bitmap = Bitmap.createBitmap(srcWidth, srcHeight, Bitmap.Config.ARGB_8888);        try {            Canvas canvas = new Canvas(bitmap);            canvas.drawBitmap(src, 0, 0, null);            canvas.scale(scaleFactor, scaleFactor, srcWidth / 2, srcHeight / 2);            canvas.drawBitmap(logo, (srcWidth - logoWidth) / 2, (srcHeight - logoHeight) / 2, null);            canvas.save(Canvas.ALL_SAVE_FLAG);            canvas.restore();        } catch (Exception e) {            bitmap = null;            e.getStackTrace();        }        return bitmap;    }

③建立二維碼檔案儲存體目錄

private static String getFileRoot(Context context) {        if (Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)) {            File external = context.getExternalFilesDir(null);            if (external != null) {                return external.getAbsolutePath();            }        }        return context.getFilesDir().getAbsolutePath();    }

④建立資料庫工具類來儲存臨時資料

public class SPUtil {    private static final String CONFIG = "config";    /**     * 擷取SharedPreferences執行個體對象     *     * @param fileName     */    private static SharedPreferences getSharedPreference(String fileName) {        return QRCodeApplication.getInstance().getSharedPreferences(fileName, Context.MODE_PRIVATE);    }    /**     * 儲存一個String類型的值!     */    public static void putString(String key, String value) {        SharedPreferences.Editor editor = getSharedPreference(CONFIG).edit();        editor.putString(key, value).apply();    }    /**     * 擷取String的value     */    public static String getString(String key, String defValue) {        SharedPreferences sharedPreference = getSharedPreference(CONFIG);        return sharedPreference.getString(key, defValue);    }}

⑤展示二維碼

public static void showThreadImage(final Activity mContext, final String text, final ImageView imageView, final int centerPhoto) {        String preContent = SPUtil.getString("share_code_content", "");        if (text.equals(preContent)) {            String preFilePath = SPUtil.getString("share_code_filePath", "");            imageView.setImageBitmap(BitmapFactory.decodeFile(preFilePath));        } else {            SPUtil.putString("share_code_content", text);            final String filePath = getFileRoot(mContext) + File.separator + "qr_" + System.currentTimeMillis() + ".jpg";            SPUtil.putString("share_code_filePath", filePath);            //二維碼圖片較大時,產生圖片、儲存檔案的時間可能較長,因此放在新線程中            new Thread(new Runnable() {                @Override                public void run() {                    boolean success = QRCodeUtil.createQRImage(text, 800, 800, BitmapFactory.decodeResource(mContext.getResources(), centerPhoto),                            filePath);                    if (success) {                        mContext.runOnUiThread(new Runnable() {                            @Override                            public void run() {                                imageView.setImageBitmap(BitmapFactory.decodeFile(filePath));                            }                        });                    }                }            }).start();        }    }

 

構造一個輸入頁面的類,使用Bundle通過<key,value>傳值(後期會改為MVVM-DataBinding形式)

public class ContentActivity extends AppCompatActivity implements View.OnClickListener {    private EditText etUrl;    private Button btnConvert;    @Override    protected void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.activity_content);        initView();    }    private void initView() {        etUrl = (EditText) findViewById(R.id.et_url);        btnConvert = (Button) findViewById(R.id.btn_convert);        btnConvert.setOnClickListener(this);    }    @Override    public void onClick(View v) {        switch (v.getId()) {            case R.id.btn_convert:                String str_url = "https://" + etUrl.getText().toString();                Bundle bundle = new Bundle();                bundle.putString("url", str_url);                // 當輸入框為空白時,提示使用者                if (str_url.equals("https://")) {                    Toast.makeText(getApplicationContext(), "輸入框不可為空", Toast.LENGTH_SHORT).show();                } else {                    Intent intent = new Intent(ContentActivity.this, MainActivity.class);                    intent.putExtras(bundle);                    startActivity(intent);                }                break;            default:                break;        }    }}

 

將二維碼圖片展示在頁面上(後期會改為MVVM-DataBinding形式)

public class MainActivity extends AppCompatActivity {    private ImageView iv;//    private String url = "http://weibo.com/cnwutianhao";    @Override    protected void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.activity_main);        String str_url = getIntent().getExtras().getString("url");        iv = (ImageView) findViewById(R.id.iv_qrcode);        QRCodeUtil.showThreadImage(this, str_url, iv, R.mipmap.ic_launcher);    }}

 

布局檔案

①輸入頁面(後期會改為DataBinding形式)

<?xml version="1.0" encoding="utf-8"?><RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"    android:layout_width="match_parent"    android:layout_height="match_parent"    android:orientation="vertical"    android:padding="10dp">    <EditText        android:id="@+id/et_url"        android:layout_width="match_parent"        android:layout_height="50dp"        android:layout_marginTop="100dp"        android:hint="請輸入網址"        android:inputType="textUri" />    <Button        android:id="@+id/btn_convert"        android:layout_width="wrap_content"        android:layout_height="wrap_content"        android:layout_alignParentBottom="true"        android:layout_centerHorizontal="true"        android:layout_marginBottom="20dp"        android:text="轉換成二維碼" /></RelativeLayout>

②二維碼展示頁面

<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"    tools:context="com.tnnowu.android.qrcode.MainActivity">    <ImageView        android:id="@+id/iv_qrcode"        android:layout_width="220dp"        android:layout_height="220dp"        android:layout_centerInParent="true"        android:layout_marginTop="40dp"        android:background="#FFFFFF" /></RelativeLayout>

 

原始碼已上傳至Github,歡迎Star,Fork。THX

https://github.com/cnwutianhao/QRCode

 

關注我的新浪微博,擷取更多Android開發資訊!
關注科技評論家,領略科技、創新、教育以及最大化人類智慧與想象力!

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.