Доступ к хранилищу в Nook - PullRequest
       30

Доступ к хранилищу в Nook

4 голосов
/ 11 октября 2011

Ближайшая вещь к документации, которую я могу найти, касающаяся хранения файлов, - этот пост (см. Ниже, если вы не можете получить к нему доступ), но он оставляет меня с несколькими вопросами.

Мне бы очень, очень, очень хотелось получить грамотное объяснение того, какие пути отображаются в каком хранилище здесь, видя, как мы должны жестко их кодировать и насколько точно мы должны получить к ним доступ. Фактический пример кода будет превосходным. Моя лучшая догадка от возни с этим:

  • / sdcard-> сопоставляется с внутренним слотом eMMC, и доступ к нему ограничен. Environment.getExternalStorageDirectory (); ... все еще возвращает это.
  • / media -> сопоставляет внутреннюю память 8 ГБ (я могу написать в это)
  • / data ->?
  • ? -> сопоставление с дополнительной картой microSD

Как мы можем получить доступ к внешней (необязательной, дополнительной, той, которую вы можете выдвинуть) sdcard, если вместо нее / sdcard отображается в ограниченное хранилище ?

Теперь процитируем документы разработчика Nook:

Фон. Существуют две разные схемы разбиения для NOOK. Цветные устройства на рынке сегодня, одно из которых доступно только 250 МБ приложения на / data разделе и один с 4 ГБ доступны для приложения в разделе / ​​data. В результате крайне важно что приложения спроектированы и разработаны таким образом, чтобы эффективно управлять пространством. Приложения, которые этого не сделают, не будут принимаются к распространению через Магазин.

Техническая рекомендация или решение, связанное с территорией, если ваш приложение требует большого количества данных (включая, но не ограничиваясь для изображений, аудио или видео), вы должны загрузить эти ресурсы во время выполнения и хранить их в большем разделе устройство. Если ваше приложение будет запрашивать и хранить более 100 МБ данных или ресурсов, которые вы ДОЛЖНЫ соблюдать Ограничения:

Ваша заявка должна четко и недвусмысленно указываться в описании при условии, что большое количество данных используется / доставляется приложение. Вы ДОЛЖНЫ записать свои ресурсы и данные на соответствующие раздел. Вы можете обнаружить, если устройство имеет увеличенный / данные разделить следующим образом:

StatFs stat = new StatFs("/data"); 
long bytesAvailable = (long)stat.getBlockSize() *(long)stat.getBlockCount(); 
long megAvailable = bytesAvailable / 1048576; 
if (megAvailable > 1000){   
... write your resources in /data
} else {  
... write your resources on /mnt/media ... 
} 

Для записи данных в личное пространство вашего приложения в / data

FileOutputStream fos = openFileOutput(FILENAME, Context.MODE_WORLD_READABLE); 

Ваша заявка НЕ ​​должна принимать наличие SD-карты на устройстве, но вы можете проверить ее с помощью звонка до

* 1 035 * Environment.getExternalStorageState (); Если SD-карта не найдена, ваше приложение ДОЛЖНО завершаться корректно с уведомлением пользователя что касается причины выхода.

Помните, что для доступа к разделу / media, а также ExternalStorage необходимо указать в манифесте:

<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE">
</uses-permission>

Ответы [ 2 ]

4 голосов
/ 23 октября 2011

Хорошо, вот что я выучил за последние пару недель.

Если вы хотите записать на внутреннюю SD-карту , используйте Context.getFilesDir () .Он вернет личный каталог для вашего приложения.Вы не можете придумать свои собственные каталоги на внутреннем флеш-накопителе (он же "/ data").У вас нет разрешения на запись нигде, кроме папки, назначенной вашему приложению.Предположительно есть два внутренних раздела, "/ data" и "/ media", но я не могу добраться до "/ media", чтобы спасти мою жизнь.

Вы можете использовать внешнюю флэш-память , "/ sdcard", если она доступна.Это карта, которую вы можете вытащить из устройства.Есть два способа сделать это:

  • Хранить вещи в папке, назначенной вашему приложению (поэтому она будет удалена при удалении вашего приложения).Вы можете найти эту папку с помощью Context.getExternalFilesDir () .
  • Храните вещи где угодно, по какому-нибудь жестко заданному пути в "/ sdcard / foo / bar" или в Environment.getExternalStorageDirectory () / независимо от того.

Этот пост от представителя B & N (на который я ссылался в моем вопросе) оказался чем-то вроде красной сельди, "/ sdcard" не отображается на слоте eMMC, и я понятия не имеючто означает «мы подключили SD-карту к нашей внутренней eMMC».

В этом посте B & N говорится, что "/ media" является внутренним, но я не могу писать в него, даже если у меня есть соответствующие разрешения для манифеста ... так что поймите рисунок.

Это скриншот моего тестового устройства, показывающий, что является и не доступно: enter image description here

Код для этого (обратите внимание, что FileUtils не включен в SDK по умолчаниюЭто из библиотеки org.apache.commons.io):

public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.main);

    TextView dataView = (TextView) findViewById(R.id.data);
    dataView.setText(testIt("/data"));

    TextView mediaView = (TextView) findViewById(R.id.media);
    mediaView.setText(testIt("/media"));

    TextView mntMediaView = (TextView) findViewById(R.id.mntMedia);
    mntMediaView.setText(testIt("/mnt/media"));

try {
        File fd = this.getFilesDir();
        if(fd != null) {
            TextView fdView = (TextView) findViewById(R.id.filesDir);
            fdView.setText("getFilesDir(): " + testIt(fd.toString()));
        }
} catch (Exception e) {
    e.printStackTrace();
}

try {
        File efd = this.getExternalFilesDir(null);
        if(efd != null) {
            TextView efdView = (TextView) findViewById(R.id.externalFilesDir);
            efdView.setText("getExternalFilesDir(): " + testIt(efd.toString()));
        }
} catch (Exception e) {
    e.printStackTrace();
}

try {
    File esd = Environment.getExternalStorageDirectory();
        if(esd != null) {
            TextView esdView = (TextView) findViewById(R.id.externalStorageDirectory);
            esdView.setText("getExternalStorageDirectory(): " + testIt(esd.toString()));
        }
} catch (Exception e) {
    e.printStackTrace();
}

try {
    File espd = Environment.getExternalStoragePublicDirectory(null);
        if(espd != null) {
            TextView espdView = (TextView) findViewById(R.id.externalStoragePublicDirectory);
            espdView.setText("getExternalStoragePublicDirectory(): " + testIt(espd.toString()));
        }
} catch (Exception e) {
    e.printStackTrace();
}
}

public String testIt(String dir){
    StatFs stat = new StatFs(dir);
        long bytesAvailable = (long) stat.getBlockSize() * (long) stat.getBlockCount();
        long megAvailable = bytesAvailable / FileUtils.ONE_MB;
        File dirFile = new File(dir + "/test/");
        dirFile.mkdir();

        return dir + "/test \n canRead() " + dirFile.canRead() + ", \n canWrite() " + dirFile.canWrite() + " with " + megAvailable + "MB available";
}
0 голосов
/ 16 октября 2011

Прежде всего попробуйте следующие методы:

Если ни один из них не возвращает вам каталог, в который вы можете писать, проверьте следующий поток google-groups и используйте код, указанный в последнем ответе, который перечисляет все текущие точки монтирования:

У меня такая же проблема с Galaxy S. До сих пор все устройства Android у меня
есть команда «mount». Я строю список доступных томов парсинг "монтирования" ответа. Это не идеально, но умнее, чем Android API хранилища.

String cmd = "/system/bin/mount"; 
try { 
   Runtime rt = Runtime.getRuntime(); 
   Process ps = rt.exec(cmd); 

   BufferedReader rd = new BufferedReader( new InputStreamReader(ps.getInputStream()) ); 
   String rs; 
   while ((rs = rd.readLine()) != null) 
   { 
       //check what you need! 
       Log.i("MOUNT_CMD", rs); 
   } 
   rd.close(); 
   ps.waitFor(); 
} catch(Exception e) { 
//...
}

Если есть возможность вставить карту microSD в устройство Nook во время его работы, вы также можете попробовать следующее:

mVolumeManagerReceiver = new BroadcastReceiver() { 
  public void onReceive(Context context, Intent intent) { 
    Log.i("MediaMounter", "Storage: " + intent.getData()); 
  } 
}; 

IntentFilter filter = new IntentFilter(); 
filter.addAction(Intent.ACTION_MEDIA_MOUNTED);
filter.addAction(Intent.ACTION_MEDIA_UNMOUNTED); 
filter.addAction(Intent.ACTION_MEDIA_REMOVED); 
filter.addDataScheme("file"); 
context.registerReceiver(mVolumeManagerReceiver, filter);
...