My problem is that i've a tabhost with two tabs.
The first is a listview and the second only have two textviews.
What i want is when i click on an item in the listview on tab one, the array position id (int) should be sent to tab/class two, where there is an array who fetches a text by the position id that was sent.
The switching of tabs is done, but i fail everytime i try to send the position-id.
This is how i send it:
TAB ONE:
//This function is called when i click a listitem
public void setDetails(String Text, long arr_id){
Detail detail = new Detail();
detail.setDetail(); // right now i don't send the parameters because it wont even work with or without it.
}
TAB TWO:
TextView descr;
TextView title;
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.detail);
descr = (TextView)findViewById(R.id.desc);
title = (TextView)findViewById(R.id.title);
}
public void setDetailText(String Text){
descr.setText(Text);
}
public void setDetailTitle(String Text){
title.setText(Text);
}
public void setDetail(){
this.setDetailTitle("example text");
this.setDetailText("example text2");
}
I want to set the text on tab two BEFORE it switch to tab two.
This works if i use SetDetail() and setDetailTitle() in the same tab/class, but not in another.
I've googled my ass off, please help me
i do this in my code using getParent() or getActivity() methods in my TabActivity and inner Activitys, cause if we use a TabActivity (wich subclass the ActivityGroup class) we can obtain the 'TextActivity' using ActivityManager and obtain the activity instance, so, here we can call the setDetail() method, and this will execute before the Activity is showed,
in your ListActivity do something like this
((MyTextActivity)((MyTabActivity)getParent()).getLocalActivityManager().getActivity(ACTIVITY_ID)).setDetail();
this works only if in you start the childs activity within your TabActivity with:
intent = new Intent(ACTIVITY_ID).setClass(this, MyMapActivity.class);
getLocalActivityManager().startActivity(ACTIVITY_ID, intent);
Related
I have searched through StackOverflow, but have not found a proper answer yet.
I have created a ListView (iteration of a checkbox + itemview) and populated it through my customAdapter (which extends BaseAdapter).
I have a button which takes the values and print it on the screen via a Toast.
So far, so good.
Next step, I still have the button in the MainActivity, but the ListView is now in a child activity that I reach by clicking an image (ImageView placed in the MainActivity). I can still check the checkboxes, but I face two issues:
I am still not able to pass the values to the MainActivity, where they will be printed on screen (or manipulated)
As soon as I press the back button to go back to the MainActivity and I press again the image, every CheckBox that was checked is not checked anymore (they came back to default state)
I don't think that code is needed, as it comes from a standard implementation (ListView - customAdapter with ViewHolder implementation, ...), but in case just let me know.
Thanks a lot in advance!
You can put which checkboxes are checked into sharedpreferences. Then move the listview initialization code to Activity's onResume method.
Sample class to handle sharedpreferences data:
class DataHandler {
private final SharedPreferences dataStore;
DataHandler(Context mContext) {
dataStore = mContext.getSharedPreferences("appname", Context.MODE_PRIVATE);
}
int which() {
return dataStore.getInt("some_key",0);
}
void setCheckedItem(int itemwhat) {
dataStore.edit().putInt("some_key",itemwhat).apply();
}
}
For multiple values, you can put them into an array then convert them to string using toString() method and save. And, to get the values:
String x = "2,3,4,5"; //assume
String[] y = new String[]{x};
int checkablepositions = Integer.parseInt(y[0]); // y[0]....y[y.length-1]
Now, at MainActivity's onResume(), Assume that you have initialized ListView as 'mainList'.
CheckBox x1y2z3 = (CheckBox)mainList.getChildAt(new DataHandler(getBaseContext).which());
x1y2z3.setChecked(true);
And for Saving item,
I would recommend you to show them in an alert-dialog instead of in a Toast. Then set a Positive button to get the values from below code and save them.
Or, if you directly save the values from listview onClick :
mainList.setOnItemClickListener(new OnItemClickListener() {
public void onItemClick(AdapterView<?> parent, View view,
int position, long id) {
new DataHandler(getBaseContext()).setCheckedItem(position);
}
});
That's it. I'm really new at programming (as you can see my StackOverFlow rep) but hope it will be able to help you.
The main concept is to : store the value → get the value → parse the value → show it on UI.
I have a problem. I have 3 activities (MainActivity, DetailsActivity, SettingsActivity) and in SettingsActivity I have a Togglebutton "Nightmode". What I want is, when the button is changed, change background of all three activities on gray color.
public class SettingsActivity extends AppCompatActivity {
//This is SettingsActivity(not Main one)
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_settings);
TextView SettingsTitle = (TextView) findViewById(R.id.SettingsTitle);
TextView NightText = (TextView) findViewById(R.id.NightmodeText);
ToggleButton toggleNightMode = (ToggleButton) findViewById(R.id.toggleNightmode);
final RelativeLayout NightBG = (RelativeLayout) findViewById(R.id.NightBG);
final LinearLayout DetailsBG = (LinearLayout) findViewById(R.id.mainBG);
final LinearLayout HomeBG = (LinearLayout) findViewById(R.id.HomeBG);
toggleNightMode.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
NightBG.setBackgroundColor(Color.parseColor("#545657"));
HomeBG.setBackgroundColor(Color.parseColor("#545657"));
DetailsBG.setBackgroundColor(Color.parseColor("#545657"));
}
});
NightBG is in the same activity as that java file (SettingsActivity). But HomeBG is in MainActivity and DetailsBG is in the DetailsActivity. Everytime I start the app, and press on that button, app craches. If I delete HomeBG and DetailsBG from this file, it works just fine with changing current layout's color to gray. Please help me.
One easy way to store little settings like this across multiple activities that may not be open/active at the time of the button click would be to use SharedPreferences.
It might be a little overkill for such a simple piece of code but you can always give it a try if you don't find anything else.
Your code could look something like this:
toggleNightMode.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
// Set the color of this activity
int color = Color.parseColor("#545657")
View view = SettingsActivity.this.getWindow().getDecorView();
view.setBackgroundColor(color);
// Save color preference
SharedPreferences sharedPref = SettingsActivity.this.getSharedPreferences("bgColorFile",Context.MODE_PRIVATE);
SharedPreferences.Editor editor = sharedPref.edit();
editor.putInt("color", color);
editor.apply();
}
});
And then when you open your activities you place something like this in the onStart() or onCreate() method of your activity:
// Get the color preference
SharedPreferences sharedPref = getSharedPreferences("bgColorFile",Context.MODE_PRIVATE);
int colorValue = sharedPref.getInt("color", 0);
View view = this.getWindow().getDecorView();
view.setBackgroundColor(colorValue);
So what you're actually doing is storing the background color as persistent data and fetching it once you reopen/open the activity that you want to have the color on. The benefit of this method is that whenever you close your app the preferred background color will be remembered. I hope this helps.
Change background for current activity in the same activity. Since DetailsActivity is not running, you can't do that, it gives you null pointer. Is kind of you are trying to eat 3 apples and you have just one. After current activity is started, change background.
Update:
You can do that in current activity and just in current activity:
findViewById(android.R.id.content).setBackground(getColor(R.color.your_color));
Don't try to call this in other activities that are not running.
setBackground()
or
setBackgroundColor()
If your other activities are open, you should send a message to the other activities by using an Intent.
How to send string from one activity to another?
When you receive the Intent you could then set the background of the activity.
If your other activities are not open yet, you will not be able to send an Intent to them. In this case you could have each Activity reference a static value in your main activity that could contain the current background color. You would want to reference that value on the other activities on create functions.
Here is an example on how to reference a variable from another activity.
How do I get a variable in another activity?
This might not be the most pretty way to handle it but it should work.
as Ay Rue said you have 2 options: use static variable for that button, and then in onResume of each activity, check the value of the static variable (true or false). or you can save a private variable nightMode and then pass this value in the intent when you need to move to the other two activities.
don't set the background color if you already set before and have an updated background color.
I am trying to take all the rows from my db and add it to the current layout, also, making each row clickable in the layout to take the user to a new screen with the id...
Here is my current code, but stuck on that part... I understand that I can put an onClickListener, but then does it have to be a button?
For a visual representation refer to a notepad app on any device where each note title appears and clicking on it takes you to that note.
public class MainActivity extends Activity implements OnClickListener {
private Button add_new_dictionary;
// Database helper
private DatabaseHelper db;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
// db setup
db = new DatabaseHelper(getApplicationContext());
// get all dictionaries
List<db_dictionary> allDictionaries = db.getAllDictioniaries();
for (db_dictionary dictionary_found : allDictionaries) {
// create new view for each dictionary name include id and make it
// dynamic and include onclick to take to dictionary_view screen
Button dictionary_button = new Button(this);
}
add_new_dictionary = (Button) findViewById(R.id.add_new_dictionary);
}
#Override
public void onClick(View v) {
if (v == add_new_dictionary) {
Intent add_new_dictionary_intent = new Intent(MainActivity.this,
add_new_dictionary.class);
startActivity(add_new_dictionary_intent);
}
}
}
To re-iterate the question: How do I go about dynamically taking rows from my db and adding it to my layout dynamically based on how many results are returned from the query? (However, the rows should be able to point to a new screen with the dictionary id)
All views in android can implement the OnClickListener interface. So no, it doesn't HAVE to be a button.
As you've decided to use the activity to handle this then you need to tell your code to pass the event to your implementation wihin your activity.
// create new view for each dictionary name include id and make it
// dynamic and include onclick to take to dictionary_view screen
Button dictionary_button = new Button(this);
dictionary_button.setOnClickListener(this);
A trick I use to store information is the setTag method which would allow you to retrieve the correct reference during your onClick:
dictionary_button.setTag(some_record_id);
Then retrieve it later:
#Override
public void onClick(View v) {
if (v == add_new_dictionary) {
Intent add_new_dictionary_intent = new Intent(MainActivity.this,
add_new_dictionary.class);
startActivity(add_new_dictionary_intent);
}
else (
Object tag = v.getTag();
//now launch the detail activity using the data from the tag
}
}
You should really look into ListAdapters and cursors to do this properly, but this method should get you going for now
If you need to pick data from a db and show it as a list (getting click events) you should probably look into CursorAdapter and ListView
http://developer.android.com/reference/android/widget/CursorAdapter.html
http://developer.android.com/reference/android/widget/ListView.html
You can fins many examples on the web on how to use a cursoradapter and the listview
I have a tabhost with two tabs. Each tab has his own activity. My goal is to execute a method in one of the tabs if the tab was changed. I have set up this OnTabChangedListener:
tabHost.setOnTabChangedListener(new OnTabChangeListener () {
#Override
public void onTabChanged(String tabID) {
Log.d("DEB", "Tab changed:" + tabID);
}});
This part works fine, everytime I change the tab a log entry is created.
Now I would like to call this method in the newly chosen tab:
public void refreshContent() {
setContentView(R.layout.listartists);
ArrayList<Song> searchResults = GetSearchResults();
final ListView lv1 = (ListView) findViewById(R.id.ListView02);
lv1.setAdapter(new MyCustomBaseAdapter2(this, searchResults));
Log.d("DEB", "ArtistView: Content refreshed.");
}
Is there anyone who can explain a possible solution for this?
Thank you in Advance!
Greetings from Germany!
Sebastian
try to put this code in onResume of the activity you want to execute this code when tab is changed because when the tab is clicked onResume is called for that activity
A navigation drawer with 3 Fragments, the third Fragment has a TextView with an on Click listener. Once it has been clicked a layout activity will open on the top which includes a ListView to allow the user to select/click on a specific Item, so later on this selected item info should be displayed on that TextView within the third fragment.
is there any method to pass data because I have used a class to pass data but the TextView wouldn't be refreshed with the sent data
This works as a design pattern to share arguments between the Activity and third fragment
--------------------------DataHolder Class---------------------------------
public class DataHolder {
private static DataHolder dataHolder = null;
private DataHolder() {
}
public static DataHolder getInstance() {
if (dataHolder == null)
{dataHolder = new DataHolder(); }
return dataHolder;
}
private String item;
public String getItem() {
return item;
}
public void setItem(String item) {
this.item = item;
}
}
If you find using startActivityForResult not sufficient in your case or using EventBus, you can overcome this by using SharedPreferences and Fragment/Activity lifecycle.
So once you start new Activity first Activity will go in onPause and with it all its Fragments will be put in onPause. When user clicks on one of the ListView items in your second Activity you can store the value inside SharedPreferences like:
PreferenceManager.getDefaultSharedPreferences(SecondActivity.this)
.edit().putString(key, selectedItemInfoHere).apply();
Then override inside your first Activity and in your third Fragment method onResume() and inside just make checking:
#Override
public void onResume() {
super.onResume();
String value = PreferenceManager.getDefaultSharedPreferences(getContext())
.getString(key, "");
if (value != null && !value.isEmpty()) {
//You have selected item value update TextView
}
}
Note that once you don't need this value you will need to remove it, because it will update your TextView every time when onResume is called. To remove value just call:
PreferenceManager.getDefaultSharedPreferences(getContext()).edit().remove(key);
If I understood you correctly, you have flow 3rd fragment --> activity which should update fragment which launched it. In this case, as for me, the most clean solution is from your opened activity call startActivityForResult method to call activity-host of your fragments and handle all what you need in overridden onActivityResult method. Than just call your fragment's updateTextView() or something like that.
On the other hand you can use this library to send messages between components, but you should be careful with usage and think about corner cases related to components lifecycle.
So, choose solution according your needs:)