I have a little app that I'm working on that displays a list of monsters. You can click on each monster to see more info about that monster.
The list is in my xml layout file in a TableLayout.
But looking at the code, it's easy to see how things can get out of hand the more monsters I add.
I was wondering, if there is a better way of determing which monster was clicked and how to get the needed info passed from the list of monsters view to the monster info view.
Here is my code so far. It works fine, but I know it's not really good because I'd have to add a new case statement for each new monster I add to the list.
public void AddNewView(View view) {
//get selected button view
switch(view.getId())
{
//get textview & imageview monsters from xml
//get monster picture and monster info from xml
case R.id.showMonsterButton1:
iv = (ImageView) findViewById(R.id.monster1_icon);
tv = (TextView) findViewById(R.id.monster1_info);
ShowMonsterInfoView(tv, iv);
break;
case R.id.showMonsterButton2:
iv = (ImageView) findViewById(R.id.monster2_icon);
tv = (TextView) findViewById(R.id.monster2_info);
ShowMonsterInfoView(tv, iv);
break;
case R.id.showMonsterButton3:
iv = (ImageView) findViewById(R.id.monster3_icon);
tv = (TextView) findViewById(R.id.monster3_info);
ShowMonsterInfoView(tv, iv);
break;
case R.id.showMonsterButton4:
iv = (ImageView) findViewById(R.id.monster4_icon);
tv = (TextView) findViewById(R.id.monster4_info);
ShowMonsterInfoView(tv, iv);
break;
}
}
public void ShowMonsterInfoView(TextView tv, ImageView iv) {
Intent intent = new Intent(this, DisplayMonsterInfo.class);
String text_tag = tv.getTag().toString();
String image_tag = iv.getTag().toString();
Bundle extras = new Bundle();
extras.putString("name", text_tag);
extras.putString("avatar", image_tag);
intent.putExtras(extras);
startActivity(intent);
}
Save your list of monsters in a List object and pass it in an ArrayAdapter object which will be used to populate the ListView. In the List object you can dynamically add more monsters on the go using obj.add(monster_name). In the setOnItemSelected method save the the selected monster in a static String object, which can be accessed in any Activity using MonsterListActivity.monster_name. Use it to pull data from file/database.
As per how to get which monster was clicked. In case if you are using RecyclerView and in case if ListView just setOnItemClickListener. By position of clicked item you can get object from list with monsters objects and then get id from there.
Put data about monster in data base and pass id of monster to another activity where you will fetch data from DB.
What you can do is simply save data to DB and assign a unique id to every monster.On the click you pass the id to the next activity and fetch the data about the monster their.
On the other hand if you don't want to save the data, pass the data with the click intent to other activity(i.e if you have the data in the first activity).
As you have to add views, I recommended you use recycler view where you can simply add the items in the list you are providing and call notifyDataSetChanged().Using table layout for this might not be a good idea.
Related
hi i have RecyclerView in that when user click on one row i am making changes in ui and updating view now i want when user click one one icon of that row it opening 2nd activity in that i am passing object of that position . and on 2nd activity if tick it i am not able to update view of that RecyclerView .. any way ? ya by doing static arreylist i can do it but cant do static as there is some problem .. part form static other way
icon.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
Intent n = new Intent(mContext, PlayerInfo.class);
Players mData = (Players) v.getTag();
((Activity) mContext).startActivityForResult(n, 1111);
}
});
As you code shows,you can start second activity by call startActivityForResult and pass your data to it.
when data changed in 2nd activity,you save the new data in one object and when the activity finishes,you pass it to first activity,and you also need to add some code to handle the new object from 2nd activity in onActivityResult,just copy data to your old data for specific position.
I have a list of buttons in one of my activities that are dynamically generated, and I was wondering how i would get one of those buttons to, when clicked, open another activity and display text based on which button in the list was clicked.
I generate the buttons using a for loop (I've ommited details relating to TextViews in the loop for easier reading, it also used some variables defined elsewhere)
for (int i = 0; i < N; i++) {
// create a new Button
final Button rowButton = new Button(this);
// Set properties of rowButton
rowButton.setText("See Recipe");
rowButton.setId(RecipeArray.get(i));
// add the Button to the LinearLayout
myLinearLayout.addView(rowButton);
// save a reference to the Button for later
myButtons[i] = rowButton;
}
The buttons represent a certain recipe and when clicked they should take the user to a new activity "HowToMake" and generate a textview with the information relating to that recipe only. They are stored in an array at the bottom of the code snippet "myButtons[i] = rowButton" But I'm not sure how I would use this.
Thanks for any help.
You'll have to add an onclicklistener to each button as you add it. Then in the onclick event, you can call the startActivity method of your current Activity. When you create your Intent which will open the new activity, you can add "extras" to it (in other words, you can add some extra data which will be passed into the new activity). New data, such as the ID of the recipe that you want to open :)
Example (Untested, but should be along the right lines):
rowButton.setTag("the unique ID by which you can read back your recipe");
rowButton.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
Intent intent = new Intent(YourActivity.this, TheViewRecipeClass.class);
intent.putExtra("id", v.getTag());
startActivity(intent);
}
}
I have been able to create a ListActivity that displays a header and a footer, and sandwiched between these a custom layout that contains on each row three checkboxes and a Contact name (reading from the Contacts database). I use a SimpleCursorAdapter to display this info. My problem has been getting the OnListItemClicked()* to fire. I click in the ListView (on the checkboxes AND on the name of the Contact) and my breakpoint is never reached. So: What must I do to get that to fire. I AM setting it, like so:
lv.SetOnListItemClicked(etc);
I think it is; I'm not at my dev machine right now
But even if I am able to get the click event to fire, how will I be able to identify the associated checkboxes? They are named ckbx1, ckbx2, and ckbx3 (or so) in the layout file, but there will be (Contacts.Count) of them, so how can I positively identify which ones have been clicked?
My other option is to dynamically create the widgets in the Activity's OnCreate().
My pseudocode for this is the following, and I'm open to suggestions/feedback on whether this makes or is [not] the best way to go about it:
OnCreate() {
Cursor c = getContacts();
for (i = 0, i == c.Count, i++) {
int id = getContactID(i);
CheckBox ckbx1 = new CheckBox();
ckbx1.Tag = id;
ckbx1.OnClick = Checkbox1Click();
CheckBox ckbx2 = new CheckBox();
ckbx2.Tag = id;
ckbx2.OnClick = Checkbox2Click();
CheckBox ckbx3 = new CheckBox();
ckbx3.Tag = id;
ckbx3.OnClick = Checkbox3Click();
TextView tv = new TextView();
tv.Text = getContactName(i);
}
Checkbox1Click() {
int ContactID = (CheckBox)object.Tag;
switch (ContactID)
case 1:
WriteToDB(1, Option1);
case 2:
WriteToDB(2, Option1);
...
}
This (especially the CheckboxClick event handler) is obviously very rough, but I think you can get the drift of where I'm going with this - saving the "checked" state of the Checkboxes to a SQLite DB so that I know Contact1 wants email (or twitter feed, or whatever the other two checkboxes indicate).
So is my previous method salvageable, or should I go down this new path (or veer off a little from that?)
Usually i uses View.setTag to identify a view instance. For example,
checkBox.setTag("listItem1");
I am writing an Android application with a main page being a list of categories, and then beside each category there is an edit button.
When edit button is clicked, an entry form with the "category" properties filled up is supposed to be shown.
How to pass the category ID or name to the new created form so that it could load from database the properties of selected category
I have no issue with getting the selected category name, by using the code below:
public String getSelectedItem(View view) {
LinearLayout vwParentRow = (LinearLayout) view.getParent();
TextView child = (TextView) vwParentRow.getChildAt(0);
return (String) child.getText();
}
//edit button clicked
public void editCategoryHandler(View view) {
Intent i = new Intent(this, EntryCategory.class);
startActivity(i);
}
I am sure you have just passed String array or ArrayList to display inside that Category List, instead you should prepare an ArrayList of Category objects, and then whenever user clicked a particular item from a category list, get that object at that position after implementing OnItemClickListener, and then pass this received object to the desired activity.
In short, get object for a clicked item and then pass this object.
To pass the value to a new activity, you have to use putExtra() and getExtra().
Please refer the following page
How to use putExtra() and getExtra() for string data
I am working on an Android application that displays a list of items when a tab is selected, then displays detail information about an item that was selected from the list :
Activity1
Tab1 -(intent)-> Activity 2: item1
item2 -(intent)-> Activity 3: ImageView1
item3 TextView1
... ImageButton1
...
The details are to be displayed using ImageViews, ImageButtons, and TextViews. The data comes from a database query, so the TextView text and ImageView drawables have to be assigned dynamically.
The correct text from the database query gets assigned to each of the Views. I can see everything being added when I step through the code in the onCreate method of Activity3 in the debugger.
BUT, the drawables are only displayed when I select the first item in the ListActivity. If I select another item, all TextViews display the correct information but the drawables are not displayed for the ImageViews or ImageButtons. It looks like only the backgrounds are being displayed.
The ImageButton drawables are not being dynamically assigned, only the ImageView drawables are. The ImageButton drawables are set in the TableLayout XML that is associated with the activity. Here is one entry :
<TableRow android:id="#+id/row11" >
<ImageButton android:id="#+id/phonebutton"
android:maxHeight="50px"
android:maxWidth="50px"
android:background="#drawable/ic_phone"
android:adjustViewBounds="true"
style="?android:attr/buttonStyleSmall"
android:src="#drawable/phoneselector" >
</ImageButton >
<TextView android:id="#+id/phonenumber"/>
(note - Originally, I had android_drawable="#drawable/ic_phone", then tried adding android:background="#drawable/ic_phone", and finally created the following selector (phoneselector.xml) :
- end note)
If I select the first item again, its proper ImageView drawables are displayed along with the proper text in the TextViews. The ImageView drawables that belong to the other items have no problems being displayed in Activity2's ListView.
The code successfully sets an onClickListener for the button (also in Activity3.onCreate). If I click on what is displayed on the spot where the drawable should be, the phone number is dialed.
The code successfully sets an onClickListener for the button (also in DetailActivity.onCreate).
Has anyone seen anything like this before? I would appreciate any help figuring out what is wrong.
Here are more details because I wonder if the problem has to do with the use of the Views :
The Activity1 extends TabActivity and sets a TabHost view that contains a FrameLayout along with the TabWidget. Activity1 creates the tabs dynamically.
Activity2 extends ListActivity and sets the content to its ListView (via setContentView(getListView()).
When ListActivity.onListItemClick is invoked (item in list is selected), a new Intent is created that contains an identifier in a Bundle and Activity3 is started.
The started activity (in Activity3.onCreate...) sets the content to a TableLayout view defined in a .xml file (via setContentView(R.layout.details.xml).
Here is the code from Activity3.onCreate :
Cursor c = null;
DatabaseHelper myDbHelper = null;
ImageButton button = null;
TextView phoneText = null;
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
Resources res = getResources();
setContentView(R.layout.details);
Bundle bundle = this.getIntent().getExtras();
Integer id = (Integer) bundle.getInt("id");
myDbHelper = new DatabaseHelper(this);
c = myDbHelper.getWinery(id);
if (c != null) {
c.moveToFirst();
ImageView image1 = (ImageView) this.findViewById(R.id.iconimage);
String wholeString = c.getString(c.getColumnIndex("PhotoIcon"));
if (wholeString != null) { String[] splitString = wholeString.split(".jpg");
String sString = splitString[0];
int path = res.getIdentifier(sString, "drawable", "com.winerytour" );
Drawable drawImage1 = this.getResources().getDrawable(path);
drawImage1.setVisible(true, true); //added to try to fix problem
try {
image1.setImageDrawable(drawImage1);
image1.refreshDrawableState(););
} catch (RuntimeException e) {
e.getMessage();
}
image1.setAdjustViewBounds(true); }
.. set other TextView text in same way ...
phoneText = (TextView) this.findViewById(R.id.phonenumber);
String phone = c.getString(c.getColumnIndex("Telephone"));
phoneText.setText(phone);
button = (ImageButton) this.findViewById(R.id.phonebutton);
button.setOnClickListener(new ImageButton.OnClickListener() {
public void onClick(View v) {
performDial(); } });
((ImageButton) button).refreshDrawableState(); // attempt to fix problem
} // end c != null
}
content to its ListView (via setContentView(getListView()). Don't do that. If you extend listactivity, the view is built it. If you don't want that, don't 'extend listview