This might be Android 101, but I'm getting used to the SDK now. Anyhow, I simply do not understand the error. I want to update some checkbox selections based on my shared preferences file and I'm using the following method:
private void updatePreferencesData() {
SharedPreferences prefs = getSharedPreferences(PREFS_NAME, 0);
Boolean textData = prefs.getBoolean(R.string.Chri, false);
CheckBox cb1 = (CheckBox) findViewById(R.id.chkbxChristmas);
cb1.setChecked(textData);
}
Android Studio doesn't like my use of R.string.Chri in Boolean textData = prefs.getBoolean(R.string.Chri, false);
It states: "getBoolean(java.lang.String, Boolean) in SharedPreferences cannot be applied to (int, Boolean)"
In my strings.xml I have the value:
<string name="Chri">Christmas</string>
When I simply change the line to
Boolean textData = prefs.getBoolean("Christmas", false);
It works fine
How is it that the strings in strings.xml is being handled differently?
Thank you!
Android Studio doesn't like my use of R.string.Chri in Boolean textData = prefs.getBoolean(R.string.Chri, false);
Correct. R.string.Chri is an int. To get a string, call getString(R.string.Chri) on some Context, such as your activity.
You should use:
prefs.getBoolean(this.getResources().getString(R.string.Chri), false);
R.string.Chri is an int. Instead use getResources().getString(R.string.Chri) to retrieve the string.
Related
I create a few ArrayLists during one of my activities. When I leave the activity and come back to it, they come up as null. From some research, SharedPreferences is the way to overcome this. How do I go about this; do I have to save it as a HashMap? is SharedPreferences it's own method or do I do it within another specific method?
You have at least three options:
Use a SharedPreferences object as you suggest in your question.
Use a SQLite database.
Use a file with your own format.
For an introduction to each of these options, read Storage Options.
Here, how to write on Shared Preferences:
SharedPreferences sp = getActivity().getPreferences(Context.MODE_PRIVATE);
//if your codes in your activity class, you dont need getActivity so you should use this
SharedPreferences.Editor editor = sp.edit();
editor.putInt("your_string_key", yourValue);
editor.commit();
Here, how to read from Shared Preferences:
SharedPreferences sp = getActivity().getPreferences(Context.MODE_PRIVATE);
//same here. If your codes in your activity don't write "getActivity." part
int yourSavedValue = sp.getInt("your_string_key", defaultValue);
//defaultValue mean if there is no value with that key, it will return defaultValue.
If you'd like to learn more about it here you can get more information.
Answer to your new updated question:
As you can see my answer there is defaultValue.
// Restore preferences
SharedPreferences settings = getSharedPreferences(PREF_FILE, Context.MODE_PRIVATE);
Set<String> tempSet = settings.getStringSet(FIRST_LIST, "");
Set<String> temp2Set = settings.getStringSet(SECOND_LIST, "");
//if it is first time it will return null. So your app going crash. To avoid that make a default value. Like this.
for (String str : tempSet)
firstList.add(Uri.parse(str));
for (String str : temp2Set)
secondList.add(Uri.parse(str));
** you have convert this array to gson.
** First pass your array in parameter public void saveArrayList(ArrayList list, String key)
** now create object of SharedPreferences
SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(activity);
SharedPreferences.Editor editor = prefs.edit();
** now convert to gson :
Gson gson = new Gson();
String json = gson.toJson(list);
editor.putString(key, json);
editor.apply(); // This line is IMPORTANT !!!
I have two activities; the first activity starts the second one with some data passed through the intent.
Intent i = new Intent(this,BActivity.class);
i.putExtra("identify", "c2f");
startActivityForResult(i, 1);
In the second activity, I want to make some TextViews/EditTexts visible (which are initially set to invisible) based on the information passed from the first activity.
Here's the code for that:
tv1 = (TextView)findViewById(R.id.textView2);
tv2 = (TextView)findViewById(R.id.textView3);
et1 = (EditText)findViewById(R.id.editText1);
et2 = (EditText)findViewById(R.id.editText2);
button = (Button)findViewById(R.id.send_result);
Bundle extras = getIntent().getExtras();
String identifier = extras.getString("identify");
if(identifier == "c2f")
{
tv1.setVisibility(0);
tv1.setText("Celcius");
et1.setVisibility(0);
}
else if(identifier == "f2c")
{
tv1.setVisibility(0);
tv1.setText("Fahrenheit");
et1.setVisibility(0);
}
else if(identifier == "currency")
{
tv1.setVisibility(0);
tv1.setText("Amount");
tv2.setVisibility(0);
tv2.setText("Conv. Rate");
et1.setVisibility(0);
et2.setVisibility(0);
}
Now when the second activity starts, none of these TextViews or EditTexts seem to get visible!
identifier (string) holds the correct value passed from first activity and it even goes into the if conditions, but it doesn't make any view visible.
Am I making any mistake in trying to make these views visible?
Use .equals instead of == to string comparison. You can also use the variable after the quoted string to avoid nullpointer. And you can use TextView.VISIBLE, it's a constant to get it visible.
if("c2f".equals(identifier))
{
tv1.setVisibility(TextView.VISIBLE);
tv1.setText("Celcius");
et1.setVisibility(TextView.VISIBLE);
}
Simply use the View's constants for this.
your_view.setVisibility(View.VISIBLE);
This will make your View visible.
your_view.setVisibility(View.INVISIBLE);
This will make it invisible but still with the layout visible (basically, the space where it goes remains untouched)
your_view.setVisibility(View.GONE);
This will make your View disappear, like it never existed!
As pointed by giacomoni, please use equals for String comparison. Here is a link to explain why.
http://javarevisited.blogspot.in/2012/03/how-to-compare-two-string-in-java.html
Also, try using the standard View.VISIBLE etc constants for showing and hiding views. They are much more easy to use and understand. Happy coding. :)
I am pretty new to the android programming thing so I am sure that there is something simple that I am not doing correctly. I have two activities that are accessing a shared preferences file; one that reads from it and displays the contents to a list, and the other reads the contents and adds a new item to the list based upon user input. The issue that I am having: when I read the contents from the file and attempt to add a new item to the list my original list is being overwritten. Maybe that's not what is actually happening but it seems to me that this is the issue. When I add a new item from the child activity and return to the original activity which displays the list I am only seeing the newest item that I saved and not any other items that I had created previously.
The first activity is the main activity and it simply reads the shared preferences and adds the items in a string, separated by commas and displays them in a listview. I only showed the method for displaying the items in the listview:
public void addItems() {
String strLists="";
SharedPreferences sharedPref = getSharedPreferences("ListNamesFile", MODE_PRIVATE);
strLists = sharedPref.getString(getString(R.string.edit_message), strLists);
listItems.clear();
String[] myLists = strLists.split(",");
for(int r=0;r<myLists.length;r++){
listItems.add(myLists[r].toString());
}
//test adding an extra list item to make sure that the issue isn't from adding
//items to the listview
//listItems.add("test");
adapter.notifyDataSetChanged();
}
The second activity is for getting a new string from an edit text control, adding it to the end of the string with the list items, and committing the changes to the shared preferences file. I have included the method for retrieving the shared preferences and writing the new item to the end of the string:
public void createListOnClick(View view){
//create a file for storing list items
SharedPreferences sharedPref = getSharedPreferences("ListNamesFile", MODE_PRIVATE);
String strMyLists = "";
sharedPref.getString(getString(R.string.edit_message),strMyLists);
String[] lists = strMyLists.split(",");
StringBuilder sb = new StringBuilder();
for (int i = 0; i < lists.length; i++) {
sb.append(lists[i]);
sb.append(",");
}
SharedPreferences.Editor editor = sharedPref.edit();
EditText txtListName = (EditText)findViewById(R.id.txt_list_name);
sb.append(txtListName.getText().toString());
editor.putString(getString(R.string.edit_message), sb.toString());
editor.commit();
finish();
}
It seems that it must be something simple that I am missing but I haven't been able to figure it out so any help would be greatly appreciated.
you still haven't assigned the sharedPref value in the strMyLists.
In the second activity, you're not actually assigning the read shared preferences:
You should replace
sharedPref.getString(getString(R.string.edit_message),strMyLists);
with
strMyLists = sharedPref.getString(getString(R.string.edit_message),strMyLists);
in getString method
sharedPref.getString(getString(R.string.edit_message),strMyLists);
second argument is default value. So you will have to write.
strMyLists = sharedPref.getString(getString(R.string.edit_message),"");
it will work with this. rest of the code is good.
I have created two EditText objects in the Java code of My android application, as
final EditText et1=(EditText)findViewById(R.id.editText1);
final EditText et2=(EditText)findViewById(R.id.editText2);
then on the onClick() event of a button, called a method with parameters as-
addStringToXmlFile(et1.getText(),et2.getText());
now in the definition of this method below, i have written-
private void addStringToXmlFile(Editable editable1,Editable editable2){
String s1=new String();
s1=editable1.toString();
String s2=new String();
s2=editable2.toString();
}
The problem is that, now i want to use these two String objects s1,s2, to make two entries in the res/values/Strings.xml file of the database, & I don't know how to do it.
please guide me further.
This is not possible - an app's apk (including it's resources) can not be changed at runtime. I'm not entirely sure of all of the reasons why, but one obvious thing I can think of is that R.java needs to contain a reference to your String in order for you to access it, and this file is generated by the compiler when you create the APK.
If you need to persist a String across sessions, you should look into using one of several data storage mechanisms that Android provides, such as SharedPreferences.
Take a look into using SharedPreferences to store your string values instead.
//Saving your strings
SharedPreferences prefs = this.getSharedPreferences("myPrefsKey", Context.MODE_PRIVATE);
Editor editor = prefs.edit();
editor.putString("s1", s1);
editor.putString("s2", s2);
editor.commit();
//retrieving your strings from preferences
SharedPreferences prefs = this.getSharedPreferences("myPrefsKey", Context.MODE_PRIVATE);
String s1 = prefs.getString("s1", ""); //empty string is the default value
String s2 = prefs.getString("s2", ""); //empty string is the default value
When I create preference activity I define all preferences in xml file. Every preference has a key defined in this xml. But when I access preference I write:
SharedPreferences appPreferences = PreferenceManager.getDefaultSharedPreferences(this);
boolean foo_value = appPreferences.getBoolean("foo_key_defined_in_xml", false);
Is there any way to avoid referencing "foo_key_defined_in_xml" in hard-coded way?
Maybe there is a possibility to reference it in R style way (not to refer to string)?
I've found that it's possible to store keys in strings.xml and refer to them from preferences.xml just like all other values android:key="#string/preference_enable".
In code you can refer to key by typing getString(R.string.preference_enable)
You can mark the string to not be translated using a <xliff:g> tag. See Localization Checklist
<string name="preference_enable"><xliff:g id="preference_key">enable</xliff:g></string>
You could use a "keys.xml" files in "res/values", but should put something like this, this way you should dont have problem when you are using multiple languages:
<resources
xmlns:tools="http://schemas.android.com/tools"
tools:ignore="MissingTranslation">
<string name="key1">key1</string>
<string name="key2">key2</string>
...
</resources>
Then you could reference it like a normal string in xml:
....
android:key="#string/key1"
....
or in your java code for example:
SwitchPreference Pref1= (SwitchPreference) getPreferenceScreen().findPreference(getString(R.string.key1));
In strings.xml mark the key as untranslatable:
<string name="screw_spacing_key" translatable="false">Screw spacing</string>
<string name="screw_spacing_title">Screw spacing</string>
<string name="screw_spacing_summary">Set screw spacing</string>
Usage:
<EditTextPreference
android:key="#string/screw_spacing_key"
android:title="#string/screw_spacing_title"
android:summary="#string/screw_spacing_summary"/>
See: Configure untranslatable rows
Try getString(R.string.key_defined_in_xml).
As far as I know there's no better way of referencing preference keys (aside from maybe using a static final String to store the string on the class).
The example given in the SDK docs does the same as what you've given in your example,
What about using a helper class to hide the getString() - instantiate the helper once in each activity or service. For example:
class Pref {
final String smsEnable_pref;
final String interval_pref;
final String sendTo_pref;
final String customTemplate_pref;
final String webUrl_pref;
Pref(Resources res) {
smsEnable_pref = res.getString(R.string.smsEnable_pref);
interval_pref = res.getString(R.string.interval_pref);
sendTo_pref = res.getString(R.string.sendTo_pref);
customTemplate_pref = res.getString(R.string.customTemplate_pref);
webUrl_pref = res.getString(R.string.webUrl_pref);
}
}
Not sure if this post need another answer, put i end up to it like this:
-Extend all the Preference needed and add this code
final static private int[] ATTR_INDEX = {android.R.attr.id};
private void init(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes){
if(attrs == null) return;
AttributeReader attributes = new AttributeReader().setAttrsIndex(ATTR_INDEX).parse(attrs);
int id = attributes.asResourceID(0);
setKey(AppContext.getIdentifierName(id));
}
In the xml, don't use the key attribute but android:id="#+id/...
And finally to get back the value,
SharedPreferences SP = PreferenceManager.getDefaultSharedPreferences(getContext());
String preference_1 = SP.getString(AppContext.getIdentifierName(R.id.pref_key_1), null);
This way, you don't have to create a string file who need to be maintain, just create any id on the fly. But you need to be familiar with extending a view and get read the attr to find what you want (Here the id attribute)