Sdcard के लिए सहेजा गया चित्र, Android की गैलरी ऐप में दिखाई नहीं देता है


92

मैं sdcard के लिए एक छवि को बचाने के लिए और यह गैलरी आवेदन में प्रकट नहीं होता है जब तक मैं sdcard बंद खींच और इसे वापस नहीं।

क्या आपके पास कोई विचार है कि ऐसा क्यों है?

लगता है कि गैलरी एप्लिकेशन में कुछ कैश है जो फ़ाइल सेव पर अपडेट नहीं है ...

वास्तव में, मैं भी गैलरी आवेदन में सिर्फ-सहेजी गई छवि को खोलने के लिए और साथ कि कोई सफलता करना चाहते हैं
इस समस्या के बारे में मेरे सवाल है।


1
इस सवाल का इस ट्यूटोरियल में चरण दर चरण उत्तर दिया गया है: stackoverflow.com/questions/30506301/…
Takermania

जवाबों:


45

सिस्टम किसी भी नई छवि (और अन्य) फ़ाइलों को खोजने के लिए माउंट होने पर एसडी कार्ड को स्कैन करता है। यदि आप प्रोग्राम फ़ाइल जोड़ रहे हैं, तो आप इस वर्ग का उपयोग कर सकते हैं:

http://developer.android.com/reference/android/media/MediaScannerConnection.html


4
साइड नोट: हालांकि प्रश्न फ़ाइल को जोड़ने के लिए संदर्भित करता है, MediaScannerConnection फ़ाइल विलोपन के लिए कोई समाधान प्रदान नहीं करता है - तब भी नहीं जब एक हटाए गए फ़ाइल के मूल फ़ोल्डर को स्कैन करने का अनुरोध किया जाता है।
एलिकएल्ज़िन-किलाका

85

एक सरल समाधान स्थिर सुविधा विधि स्कैनफाइल () का उपयोग करना है :

File imageFile = ...
MediaScannerConnection.scanFile(this, new String[] { imageFile.getPath() }, new String[] { "image/jpeg" }, null);

जहां thisआपकी गतिविधि (या जो भी संदर्भ) है, माइम-प्रकार केवल तभी आवश्यक है जब आप गैर-मानक फ़ाइल एक्सटेंशन का उपयोग कर रहे हों और nullवैकल्पिक कॉलबैक के लिए है (जिसे हमें इस तरह के सरल मामले की आवश्यकता नहीं है)।


2
प्रसारण विधि, जो अन्य (और Google) प्रदान करती है, बहुत कम ही काम करती है।
क्रिस। जेनकिंस

2
यह मेरे लिए पहले के एंड्रॉइड वर्जन ~ 4.0 में काम कर रहा था, लेकिन अब 4.3+ में काम नहीं कर रहा है। चित्र गैलरी ऐप में दिखाई नहीं दे रहे हैं।
hooby3dfx

उत्तम ! आप इसके साथ संदर्भ पा सकते हैं: Android.App.Application.Context
jug

मार्शमॉलो में काम किया
हितेश साहू

66

मूल प्रश्न और किसी और को, जिसका यह समस्या हो सकता है:

मुझे भी यही समस्या आ रही थी, मेरे ऐप में मौजूद चित्र जो एसडी कार्ड में सहेजे गए लोग अपनी गैलरी में तुरंत नहीं दिखा रहे थे। कुछ खोज के बाद मुझे कोड की एक लाइन मिली जो मेरे 'सेव टू एसडीकार्ड' कोड के बाद डाली गई जिसने समस्या को ठीक किया:

sendBroadcast(new Intent(Intent.ACTION_MEDIA_MOUNTED, Uri.parse("file://"+ Environment.getExternalStorageDirectory())));

क्या हमें इस प्रसारण का उपयोग करने में सक्षम होने के लिए मीडिया स्कैनर का उपयोग करने की आवश्यकता है? मैं अपनी गैलरी में छवियों को प्रदर्शित करने के लिए एक अन्य मैथोड का उपयोग कर रहा हूं। जब मैं save बटन पर ऊपर sendBroadcast का उपयोग कर रहा हूं तो क्लिक करें मेरी गैलरी नई छवि के साथ अपडेट नहीं हुई है!
बदलें

4
यह पुराना है, लेकिन यह किसी की मदद कर सकता है - एक अधिक विशिष्ट पथ: sendBroadcast (नई आशय (Intent.ACTION_MEDIA_MOUNTED, Uri.parse ("फ़ाइल: //" + Environment.getExternalStoragePoreDirectory (Environment.DIRECTORY_PICTURES))); यह विधि (यह उत्तर, न केवल मेरी टिप्पणी) एमुलेटर पर काम नहीं करती है। असली डिवाइस पर परीक्षण।

मेरा मानना ​​है कि स्वीकृत उत्तर इसे करने का सही तरीका प्रदान करता है। लेकिन अगर आप एपीआई <= 7 का समर्थन करने की कोशिश कर रहे हैं तो यह एक अच्छी गिरावट है।
अमृत ​​मोस्तफा

आपका उत्तर अन्य उपकरणों के लिए सहायक है। यह एचटीसी पर काम नहीं कर रहा है, जब मैं अपने एप्लिकेशन फ़ोल्डर को स्कैन करने का प्रयास करता हूं। यह नई जोड़ी गई छवि को नहीं दिखाता है।
मोबाइलएवंज़ेलिस्ट

6
ऐसा लगता है कि यह अब एंड्रॉइड 4.4 या उससे अधिक पर समर्थित नहीं है। इस मामले में अनुमति अपवाद फेंक दी जाएगी।
rsp1984

13

आप इरादे से मीडिया गैलरी में एक छवि भी जोड़ सकते हैं, उदाहरण कोड पर एक नज़र डालें कि यह कैसे किया जाता है:

ContentValues image = new ContentValues();

image.put(Images.Media.TITLE, imageTitle);
image.put(Images.Media.DISPLAY_NAME, imageDisplayName);
image.put(Images.Media.DESCRIPTION, imageDescription);
image.put(Images.Media.DATE_ADDED, dateTaken);
image.put(Images.Media.DATE_TAKEN, dateTaken);
image.put(Images.Media.DATE_MODIFIED, dateTaken);
image.put(Images.Media.MIME_TYPE, "image/png");
image.put(Images.Media.ORIENTATION, 0);

 File parent = imageFile.getParentFile();
 String path = parent.toString().toLowerCase();
 String name = parent.getName().toLowerCase();
 image.put(Images.ImageColumns.BUCKET_ID, path.hashCode());
 image.put(Images.ImageColumns.BUCKET_DISPLAY_NAME, name);
 image.put(Images.Media.SIZE, imageFile.length());

 image.put(Images.Media.DATA, imageFile.getAbsolutePath());

 Uri result = context.getContentResolver().insert(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, image);

नमस्ते। यह विधि छवि को MediaStore में जोड़ती है, मैंने इसे लौटाकर इसकी पुष्टि की है Uriलेकिन समस्या यह है कि सम्मिलित चित्र गैलरी में नहीं दिख रहा है। मैंने शुरुआत और गैलरी के अंत में दोनों की जाँच की है। क्या आप कृपया कोई भी तरीका सुझा सकते हैं ताकि सम्मिलित चित्र गैलरी में तुरंत दिखाई दे?
शजील अफजल

12

Android KITKAT सहित गैलरी ताज़ा

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT)
{
        Intent mediaScanIntent = new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE);
        File f = new File("file://"+ Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES));
        Uri contentUri = Uri.fromFile(f);
        mediaScanIntent.setData(contentUri);
        this.sendBroadcast(mediaScanIntent);
}
else
{
        sendBroadcast(new Intent(Intent.ACTION_MEDIA_MOUNTED, Uri.parse("file://" + Environment.getExternalStorageDirectory())));
}

वह कोड जो पहली शर्त व्हाइटिन के अंदर है "IF" स्टेटमेंट किटकैट (Android 4.4.4, API 19) में मेरे लिए ठीक काम करता है।
एलेक्स

8

यहाँ MediaScannerConnection के लिए कोड है:

MyMediaConnectorClient client = new MyMediaConnectorClient(newfile);
MediaScannerConnection scanner = new MediaScannerConnection(context, client);
client.setScanner(scanner);
scanner.connect();

newfile आपकी नई / सहेजी गई फ़ाइल का फ़ाइल ऑब्जेक्ट है।


2
आपके उत्तर के लिए धन्यवाद। वास्तव में, मैं इस परियोजना को बहुत पहले ही समाप्त कर चुका हूं ... मुझे यह भी याद नहीं है कि मैंने जो उपयोग किया था उसका समाधान क्या था। अन्य उपयोगकर्ताओं को आपके समाधान में मदद मिल सकती है यदि आप इसे लागू करने की MyMediaConnectorClient...
माइकल केसलर

हाँ - मैं इस समय इसके साथ वास्तविक सिरदर्द हूँ। कृपया पोस्ट करें :)
स्टीव

हां, मैं वास्तव में स्पष्ट नहीं हूं कि प्रवाह कैसे होना चाहिए-मुझे सही करें जहां मैं गलत हूं मैं SDCAARD जानकारी को अपडेट करने के लिए MediaScannerConnection का उपयोग कर सकता हूं इसलिए मैं कैमरे के साथ तस्वीर लेता हूं और नई फाइल को एमएससी में पास करता हूं और अब मैं फ़ाइल तक पहुंच सकता हूं एक कनेक्शन स्कैनर क्लाइंट के साथ?
स्टीव

प्रवाह है: आप एक तस्वीर लेते हैं, इसे अपने एसडीकार्ड में सहेजें और फिर स्कैनर अपडेट करें, ताकि डिवाइस गैलरी में आपके सहेजे गए चित्र को देखने के लिए फाइल सिस्टम अपडेट हो जाए। यदि आप स्कैनर के साथ ऐसा नहीं करते हैं, तो आप गैलरी में अगले डिवाइस को पुनरारंभ करने के बाद अपना चित्र देखते हैं।
डीएमजी

7

एमुलेटर में एक ऐप है जो कहता है - 'देव टूल्स'

उस पर क्लिक करें और 'मीडिया स्कैनिंग' चुनें .. सभी चित्र स्कैन हो जाएंगे


यह जानने के लिए कि आपके फोन पर रिबूट करने से पहले मुझे पता था कि एक ही तरीका :),
mishkin

6

अपनी गतिविधि को 'MediaScannerConnectionClient' लागू करने दें और इसे अपनी गतिविधि में जोड़ें:

private void startScan() 
{ 
    if(conn!=null) conn.disconnect();  
    conn = new MediaScannerConnection(YourActivity.this,YourActivity.this); 
    conn.connect(); 
} 

@Override 
public void onMediaScannerConnected() { 
    try{
        conn.scanFile(yourImagePath, "image/*");
       } catch (java.lang.IllegalStateException e){
       }
}

@Override 
public void onScanCompleted(String path, Uri uri) { 
    conn.disconnect(); 
} 

नमस्ते! क्या होगा अगर हम Uriछवि के बारे में जानते हैं , उदाहरण के लिए:content://media/external/images/media/1231778
शजील अफ़ज़ल

6

यह काम मेरे साथ

File file = ..... // Save file

context.sendBroadcast(new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, Uri.fromFile(file)));

4
 File folderGIF = new File(Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES) + "/newgif2");    //path where gif will be stored
success = folderGIF.mkdir();    //make directory
 String finalPath = folderGIF + "/test1.gif";  //path of file
.....
/* changes in gallery app if any changes in done*/
 MediaScannerConnection.scanFile(this,
                    new String[]{finalPath}, null,
                    new MediaScannerConnection.OnScanCompletedListener() {
                        public void onScanCompleted(String path, Uri uri) {
                            Log.i("ExternalStorage", "Scanned " + path + ":");
                            Log.i("ExternalStorage", "-> uri=" + uri);
                        }
                    });

मैं एनिमेटेड जिफ़ फ़ाइल को सहेजना चाहता हूं जो बाहरी संग्रहण में स्थित है और मेरे पास पथ है / अर्थात /storage/emulated/0/Android/data/<PackageName>/files/<FolderName>/xyz.gif। अब मैं इस फाइल को इमेज गैलरी में सेव / कॉपी करना चाहता हूं और वहां दिखाना चाहता हूं। यह कैसे करना है।
जिया उर रहमान

3

यहां मैं कोड साझा कर रहा हूं जो बिटमैप के रूप में छवि को लोड कर सकता है और उस छवि को ऐप नाम फ़ोल्डर में sdcard गैलरी पर सहेज सकता है। आपको इन चरणों का पालन करना चाहिए

  1. सबसे पहले इमेज बिटमैप डाउनलोड करें



     private Bitmap loadBitmap(String url) {
        try {
            InputStream in = new java.net.URL(url).openStream();
            return BitmapFactory.decodeStream(in);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
       }


  1. कृपया अपने AndroidManifest.xml फ़ाइल में निम्नलिखित अनुमति प्रदान करें।


    uses-permission android:name="android.permission.INTERNET" 
    uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"


  1. यहाँ संपूर्ण कोड है जो सक्रियता में लिखा गया है जिसमें हम यह कार्य करना चाहते हैं।



     void saveMyImage(String appName, String imageUrl, String imageName) {

            Bitmap bmImg = loadBitmap(imageUrl);
            File filename;
            try {
                String path1 = android.os.Environment.getExternalStorageDirectory()
                        .toString();
                File file = new File(path1 + "/" + appName);
                if (!file.exists())
                    file.mkdirs();
                filename = new File(file.getAbsolutePath() + "/" + imageName
                        + ".jpg");
                FileOutputStream out = new FileOutputStream(filename);
                bmImg.compress(Bitmap.CompressFormat.JPEG, 90, out);
                out.flush();
                out.close();
                ContentValues image = new ContentValues();
                image.put(Images.Media.TITLE, appName);
                image.put(Images.Media.DISPLAY_NAME, imageName);
                image.put(Images.Media.DESCRIPTION, "App Image");
                image.put(Images.Media.DATE_ADDED, System.currentTimeMillis());
                image.put(Images.Media.MIME_TYPE, "image/jpg");
                image.put(Images.Media.ORIENTATION, 0);
                File parent = filename.getParentFile();
                image.put(Images.ImageColumns.BUCKET_ID, parent.toString()
                        .toLowerCase().hashCode());
                image.put(Images.ImageColumns.BUCKET_DISPLAY_NAME, parent.getName()
                        .toLowerCase());
                image.put(Images.Media.SIZE, filename.length());
                image.put(Images.Media.DATA, filename.getAbsolutePath());
                Uri result = getContentResolver().insert(
                        MediaStore.Images.Media.EXTERNAL_CONTENT_URI, image);
                Toast.makeText(getApplicationContext(),
                        "File is Saved in  " + filename, Toast.LENGTH_SHORT).show();
            } catch (Exception e) {
                e.printStackTrace();
            }

        }


  1. आशा है कि यह आपकी पूरी समस्या को हल कर सकता है।

3
sendBroadcast(new Intent(Intent.ACTION_MEDIA_MOUNTED, Uri.parse("file://"+ Environment.getExternalStorageDirectory())));

KITKAT पर काम नहीं करता है। यह अनुमति के अपवाद को फेंक देता है और ऐप को क्रैश कर देता है। तो इसके लिए, मैंने निम्नलिखित कार्य किए हैं:

String path = mediaStorageDir.getPath() + File.separator
                    + "IMG_Some_name.jpg";
CameraActivity.this.sendBroadcast(new Intent(
                             Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, Uri
                            .parse("file://" + path)));

आशा करता हूँ की ये काम करेगा।


2

छवि को बचाने के बाद इसका उपयोग करें

sendBroadcast(new Intent(Intent.ACTION_MEDIA_MOUNTED, Uri.parse("file://"+ Environment.getExternalStorageDirectory())));

3
यह काम करता है लेकिन यह सबसे अच्छा समाधान नहीं है। आप सिस्टम को यह सोचकर चकमा दे रहे हैं कि एसडी कार्ड (पुनः) घुड़सवार होगा और संभवत: पूरे एसडी कार्ड को पुन: स्थापित करने के लिए मजबूर करेगा। MediaScanner.scanFile (..) सबसे अच्छा समाधान है जब आप अब वह फ़ाइल जो आप जोड़ना चाहते हैं।
पोकमो

1
यह सभी छवियों के लिए खोज करता है। और इसमें बहुत सी अनावश्यक डेटा प्रोसेसिंग शामिल है जो अप्रासंगिक हो सकती है जब हमारे पास गैलरी में दिखाए जाने के लिए सिर्फ एक छवि है।
राहुल रस्तोगी

2

MyMediaConnectorClient के लिए मेरा कोड:

public class MyMediaConnectorClient implements MediaScannerConnectionClient {

    String _fisier;
    MediaScannerConnection MEDIA_SCANNER_CONNECTION;

    public MyMediaConnectorClient(String nume) {
        _fisier = nume;
    }

    public void setScanner(MediaScannerConnection msc){
        MEDIA_SCANNER_CONNECTION = msc;
    }

    @Override
    public void onMediaScannerConnected() {
        MEDIA_SCANNER_CONNECTION.scanFile(_fisier, null);
    }

    @Override
    public void onScanCompleted(String path, Uri uri) {
        if(path.equals(_fisier))
            MEDIA_SCANNER_CONNECTION.disconnect();
    }
}

0

आपको गैलरी ऐप को अनुमति देने की आवश्यकता है। होम स्क्रीन में गैलरी ऐप आइकन को बस देर तक दबाएं और स्क्रीन के शीर्ष पर पॉप अप करने वाले 'एपीपी इन्फो' पर टैप करें। ऐसा करने से गैलरी ऐप सेटिंग दिखाई देगी। अब अनुमतियां टैब में जाएं और इसे टॉगल करके स्टोरेज, कैमरा अनुमतियां सक्षम करें। अब अपने मूल गैलरी ऐप पर जाएं और आपको अपने सहेजे गए चित्र मिल जाएंगे।


0

यह आपकी समस्या को हल करेगा यदि गैलरी में आपकी छवि दिखाई नहीं दे रही है तो वे मिडल में 404 प्रकार का बिटमैप दिखा सकते हैं। कृपया वे टैग जोड़ें जो मेरी कोड में आपकी छवि के साथ हैं क्योंकि गैलरी में छवि दिखाने के लिए कुछ मेटा डेटा होना चाहिए।

      String resultPath = getExternalFilesDir(Environment.DIRECTORY_PICTURES)+ 
      getString(R.string.directory) + System.currentTimeMillis() + ".jpg";

       new File(resultPath).getParentFile().mkdir();

        try {
            OutputStream fileOutputStream = new FileOutputStream(resultPath);
            savedBitmap.compress(CompressFormat.JPEG, 100, fileOutputStream);
            fileOutputStream.flush();
            fileOutputStream.close();
        } catch (IOException e2) {
            e2.printStackTrace();
        }
        savedBitmap.recycle();

        File file = new File(resultPath);
        ContentValues values = new ContentValues();
        values.put(MediaStore.Images.Media.TITLE, "Photo");
        values.put(MediaStore.Images.Media.DESCRIPTION, "Edited");
        values.put(MediaStore.Images.Media.MIME_TYPE, "image/jpeg");
        values.put(MediaStore.Images.Media.DATE_TAKEN, System.currentTimeMillis ());
        values.put(MediaStore.Images.Media.DATE_ADDED, System.currentTimeMillis());
        values.put(MediaStore.Images.ImageColumns.BUCKET_ID, file.toString().toLowerCase(Locale.US).hashCode());
        values.put(MediaStore.Images.ImageColumns.BUCKET_DISPLAY_NAME, file.getName().toLowerCase(Locale.US));
        values.put("_data", resultPath);

        ContentResolver cr = getContentResolver();
        cr.insert(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, values);




        return  resultPath;

0

इसे आज़माएं, यह एक नई छवि के बारे में प्रसारित होगा, जिससे आपकी छवि दिखाई देगी। एक गैलरी के अंदर। फोटोफाइल नई बनाई गई छवि के वास्तविक फ़ाइल पथ के साथ बदल देता है

private void galleryAddPicBroadCast() {
        Intent mediaScanIntent = new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE);
        Uri contentUri = Uri.fromFile(photoFile);
        mediaScanIntent.setData(contentUri);
        this.sendBroadcast(mediaScanIntent);
    }
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.