android - حفظ الصورة النقطية إلى الموقع




bitmap save (10)

أنا أعمل على وظيفة لتنزيل صورة من خادم ويب ، وعرضها على الشاشة ، وإذا كان المستخدم يرغب في الاحتفاظ بالصورة ، قم بحفظها على بطاقة SD في مجلد معين. هل هناك طريقة سهلة لالتقاط صورة نقطية وحفظها على بطاقة SD في مجلد من اختياراتي؟

مشكلتي هي أنه يمكنني تنزيل الصورة وعرضها على الشاشة كصورة نقطية. الطريقة الوحيدة التي تمكنت من العثور على لحفظ صورة إلى مجلد معين هي استخدام FileOutputStream ، ولكن ذلك يتطلب صفيف بايت. لست متأكدًا من كيفية التحويل (إذا كانت هذه هي الطريقة الصحيحة) من الصورة النقطية إلى صفيف البايت ، لذلك يمكنني استخدام FileOutputStream لكتابة البيانات.

الخيار الآخر لدي هو استخدام MediaStore:

MediaStore.Images.Media.insertImage(getContentResolver(), bm,
    barcodeNumber + ".jpg Card Image", barcodeNumber + ".jpg Card Image");

الذي يعمل بشكل جيد للحفظ على بطاقة SD ، ولكن لا يسمح لك بتخصيص المجلد.


// | == | إنشاء ملف PNG من الصورة النقطية:

void devImjFylFnc(String pthAndFylTtlVar, Bitmap iptBmjVar)
{
    try
    {
        FileOutputStream fylBytWrtrVar = new FileOutputStream(pthAndFylTtlVar);
        iptBmjVar.compress(Bitmap.CompressFormat.PNG, 100, fylBytWrtrVar);
        fylBytWrtrVar.close();
    }
    catch (Exception errVar) { errVar.printStackTrace(); }
}

// | == | احصل على Bimap من الملف:

Bitmap getBmjFrmFylFnc(String pthAndFylTtlVar)
{
    return BitmapFactory.decodeFile(pthAndFylTtlVar);
}

أود أيضًا حفظ صورة. ولكن مشكلتي (؟) هي أنني أريد حفظه من الصورة النقطية التي تم رسمها.

لقد صنعت هكذا:

 @Override
 public boolean onOptionsItemSelected(MenuItem item) {
            switch (item.getItemId()) {
            case R.id.save_sign:      

                myView.save();
                break;

            }
            return false;    

    }

public void save() {
            String filename;
            Date date = new Date(0);
            SimpleDateFormat sdf = new SimpleDateFormat ("yyyyMMddHHmmss");
            filename =  sdf.format(date);

            try{
                 String path = Environment.getExternalStorageDirectory().toString();
                 OutputStream fOut = null;
                 File file = new File(path, "/DCIM/Signatures/"+filename+".jpg");
                 fOut = new FileOutputStream(file);

                 mBitmap.compress(Bitmap.CompressFormat.JPEG, 85, fOut);
                 fOut.flush();
                 fOut.close();

                 MediaStore.Images.Media.insertImage(getContentResolver()
                 ,file.getAbsolutePath(),file.getName(),file.getName());

            }catch (Exception e) {
                e.printStackTrace();
            }

 }

بعد Android 4.4 Kitkat ، واعتبارًا من عام 2017 ، حصة Android 4.4 وأقل تقريبًا حوالي 20٪ وخفض ، لا يمكن حفظ بطاقة SD باستخدام فئة File و getExternalStorageDirectory() . تؤدي هذه الطريقة إلى إعادة تخزين الذاكرة الداخلية للجهاز وصوره لكل تطبيق. يمكنك أيضًا حفظ صور خاصة فقط لتطبيقك وحذفها عندما يحذف المستخدم تطبيقك باستخدام طريقة openFileOutput() .

بدءاً من Android 6.0 ، يمكنك تهيئة بطاقة SD كذاكرة داخلية ولكنها خاصة فقط بجهازك. (إذا قمت بتهيئة سيارة SD كذاكرة داخلية ، فسيتمكن جهازك من الوصول إلى محتوياته أو مشاهدتها فقط) يمكنك حفظها على بطاقة SD باستخدام إجابات أخرى ولكن إذا كنت ترغب في استخدام بطاقة SD قابلة للإزالة ، فعليك قراءة إجابتي أدناه.

يجب عليك استخدام Access Storage Framework للحصول على uri إلى المجلد onActivityResult طريقة النشاط للحصول على المجلد المحدد من قبل المستخدم ، وإضافة إذن onActivityResult من الوصول إلى المجلد بعد قيام المستخدم بإعادة تشغيل الجهاز.

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    super.onActivityResult(requestCode, resultCode, data);

    if (resultCode == RESULT_OK) {

        // selectDirectory() invoked
        if (requestCode == REQUEST_FOLDER_ACCESS) {

            if (data.getData() != null) {
                Uri treeUri = data.getData();
                tvSAF.setText("Dir: " + data.getData().toString());
                currentFolder = treeUri.toString();
                saveCurrentFolderToPrefs();

                // grantUriPermission(getPackageName(), treeUri,
                // Intent.FLAG_GRANT_READ_URI_PERMISSION |
                // Intent.FLAG_GRANT_WRITE_URI_PERMISSION);

                final int takeFlags = data.getFlags()
                        & (Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION);
                // Check for the freshest data.
                getContentResolver().takePersistableUriPermission(treeUri, takeFlags);

            }
        }
    }
}

الآن ، قم بحفظ الحفظ إلى التفضيلات المشتركة لعدم مطالبة المستخدم بتحديد المجلد في كل مرة تريد فيها حفظ صورة.

يجب عليك استخدام فئة DocumentFile لحفظ صورتك ، وليس File أو ParcelFileDescriptor ، لمزيد من المعلومات ، يمكنك التحقق من هذا الموضوع لحفظ الصورة إلى بطاقة SD مع compress(CompressFormat.JPEG, 100, out); الطريقة وفئات DocumentFile .


تأكد من إنشاء الدليل قبل الاتصال بـ bitmap.compress :

new File(FileName.substring(0,FileName.lastIndexOf("/"))).mkdirs();

ستتجاهل بعض التنسيقات ، مثل PNG التي لا تحمل أي ضياع ، إعداد الجودة.


فيما يلي نموذج التعليمة البرمجية لحفظ الصورة النقطية في الملف:

public static File savebitmap(Bitmap bmp) throws IOException {
    ByteArrayOutputStream bytes = new ByteArrayOutputStream();
    bmp.compress(Bitmap.CompressFormat.JPEG, 60, bytes);
    File f = new File(Environment.getExternalStorageDirectory()
            + File.separator + "testimage.jpg");
    f.createNewFile();
    FileOutputStream fo = new FileOutputStream(f);
    fo.write(bytes.toByteArray());
    fo.close();
    return f;
}

الآن استدعاء هذه الدالة لحفظ الصورة النقطية إلى الذاكرة الداخلية.

File newfile = savebitmap(bitmap) ؛

آمل أن تساعدك. سعيد الحياة الترميز.


ليس في الواقع إجابة ، ولكن تعليق. أنا على جهاز Mac الذي يعمل على تشغيل بيئة المحاكي ، واحصل على java.io.IOException: تم رفض الإذن - خطأ في هذا الكود:

protected void onActivityResult(int requestCode, int resultCode, Intent imageReturnedIntent) {
    Log.d("DEBUG", "onActivityResult called");
    super.onActivityResult(requestCode, resultCode, imageReturnedIntent);
    if(requestCode == 0 && resultCode == RESULT_OK) {
        Log.d("DEBUG", "result is ok");
        try{
            Bitmap map = (Bitmap) imageReturnedIntent.getExtras().get("data");
            File sd = new File(Environment.getExternalStorageDirectory(), "test.png");
            sd.mkdirs();
            sd.createNewFile();
            FileOutputStream out = new FileOutputStream(sd);
            map.compress(Bitmap.CompressFormat.PNG, 90, out);
            out.flush();
            out.close();
        } catch(FileNotFoundException e){
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

أضفت أيضًا الإذن باستخدام android.permission.WRITE_EXTERNAL_STORAGE إلى ملف البيان (كما لاحظه الآخرون).


مهلا فقط إعطاء الاسم ل. bmp

افعل هذا:

ByteArrayOutputStream bytes = new ByteArrayOutputStream();
_bitmapScaled.compress(Bitmap.CompressFormat.PNG, 40, bytes);

//you can create a new file name "test.BMP" in sdcard folder.
File f = new File(Environment.getExternalStorageDirectory()
                        + File.separator + "**test.bmp**")

سيبدو ذلك IM مجرد خداع حول ولكن حاول مرة واحدة سوف تحصل على حفظ في foramt bmp ..


Bitmap bbicon;

bbicon=BitmapFactory.decodeResource(getResources(),R.drawable.bannerd10);
//ByteArrayOutputStream baosicon = new ByteArrayOutputStream();
//bbicon.compress(Bitmap.CompressFormat.PNG,0, baosicon);
//bicon=baosicon.toByteArray();

String extStorageDirectory = Environment.getExternalStorageDirectory().toString();
OutputStream outStream = null;
File file = new File(extStorageDirectory, "er.PNG");
try {
    outStream = new FileOutputStream(file);
    bbicon.compress(Bitmap.CompressFormat.PNG, 100, outStream);
    outStream.flush();
    outStream.close();
} catch(Exception e) {

}

FileOutputStream out = null;
try {
    out = new FileOutputStream(filename);
    bmp.compress(Bitmap.CompressFormat.PNG, 100, out); // bmp is your Bitmap instance
    // PNG is a lossless format, the compression factor (100) is ignored
} catch (Exception e) {
    e.printStackTrace();
} finally {
    try {
        if (out != null) {
            out.close();
        }
    } catch (IOException e) {
        e.printStackTrace();
    }
}




save