2012-01-29 17 views
10

Estoy desarrollando una aplicación de diccionario. En mi aplicación, supongo que el usuario quiere guardar las palabras favoritas. He decidido usar SharedPreferences para guardar estos valores (soy consciente de que SQLite y los archivos son mejores, pero estoy atascado en "SharedPreferences", así que sigo con él).¿Cómo se usa SharedPreferences para guardar más de un valor?

A continuación es mi código:

@Override 
public void onClick(View v) {          
    SharedPreferences faves = PreferenceManager.getDefaultSharedPreferences(getApplicationContext()); 
    { 
     SharedPreferences.Editor editor = faves.edit(); 
     editor.putString("favourite", mSelectedDB + "::" + mCurrentWordId + "::" + mCurrentWord + ","); 
     editor.commit();  
    } 
    Log.i(CONTENT_TAG,"Favourite saved!"); 

    Toast toast = Toast.makeText(ContentView.this, R.string.messageWordAddedToFarvourite, Toast.LENGTH_SHORT); 
    toast.show(); 
} 

El problema es que no conserva más de una palabra favorita. Quiero decir que solo se guarda una palabra favorita y cuando se agrega una nueva, se borra la anterior.

Entonces, ¿cómo se puede editar el código anterior para que se resuelva este problema?

¿Pueden ayudarme? Muchas gracias.

Respuesta

17

Puede guardar varios favoritos en una sola preferencia agregando numerosos favoritos en una sola cadena, cada elemento favorito separado por comas. Luego puede usar el método convertStringToArray para convertirlo en String Array. Aquí está el código fuente completo.
Utilice MyUtility Methods para guardar varios artículos favoritos.

  MyUtility.addFavoriteItem(this, "Sports"); 
      MyUtility.addFavoriteItem(this, "Entertainment"); 

obtener una cadena de serie de todos los favoritos guardados

String[] favorites = MyUtility.getFavoriteList(this);// returns {"Sports","Entertainment"}; 

Guardar estos métodos en la clase de servicio independiente

public abstract class MyUtility { 

    public static boolean addFavoriteItem(Activity activity,String favoriteItem){ 
     //Get previous favorite items 
     String favoriteList = getStringFromPreferences(activity,null,"favorites"); 
     // Append new Favorite item 
     if(favoriteList!=null){ 
      favoriteList = favoriteList+","+favoriteItem; 
     }else{ 
      favoriteList = favoriteItem; 
     } 
     // Save in Shared Preferences 
     return putStringInPreferences(activity,favoriteList,"favorites"); 
    } 
    public static String[] getFavoriteList(Activity activity){ 
     String favoriteList = getStringFromPreferences(activity,null,"favorites"); 
     return convertStringToArray(favoriteList); 
    } 
    private static boolean putStringInPreferences(Activity activity,String nick,String key){ 
     SharedPreferences sharedPreferences = activity.getPreferences(Activity.MODE_PRIVATE); 
     SharedPreferences.Editor editor = sharedPreferences.edit(); 
     editor.putString(key, nick); 
     editor.commit();       
     return true;   
    } 
    private static String getStringFromPreferences(Activity activity,String defaultValue,String key){ 
     SharedPreferences sharedPreferences = activity.getPreferences(Activity.MODE_PRIVATE); 
     String temp = sharedPreferences.getString(key, defaultValue); 
     return temp;   
    } 

    private static String[] convertStringToArray(String str){ 
     String[] arr = str.split(","); 
     return arr; 
    } 
} 

Si tiene que añadir favoritos adicionales. A continuación, obtenga la secuencia favorita de SharedPreference y añada la coma + elemento favorito y guárdela de nuevo en SharedPreference.
* Puede usar cualquier otra cadena para separador en lugar de coma.

+0

Muchas gracias. Pero aún no entiendo qué hacer programáticamente. Aquí está la cadena de SharedPreferences: ' dict_name :: 149272 :: go,'. ¿Dónde debe colocarse tu código? –

+0

@ user998032 He agregado el código para explicar cómo podemos agregar varios artículos favoritos. Puede usar el código tal como está, funcionará para usted. –

+0

@@ Muhammad Nabeel Arif: Muchas gracias, pero aún no tuvimos suerte, lo siento! Quiero que el favorito se guarde después de onClick, pero se producen muchos errores después del código editado anterior. –

7

SharedPreferences funcionan a través de una clave/valor simple de modo que cuando proporcione un nuevo valor para la misma clave, se sobrescriba el valor anterior. La única forma de hacer lo que intenta hacer es usar diferentes claves, lo que sugiere que probablemente no debería usar SharedPreferences para lo que está tratando de hacer.

5

Honeycomb añadió el método putStringSet, por lo que podría utilizar que si usted no tiene que soportar cualquier cosa menos de nido de abeja:

@Override 
public void onClick(View v) { 
    SharedPreferences faves = PreferenceManager.getDefaultSharedPreferences(getApplicationContext()); 
    { 
     Set<String> faveSet = faves.getStringSet("favourite"); 
     faveSet.add(mSelectedDB + "::" + mCurrentWordId + "::" + mCurrentWord + ","); 
     SharedPreferences.Editor editor = faves.edit(); 
     editor.putStringSet("favourite", faveSet); 
     editor.commit(); 
    } 
    Log.i(CONTENT_TAG,"Favourite saved!"); 

    Toast toast = Toast.makeText(ContentView.this, R.string.messageWordAddedToFarvourite, Toast.LENGTH_SHORT); 
    toast.show(); 
} 

Si necesita soporte para dispositivos pre-nido de abeja, que tendrá que llegar con su propio esquema.

Una posibilidad es almacenar las palabras como valores separados por comas en una preferencia.

Otra es generar una nueva clave para cada nueva palabra, "favourite1", "favourite2", "favourite3" y tiene otra preferencia que utiliza para almacenar el número de palabras.

+0

Eso es cierto, pero desafortunadamente estoy haciendo cosas para los dispositivos pre-Honeycomb. Muchas gracias. –

2

Cada vez que hace clic en el botón, guarda la palabra favorita con la clave ya presente: favorite y la reemplaza. Para guardar más de una palabra, debes guardar las palabras con diferentes claves. Así que cada vez que se guarda una palabra favorita que podría hacer:

private static int incrementedValue = 0; 
... 
@Override 
public void onClick(View v) { 
    SharedPreferences faves = PreferenceManager.getDefaultSharedPreferences(getApplicationContext()); 

    SharedPreferences.Editor editor = faves.edit(); 
    editor.putString("favourite" + incrementedValue, mSelectedDB + "::" + mCurrentWordId + "::" + mCurrentWord + ","); 
    editor.commit(); 

    Log.i(CONTENT_TAG,"Favourite saved!"); 

    Toast toast = Toast.makeText(ContentView.this, R.string.messageWordAddedToFarvourite, Toast.LENGTH_SHORT); 
    toast.show(); 
    incrementedValue++; 
} 
+0

Muchas gracias. Me gusta su enfoque pero cuando se aplica, produce errores con ** incrementedValue **, diciendo VariableDeclarationId esperado después ... –

+0

@ user998032 He editado mi respuesta, olvidé agregar 'int' a la declaración de la variable incrementedValue (no te olvides de agregar la primera línea, la declaración de la variable, en tu clase con el método onClick()). – Luksprog

+0

Muchas gracias, slukian! Funciona pero no como esperaba. SharePreferences ahora guarda las cadenas como: ' dict_name :: 157562 :: heap up, dict_name :: 31377 :: bell, dict_name :: 349333 :: tell, dict_name :: 349333 :: tell, dict_name :: 11834 :: am,', pero solo la primera palabra favorita ("favourite0") se carga para ver. –

1

Bueno, eso es debido a que el almacenamiento de preferencia real no es una lista de cadenas, a uno solo, por lo que cada vez que usted dice putString() sobrescribe el valor anterior. Una buena forma de almacenar múltiples objetos en una sola cadena de preferencias es usar JSON. Simplemente serialice el valor y luego escríbalo. También tiene el beneficio de convertir directamente a un objeto de la complejidad que desee. Consulte si usa el Jackson si decide seguir esta ruta.

1

Puede usar un TreeMap (u otro tipo de lista que implemente Serializable). Así es como manejé una lista de favoritos recientemente. En TreeMap, Favorite es una clase que uso. En su caso, podría usar TreeMap < Entero, Cadena> en su lugar.

private static TreeMap<Integer, Favourite> favourites; 

... 
... 
... 

// load favourites 
FileInputStream fis=null; 
ObjectInputStream ois = null; 
try { 
    fis = context.openFileInput(context.getString(R.string.favourites_file)); 
    try { 
    ois = new ObjectInputStream(fis); 
    favourites = (TreeMap<Integer, Favourite>) ois.readObject(); 
    } catch (StreamCorruptedException e) { 
    } catch (IOException e) { 
    } catch (ClassNotFoundException e) { 
    } 
} catch (FileNotFoundException e) { 
} finally { 
    try { 
    if (ois!=null){ 
     ois.close(); 
    } 
    } catch (IOException e) { 
    }  
} 

if (favourites==null){ 
    favourites = new TreeMap<Integer, Favourite>();  
} 

... 
... 
... 

// save favourites 
FileOutputStream fos=null; 
ObjectOutputStream oos=null; 
try { 
    fos = context.openFileOutput(context.getString(R.string.favourites_file), MODE_PRIVATE); 
    try { 
    oos = new ObjectOutputStream(fos); 
    oos.writeObject(favourites); 
    } catch (IOException e) { 
    } 
} catch (FileNotFoundException e) { 
} finally { 
    if (oos!=null){ 
    try { 
     oos.close(); 
    } catch (Exception e2) { 

    } 
    }  
} 

También puede evitar la "::" cosa que está haciendo para separar los valores.

Espero que ayude ...

+0

Muchas gracias. He intentado el similar antes, pero tengo un problema cuando los favoritos están en la lista. –

Cuestiones relacionadas