So, my friend got me to mess with android programming in android studio today. I started making a beginner application and have had some good results. But right now I am trying to get a button to change the value of a textview.
Here is the code for the button and the textview
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Add one"
android:id="#+id/button3"
android:layout_alignBottom="#+id/button2"
android:layout_alignRight="#+id/textView"
android:layout_toRightOf="#+id/button"
android:onClick="addone"/>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text=""
android:id="#+id/counter"
android:textSize="40dp"
android:layout_alignTop="#+id/button3"
android:layout_centerHorizontal="true"/>
and here is the code that is attempting to change the value of the text view.
public void addone(){
numtest+=1;
TextView t = (TextView) findViewById(R.id.counter);
t.setText(numtest);
}
THe program compiles and opens, but it crashes whenever i press the button. I believe I have narrowed down the culprit to this line, but im not sure why it isnt working
TextView t = (TextView) findViewById(R.id.counter);
Any ideas?
An overloaded method is your problem. It is subtle, a mistake even a seasoned programmer could make. I've made it myself before.
You are calling TextView.setText(Integer). This attempts to load a string having a resource id of numtest, which does not exist.
Try this instead:
public void addone(View v){
numtest+=1;
TextView t = (TextView) findViewById(R.id.counter);
t.setText(numtest+"");
}
This will call TextView.setText(CharSequence) instead, which is what you're really trying to do.
Also, as Osmium USA demonstrated, your method signature is incorrect. The button pressed callback method must accept a view, and must be public.
When you give a layout element a function to execute, it looks for that name accepting a View (so you know what was clicked if you assign multiple elements the same click behavior in the XML).
So addone() must be addone(View v)
From the Button Docs
In order for this to work, the method must be public and accept a View as its only parameter
William Morrison also has a good point. You should make that number a String either by what he did or use the Integer Class:
t.setText(Integer(numtest).toString());
or
t.setText(numtest+"");
this should work:
public void addone(View view){
switch(view.getId())
{
case R.id.button3:
numtest+=1;
TextView t = (TextView) findViewById(R.id.counter);
t.setText(Integer.toString(numtest));
break;
}
}
Related
I am trying to make a clickable phone number button with an icon in my app. I was checking for some references and found google maps implementation good. How can I achieve this in my app?
I have tried the Image Button view but that does not solve the problem. I have put 'onClick' attribute for text & image views, but the button animation isn't there and both text & image icon does not look together.
Please guide me as to what view/s we have to use to achieve the result as in the image and how to get that animation on click of the button. Or is there any better way to achieve this?
I am aware of intents, so that part is clear.
If you can let me know how to make that phone number copied to the clipboard automatically on hold of that button, that would be really great.
Try this code
Change spacing dimens according to your use and also change icon.
<LinearLayout
android:id="#+id/callButton"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center"
android:orientation="horizontal">
<androidx.appcompat.widget.AppCompatImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerVertical="true"
android:layout_marginLeft="#dimen/spacing_small"
android:padding="#dimen/spacing_small"
android:clickable="false"
app:srcCompat="#drawable/ic_download"
android:tint="#color/black" />
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:fontFamily="#font/amaranth"
android:gravity="center_vertical"
android:paddingLeft="#dimen/spacing_xxhuge"
android:paddingTop="#dimen/spacing_medium"
android:paddingBottom="#dimen/spacing_medium"
android:text="000 0000 000"
android:textColor="#color/grey_70"
android:textSize="#dimen/textsize_large" />
</LinearLayout>
and set on click listener on callButton. use below code in java code.
And also i have added a code to copy phone number directly on click event. You have to save text in clipboard.
LinearLayout callButton = findViewById("callButton");
callButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
ClipboardManager clipboard = (ClipboardManager) getSystemService(Context.CLIPBOARD_SERVICE);
ClipData clip = ClipData.newPlainText(label, text);
// You have to get text from phoneNumber textview. and set it to clipboard.
clipboard.setPrimaryClip(clip);
}
});
Some questions:
Do you have any experience with Android development?
If so, do you have anything up and running?
I'm gonna assume you do have experience but you're asking before you start coding anything. There are many ways to implement this, the way that would be easiest would be to have a custom listview (here's a simple and easy tutorial for that) and use an item in the listview to display a phone number. Each listview item has a setOnItemLongClickListener which you can use and inside it use the ClipboardManager to copy or use an intent to the phone calling service.
list.setOnItemLongClickListener(new OnItemLongClickListener() { //list is my listView
#Override
public boolean onItemLongClick(AdapterView<?> arg0, View arg1,
final int pos, long id) {
//Whatever you wanna do
ClipboardManager clipboard = (ClipboardManager)
getSystemService(Context.CLIPBOARD_SERVICE);
ClipData clip = ClipData.newPlainText(label, text);
clipboard.setPrimaryClip(clip);
}
});
I believe this is what you want to achieve
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent">
<!--Your other layouts-->
<TextView
android:background="?selectableItemBackground"
android:focusable="true"
android:clickable="true"
android:padding="#dimen/activity_vertical_margin"
android:drawableStart="#drawable/ic_phone"
android:drawablePadding="16dp"
android:text="The mobile number here"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
</LinearLayout>
android:background="?selectableItemBackground"
This will add the default system animation of ripple(or anything) on click.
Also android:focusable=" and android:clickable="true" is necessary for this to work.
If you want to customize the click events, you better be using selectors in the background of your view.
For the 'Copy to Clipboard' feature you can refer to the other answers.
Happy Coding!
I'm trying to create a bottomsheet that's either completely expanded or completely out of view - I don't want it to be anywhere in the middle or peeking.
Here's the xml:
<LinearLayout
android:id="#+id/bottom_sheet"
android:layout_width="250dp"
android:layout_height="250dp"
android:layout_gravity="center_horizontal"
android:background="#android:color/holo_blue_bright"
android:clipToPadding="true"
android:orientation="vertical"
android:elevation="10dp"
app:behavior_peekHeight="0dp"
app:behavior_hideable="true"
app:behavior_skipCollapsed="true"
app:layout_behavior="android.support.design.widget.BottomSheetBehavior">
<TextView
android:id="#+id/delete_btn"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:background="#color/cinza3"
android:text="clear/delete Q"/>
</LinearLayout>
In my code I have the following methods:
private void showHideBottomSheet() {
if (mBSBehavior.getState() != BottomSheetBehavior.STATE_EXPANDED) {
showBottomSheet();
} else {
hideBottomSheet();
}
}
private void showBottomSheet() {
mBSBehavior.setState(BottomSheetBehavior.STATE_EXPANDED);
}
private void hideBottomSheet() {
mBSBehavior.setState(BottomSheetBehavior.STATE_HIDDEN);
}
And in my layout there's a button that calls showHideBottomSheet() when clicked.
When I click the button, everything works fine and the bottomsheet is shown/hidden. But if it's EXPANDED and I click on a textview elsewhere in the code (outside the bottomsheet), for example, the bottomsheet moves down a little, but not completely - it's top half is visible, but if I log it's state, it's STATE_EXPANDED.
what's the difference between STATE_HIDDEN and STATE_COLLAPSED? I've searched everywhere for a visual explanation but couldn't find it. Is this 'intermediate' state the collapsed state? Even if I set peekHeight="0" in the xml and skipCollapsed="true"?
what does peekHeight and skipCollapsed in the xml actually do?
how can I make it to be fully visible or fully hidden at all times and avoid this 'intermediate' state?
EDIT: There's a TextView inside the BottomSheet, and and OnClickListener on it. When I click it, the BottomSheet goes to that 'intermediate' state too, even though the OnclickListener does not call setState or anything related to the BottomSheet.
Updated my support:design library to 25.3.1 and it started working as expected.
I would like the hint to display after a default value I put in the EditText.
For example, the contents of the EditText must look like:
192.168.1.1 (Hint: First IP address) - all inside the EditText, and when the user clicks it, it defaults to show only 192.168.1.1.
The EditText takes a string as input. I want the hint to just be there, but not count as the input string.
Please help.
Thanks
Regards
Ok, I got your point. So you want a floating label when an edit text receive a focus. You just have to wrap your edit text inside TextInputLayout.
Here is my updated sample:
<android.support.design.widget.TextInputLayout
android:id="#+id/input_layout_id"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<EditText
android:id="#+id/edit_txt_id"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="#string/str_reource_id"
android:inputType="depends_on_your_use_case"/>
</android.support.design.widget.TextInputLayout>
Define ip_hint and ip you want in resources then in your onCreate:
editText.setText(R.string.ip_hint);
editTxt.setOnFocusChangeListener(new View.OnFocusChangeListener() {
#Override
public void onFocusChange(final View view, final boolean hasFocus) {
if (hasFocus)
editTxt.setHint(R.string.ip);
else if(editText.getText().equals(context.getResource(R.string.ip))
editText.setText(R.string.ip_hint);
}
});
There is no way to achieve this task. Use hint as input string and append with input string.
Late to the show, but you can also add a formatted string in your hint in onCreate,
<EditText
android:id="#+id/foo"
android:hint="#string/hint_foo"
...
where hint_foo is defined in string resource,
<string name="hint_foo">Foo: %1$s</string>
and then initialise with getString() in activity,
TextView hinter = (TextView) findViewById(R.id.foo);
hinter.setHint(getString(R.string.hint_foo, ip_string));
I have several checkboxes in my Activity_Main.XML similar to as follows
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="#string/Video"
android:id="#+id/Video"/>
<CheckBox
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/VideoCheck"
android:onClick="onCheckboxClicked"/>
Now on a different activity I want the state of this checkbox to be displayed, for ease of use I have set up the code so it will change the text or a text label. Code in my MenuActivity.java is as follows
public void onCheckboxClicked(View view) {
boolean checked = ((CheckBox) view).isChecked();
switch (view.getId())
{
case R.id.VideoCheck:
if (checked) {
TextView MyTextLabel = (TextView)findViewById(R.id.Test1);
MyTextLabel.setText("Video");
}
else
{
TextView MyTextLabel = (TextView)findViewById(R.id.Test1);
MyTextLabel.setText("No Video");
}
break;
}
}
Worth saying the text label on the XML display is called MyTextLabel. I think the problem is because the Checkboxes are set up to call "onCheckboxClicked" but that checkbox clicked part is not in the Activity native to that set up.
Essentially the first page(activity_main.xml, MainActivity.Java) of my app has the checkboxes, then a button takes the user to the second page (activity_menu.xml, MenuActivity.java) has the Label set to change depending on the state of the checkboxes on the first page.
I appreciate this is explained horrendously but please ask any question you may have.
You need to send the state of the checkbox in the Intent you use to start the second activity. See Build an Intent for details. Then in the second activity, you need to extract the checkbox state from the received intent. See Receive an Intent.
Note that I am assuming that you already know how to create an Intent to start an Activity. If not, you should read Starting Another Activity.
I've got a ListActivity and ListView and I've bound some data to it. The data shows up fine, and I've also registered a context menu for the view. When I display the list items as just a simple TextView, it works fine:
<TextView xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/nametext"
android:layout_width="wrap_content"
android:layout_height="wrap_content"/>
However when I try something a bit more complex, like show the name and a CheckBox, the menu never shows up:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="horizontal">
<TextView android:id="#+id/nametext"
android:layout_width="wrap_content"
android:layout_height="wrap_content"/>
<CheckBox
android:id="#+id/namecheckbox"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
/>
</LinearLayout>
Can long-presses work on more complex elements? I'm building on 2.1.
(edit)
Registering with this on the ListActivity:
registerForContextMenu(getListView());
The code I posted is the item template for the list.
Your CheckBox may be interfering with matters. Consider using a CheckedTextView instead of a LinearLayout, CheckBox, and TextView combination, since CheckedTextView is what Android expects for a CHOICE_MODE_MULTIPLE list.
Check out $ANDROID_HOME/platforms/$VERSION/data/res/layout/simple_list_item_multiple_choice.xml, where $ANDROID_HOME is wherever you installed the SDK and $VERSION is some Android version (e.g., android-2.1). This resource is the standard resource you should use for CHOICE_MODE_MULTIPLE lists. Feel free to copy it into your project and adjust the styling of the CheckedTextView as needed.
set checkbox property
focusable = false;
and run project again..
Found at this place: http://www.anddev.org/view-layout-resource-problems-f27/custom-list-view-row-item-and-context-menu-t52431.html
Setting the checkbox to not be focusable fixes the problem.
Not sure if it would cause issues when navigating the UI with something else than a touchscreen (with a wheel or arrow keys), but it fixed my problem (my layout was a bit more complicated than just a TextView and a Checkbox...)
Context menu's can only be registered to subclasses of View. I don't know how you registered the LinearLayout with a context menu, did you package it in some type of View? if so, you should post that code.
Anyways why not just register the TextView of each list item? Who would long press a checkbox...
This should from a regular ListView as well. But if you're starting from scratch on a new list I would consider using the CheckedTextView:
checkBox.setOnLongClickListener(new View.OnLongClickListener() {
public boolean onLongClick(View v) {
// return false to let list's context menu show
return false;
}
});