Whats the difference between these two buttons? Android programming - android

Ok ive just started programming some android in Eclipse, and im a little dumbfounded about this. Here are two ways that the button programming has been written in this book, they both work fine, except the first one seems simpler and shorter. Which is better and why?
View newButton = findViewById(R.id.main_new_button);
newButton.setOnClickListener(this);
Button newButton= (Button) this.findViewById(R.id.main_new_button);
newButton.setOnClickListener(this);

The two forms are equivalent. In both cases findViewById returns a View object, the only difference is that in the second version an explicit cast is made to Button, a subclass of View.
As you can see in the documentation, View is the superclass of TextView, and TextView is the superclass of Button.
Which one is better? it depends. If you need to use functionality specific to a Button, then the second way is preferred. On the other hand, if a View object suffices, then use the first way.

I like your way of thinking.In android every widget is view.I will tell you in step--
1)
First important thing is Every Button is View but not necessarily Every View should button
View newButton = findViewById(R.id.main_new_button);
newButton.setOnClickListener(this);
you are using it that does not mean that newButton is always a Button.We can stroe any View reference (for ex. LinearLayout, ImageButton etc) to newButton
But In second case
Button newButton= (Button) this.findViewById(R.id.main_new_button);
newButton.setOnClickListener(this);
newButton is definitely should be Button if R.id.main_new_button is button ID in XML
2)-
As i said we know every Button is View but we do not know which View is button.That's it ask you to cast findViewByid.And your first case discourage as every view has its own method that can not be used if we generalize this view.So we have to use specifically Button.
Hope you got it

If you want a button, you need the latter formation. The formmer formation is ok but it's not the perfect method.Because the view's usage is not only for button.

In the second case, you have cast the result to the correct type. This allows you to access Button-specific methods. The first one returns just a View object although it is a Button. So you will not have access to Button-specific functionality.

A Button is a widget which extends a TextView. A TextView extends a View. If you go for the Button class, you will be exposed to more specific member functions rather than the aforementioned super classes. As far as what those specific methods are... you would have to go into the android.widget.Button class to explore that =). Upon doing this, all I see are three constructors (for explicitly declaring the button) -- all other member functions are identical.
public Button(android.content.Context context);
public Button(android.content.Context context, android.util.AttributeSet attrs);
public Button(android.content.Context context, android.util.AttributeSet attrs, int defStyle);
But if you don't want to confuse yourself down the line when you come back to this code after 3 months, or the other developers working along side with you, the second method is the proper method to use:
Button newButton= (Button) this.findViewById(R.id.main_new_button);
newButton.setOnClickListener(this);

The button which is built by View is a view, not a button widget.If you create a button from a View Class,you could not call the functions of Button Class. View Class and Button Class both have the "setOnClickListener" function,but that function of View Class is not the same as it from Button.

Related

difference between android:onClick and onClickListener [duplicate]

I realize that a similarly-worded question has been asked before, but this is different. I am pretty new at developing android apps and I have three questions regarding the difference(s) between the android:onclick="" XML attribute and the setOnClickListener method.
What are the differences between the two? Is the difference between the two implementations found at compile time or run time or both?
What use cases are favorable to which implementation?
What difference(s) does the use of fragments in Android make in implementation choice?
Difference Between OnClickListener vs OnClick:
OnClickListener is the interface you need to implement and can be set
to a view in java code.
OnClickListener is what waits for someone
to actually click, onclick determines what happens when someone
clicks.
Lately android added a xml attribute to views called android:onclick,
that can be used to handle clicks directly in the view's activity
without need to implement any interface.
You could easily swap one listener implementation with another if you need to.
An OnClickListener enable you to separate the action/behavior of the click event from the View that triggers the event. While for simple cases this is not such a big deal, for complex event handling, this could mean better readability and maintainability of the code
Since OnClickListener is an interface, the class that implements it has flexibilities in determining the instance variables and methods that it needs in order to handle the event. Again, this is not a big deal in simple cases, but for complex cases, we don't want to necessary mix up the variables/methods that related to event handling with the code of the View that triggers the event.
The onClick with function binding in XML Layout is a binding between onClick and the function that it will call. The function have to have one argument (the View) in order for onClick to function.
Both function the same way, just that one gets set through java code and the other through xml code.
setOnClickListener Code Implementation:
Button btn = (Button) findViewById(R.id.mybutton);
btn.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
myFancyMethod(v);
}
});
// some more code
public void myFancyMethod(View v) {
// does something very interesting
}
XML Implementation:
<?xml version="1.0" encoding="utf-8"?>
<!-- layout elements -->
<Button android:id="#+id/mybutton"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Click me!"
android:onClick="myFancyMethod" />
<!-- even more layout elements -->
Performance:
Both are the same in performance. Xml is pre-parsed into binary code while compiling. so there is no over-head in Xml.
Limitation:
android:onClick is for API level 4 onwards, so if you're targeting < 1.6, then you can't use it.
I'm shocked nobody talked about this but be careful, although android:onClick XML seems to be a convenient way to handle click, the setOnClickListener implementation do something additional than adding the onClickListener. Indeed, it put the view property clickable to true.
While it's might not be a problem on most Android implementations, according to the phone constructor, button is always default to clickable = true but other constructors on some phone model might have a default clickable = false on non Button views.
So setting the XML is not enough, you have to think all the time to add android:clickable="true" on non button, and if you have a device where the default is clickable = true and you forget even once to put this XML attribute, you won't notice the problem at runtime but will get the feedback on the market when it will be in the hands of your customers !
In addition, we can never be sure about how proguard will obfuscate and rename XML attributes and class method, so not 100% safe that they will never have a bug one day.
So if you never want to have trouble and never think about it, it's better to use setOnClickListener or libraries like ButterKnife with annotation #OnClick(R.id.button)
Simply:
If you have android:onClick = "someMethod" in xml, it looks for the public void someMethod in your Activity class. OnClickListener is called right from your Activity and it is linked to some particular View. For example someButton.setOnClickListener and in the code below is said what has to be done when someButton is pressed.
Hope it helps :)
As said before: they both are a way to add logic in response to an event, in this case a 'click' event.
I would go for a separation between logic and presentation, just like we do in the HTML/JavaScript world: Leave the XML for presentation and add event listeners by means of code.
There are a couple of reasons why you might want to programmatically set an OnClickListener. The first is if you ever want to change the behaviour of your button while your app is running. You can point your button at another method entirely, or just disable the button by setting an OnClickListener that doesn't do anything.
When you define a listener using the onClick attribute, the view looks for a method with that name only in its host activity. Programmatically setting an OnClickListener allows you to control a button's behaviour from somewhere other than its host activity. This will become very relevant when we use Fragments, which are basically mini activities, allowing you to build reusable collections of views with their own lifecycle, which can then be assembled into activities. Fragments always need to use OnClickListeners to control their buttons, since they're not Activities, and won't be searched for listeners defined in onClick.
If you have several buttons using only one method, I suggest doing it in java. But if you have a button with one specific method, onClick in XML would be better.
It's more convenient to always use android:onClick attribute unless you have a good reason not to, for example, if you instantiate the Button at runtime or you need to declare the click behavior in a Fragment subclass.
I think main difference between them is:
OnClick: When you click on the button with your finger.
OnClickListner: It is may be a wider choice that be implemented in various codes.
For example when you type url "ymail.com", yahoo finds your username and your password from your browser and enable click state button to open your mail. This action should be implemented only in onClickListener.
This is my idea!

Duplicate a View Android

I would like to clone a View, graphicaly and functionaly (event). For exemple I have a button on my RelativeView, I get it with findViewById(View) and copy the info inside another button, and finaly put it (the clone) on the relativeView. Like that I could have two buttons and when I click on the copy it triggers the same event. I already did clone = findViewById(View) but the app crash. I don't know if it's possible. I would like to know also if it could be possible to make a generic class. Because the view could be a button but also a Text or An Image. I want to know it's possible to avoid to make three differents methods. But if I have to copy info by info, i will need to make three methods.I'm a begginer in Android ;).
Thanks for you answers.
you are smart Sir, unfortunately that is the way to go though, quick tip when you are implementing Button extends TextView so can always call text functions on a Button like View.setText(""), so forget about it being Button or TextView and go for a boolean attack on ImageView or TextView
hope i am smart too
I would recommend to implement custom views which have the desired properties.
Then you can do this:
LinearLayout myLayout = root.findViewByID(R.id.main);
CustomView myView = new CustomView(this);
myLayout.addView(myView);

Loading XML layout

I have a problem loading previously created layout. I would like to load it and change text on buttons inside, then show it to the user. It will be quiz question and I have to show it many times during one activity. I don't want to create new class for my layout.
What do I have to use? I read something about Inflate class, but I think it is used only to create new classes. I tried setContentView() method, but app stops when method doing this load starts:
LinearLayout layout = (LinearLayout) findViewById(R.id.CapitalQuestionLayout);
setContentView((View) layout);
Can someone give some hints?
Try using the layout field not the id field, when you call from the R class, like so :
LinearLayout layout = (LinearLayout) findViewById(R.layout.CapitalQuestionLayout);
setContentView((View) layout);
For creating a "Quiz" app your basic requirement is:
a layout which has a TextView for Question and 4 Buttons for options.
a set of questions; pretty obvious :-).
You can create a Custom Class - Questions that will hold Text for a question and its associated options (as Strings).
Now, whenever you want to display a new question with different text for buttons just do the following:
If user clicks on right answer then display a Right-Answer-Activity to the user (that has a next-question-Button).
When user clicks on next-question-button you can display Question-Activity and populate the layout-views with a randomly picked question-object's attributes (i.e. Question's text and options' text).
Hope this helps.
This is quite common in Android apps. Do your fields/buttons have an id? For the parent activity, you mostly do
Button someButton = (Button) findViewById(R.id.the_id_to_the_button_you_want_to_change);
This allows you to do things like
someButton.setText("What is the ultimate answer to life, the universe, and everything?");
Look up the Andorid documentation if you want to do other things like set the color. If you have a viewgroup of some sort (RelativeLayout / LinearLayout / etc), you can specify that specific one
Button someButton = (Button)viewGroup.findViewById(R.id.awesomely_named_button_identifier);
The above someOtherButton is used more often with inflated viewGroups

findViewByTag within a dialog

I've got a custom dialog layout that has two EditText fields and I've initially set the visibility to GONE for both (in the layout XML). In the dialog onCreate I want to do a findViewByTag to locate one of the two EditText fields so I can switch visibility to VISIBLE. Everything works find in the dialog if I switch visibility in the XML but I don't know how to get a reference to the dialog's main View from within the dialog so I can call findViewByTag.
I am inflating the layout in the dialog class's onCreate because that's how the example I found did it. I'm willing to change that if necessary to get the reference in the caller and set visibility before showing the dialog if that's the best way to do it.
Still pretty new to Android so any tips on how best to handle custom dialogs is appreciated.
I'm going to assume this example from outside of a view class.
Dialog amazingDialog = new Dialog(context);
amazingDialog.setContentView(R.layout.amazingdialogcontentview)
MyAmazingView view = (MyAmazingView)amazingDialog.findViewById(R.id.amazingview);
TextView tv = (TextView)amazingDialog.findViewById(R.id.textview);
I'm not sure precisely what your use case is, so there may be a better way to do this if you have access to some member variables you could initialize in onCreate, but if you don't:
You could try
View parent = myDialog.findViewById(R.id.parentId)
to get a known parent view of those EditTexts, and then call
parent.findViewWithTag(myTag)
to find your EditText.
Looking at the way you've phrased your question, and the fact you said you're new at Android, are you familiar with the difference between IDs and Tags?
An ID is a resource number assigned to an item (e.g., a View) by Android when you tell it to give something a name. You'd declare, in your XML:
<TextView android:id="#+id/myTextView"/> <!--with other parameters as necessary-->
And then you'd use
TextView tv = (TextView)findViewById(R.id.myTextView);
to find that TextView.
A Tag is an object that you can attach to a View (which I am pretty sure you can't do by XML), either for finding it later or for persisting some interesting information about it to use whenever you might next look it up (like a data object associated with its contents). So, you might say:
tv.setTag(myInterestingData);
so that you could later look up myInterestingData just by having a reference to tv.
After much reading and trial and error, I've concluded that the only way to do this is to use multiple EditText in the XML, all with visibility="gone". Then, in the Java code, have an if or switch to lookup and show the control either by tag or by ID. I was just trying to force too much abstraction into the Dialog class. With the multiple EditText I can use the class for multiple dialogs instead of having one class for each dialog.

Dynamically add or remove views

For my project I need a functionality to dynamically add and remove views(textedit or buttons, etc).
I saw this similar functionality in Android "Add Contact" screen, where plus button add new fields and minus button delete the fields.
I found that EditContactActitivity.java is the file behind "Add Contacts".
I tried to find the methods that are called when plus or minus buttons are pressed but unable to find it, seems like "Add Contact" code is spreaded over multiple files. I am having difficulty understanding Android source code because documentation is unavailable.
Any advice?
You can add and remove views by calling .add() or .remove() on the reference to your main layout and passing the view you wish to add or remove;
Here is a simple example of an onCreate method that demonstrates adding and removing a button:
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
LinearLayout myMainLayout = (LinearLayout)findViewById(R.id.yourMainLayout);
Button b = new Button(this);
//you can have some b.setXXX calls here to set text, view, click listeners etc...
myMainLayout.add(b);
//to remove
myMainLayout.remove(b);
}
I would consider researching Visibility of views rather than going through all this trouble. For example. I have an app where I have a 'record' entry screen that is relatively simple that appears as a Dialogs content. A few views/viewgroups are currently using visibility of gone, to not appear at all. If the user edits the record to add more detail, I launch an Activity that uses the same xml layout, but instantiates some of the currently 'gone' views and changes their visibility to 'visible'.
It is programmatically easy to toggle a view's visibility so I think it is really the way to go.
The only limitation I'm aware of here, would be the views order or position.

Categories

Resources