Is there any way to make Linearlayout having children not clickable android? - android

I have a linearyLayout having several linearlayout and some views.
I want to make the whole layout not clickable.
this is the the first part of the linearlayout
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="#drawable/selector_timetable_row"
android:orientation="vertical">
I first did inflating
View view = layoutInflater.inflate(~~, above layout);
And I did
view.setClickable(false);
but it is still clickable
listener to the layout still fires when i touch the layout.

You can disable touch event propagation with custom view like below:
public class CustomLinearLayout extends LinearLayout {
public CustomLinearLayout(Context context) {
super(context);
}
public CustomLinearLayout(Context context, AttributeSet attrs) {
super(context, attrs);
}
public CustomLinearLayout(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
}
#Override
public boolean dispatchTouchEvent(MotionEvent ev) {
return false;
}
}
Use like this:
<{Here is package name}.CustomLinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="#drawable/selector_timetable_row"
android:orientation="vertical">

Related

cannot dynamically add views android

I'm trying to implement a custom view with textview children added dynamically. But it isn't showing any result. there are no error, just nothing shows up:
My Class:
public class CustomPasscodeEntryView extends LinearLayout {
private Context mContext;
private CustomPasscodeEntryView thisView;
public CustomPasscodeEntryView(Context context) {
super(context);
/* same as below */
}
public CustomPasscodeEntryView(Context context, #Nullable AttributeSet attrs) {
super(context, attrs);
/*same as below*/
}
public CustomPasscodeEntryView(Context context, #Nullable AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
mContext = context;
LayoutInflater inflater = (LayoutInflater) mContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
thisView = (CustomPasscodeEntryView) inflater.inflate(R.layout.view_passcode_entry,this);
}
public void addDigit(int digit){
LayoutInflater inflater = (LayoutInflater) mContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
final pinView pin = (pinView) inflater.inflate(R.layout.password_bullet_view,null);
pin.setDigit(digit);
thisView.addView(pin, thisView.getChildCount());
pin.setVisibility(VISIBLE);
}
public void deleteDigit(){
if(getChildCount() > 0)
thisView.removeView(thisView.getChildAt(getChildCount()-1));
}
}
class pinView extends TextView {
int digit;
public pinView(Context context) {
super(context);
}
public pinView(Context context, AttributeSet attrs) {
super(context, attrs);
}
public pinView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
setText('•');
}
public void setDigit(int digit) {
this.digit = digit;
this.setText(Integer.toString(digit));
}
}
and my XMLs:
view_passcode_entry:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_gravity="center"
android:animateLayoutChanges="true">
</LinearLayout>
password_bullet_view:
<com.github.lockpin.lollipin.lib.views.pinView
xmlns:android="http://schemas.android.com/apk/res/android"
android:textColor="#android:color/white"
android:text="•"
android:textSize="20sp"
android:gravity="center"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="2.5dp"
/>
EDIT: the view in my activity:
<com.github.lockpin.lollipin.lib.views.CustomPasscodeEntryView
android:id="#+id/custom_passcode_entry_view"
android:layout_width="300dp"
android:layout_below="#id/pin_code_text_view"
android:layout_centerHorizontal="true"
android:layout_height="40dp"/>
I cant see what's wrong, and I've followed tutorials online and made a few changes. Am I missing something here? Or is this plainly wrong?
You use wrong view id view_passcode_entry when inflating view, which is instance of LinearLayout, and typecast it to CustomPasscodeEntryView.
You only need to use this when call addView() in addDigit() because CustomPasscodeEntryView is also instance of LinearLayout. So layout view_passcode_entry can be removed because it is not needed anymore.
this.addView(pin, this.getChildCount());
But if you want to add view view_passcode_entry as child of CustomPasscodeEntryView instance then you need to add thisView also
private ViewGroup thisView;
...
thisView = (ViewGroup) inflater.inflate(R.layout.view_passcode_entry, this);
this.addView(thisView, 0);
and then if you want to use view_passcode_entry as parent of pinView then you can use
thisView.addView(pin, thisView.getChildCount());
Is it because of you have already mentioned the height of CustomPasscodeEntryView in the xml (android:layout_height="40dp")?
Can you try wrap_content instead?

What is correct way to make custom view based on EditText?

What is correct way to extend EditText?
The problem is following:
I have empty application from template with two EditText:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<EditText
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="one"/>
<EditText
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="two"/>
</LinearLayout>
It works fine:
Then I create my custom view from EditText:
public class CuteEditText extends EditText {
public CuteEditText(Context context) {
this(context, null);
}
public CuteEditText(Context context, AttributeSet attrs) {
this(context, attrs, 0);
}
public CuteEditText(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
// some special initialization will be here
}
}
And when I change EditText to my CuteEditText, interface works incorrectly:
The problem is not only with view ot UI. If I type something in first EditText and than touch the second one, nohing happens: input will continue in first.
The same behaviour if I inherite CuteEditText from AppCompatEditText.
What is wrong?
Sources for experiment are available at https://github.com/tseglevskiy/EditTextExperiment
Your construtors are broken. This is how it should look:
public class CuteEditText extends EditText {
public CuteEditText(Context context) {
super(context);
}
public CuteEditText(Context context, AttributeSet attrs) {
super(context, attrs);
}
public CuteEditText(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
}
}
You don't need the third constructor overload. The first one is for creating the view programmatically and the second one is for creating the view from xml. Those two should be enough for most cases.
public class CuteEditText extends EditText {
public CuteEditText(Context context) {
this(context, null);
}
public CuteEditText(Context context, AttributeSet attrs) {
super(context, attrs);
}
}

Show/Hide LinearLayout when scrolling a RecyclerView?

I have a fragment loaded into my MainActivity. On top of the fragment's layout I have a LinearLayout which I would like to show/hide as the user scrolls up/down.
Can this be achieved using the Coordinator layout or I need to do my own hack?
layout.xml:
<android.support.design.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#ececec">
<android.support.v7.widget.RecyclerView
android:id="#+id/discoverRView"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingLeft="5dp"
android:paddingRight="5dp">
</android.support.v7.widget.RecyclerView>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="100dp"
android:background="#f00"
app:layout_anchor="#+id/discoverRView"
app:layout_anchorGravity="top"
app:layout_scrollFlags="scroll"
>
</LinearLayout>
</android.support.design.widget.CoordinatorLayout>
Maybe there are better solutions, but this can be achieved by creating a custom CoordinatorLayout.Behavior and adding it to a CustomLinearLayout:
//This is taken from a project of mine, it scrolls a Layout up if a snackbar shows up.
public class MoveUpwardBehavior extends CoordinatorLayout.Behavior<View> {
public MoveUpwardBehavior(){
//super();
}
public MoveUpwardBehavior(Context context, AttributeSet attrs) {
super(context, attrs);
}
#Override
public boolean onDependentViewChanged(CoordinatorLayout parent, View child, View dependency) {
float translationY = Math.min(0, dependency.getTranslationY() - dependency.getHeight());
child.setTranslationY(translationY);
return true;
}
#Override
public boolean layoutDependsOn(CoordinatorLayout parent, View child, View dependency) {
return dependency instanceof Snackbar.SnackbarLayout;
}
#Override
public void onDependentViewRemoved(CoordinatorLayout parent, View child, View dependency) {
super.onDependentViewRemoved(parent, child, dependency);
child.setTranslationY(0);
}
}
You'll need a custom LinearLayout, but this part is easy peasy:
#CoordinatorLayout.DefaultBehavior(MoveUpwardBehavior.class)
public class CustomLinearLayout extends LinearLayout {
public CustomLinearLayout(Context context) {
super(context);
}
public CustomLinearLayout(Context context, AttributeSet attrs) {
super(context, attrs);
}
public CustomLinearLayout(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
}
public CustomLinearLayout(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
super(context, attrs, defStyleAttr, defStyleRes);
}
}
Surely, you'll need to use this layout in your xml:
<com.your.project.CustomLinearLayout
android:layout_width="match_parent"
android:layout_height="100dp"
android:background="#f00"
app:layout_anchor="#+id/discoverRView"
app:layout_anchorGravity="top">
</com.your.project.CustomLinearLayout>
So, I think you get the idea. You'll need to update the behaviour to depend on the scroll of your RecyclerView. If you need more help, I can try to build a working example.

Scroll layout in webview android

I am using web view in my application. web layout contains long layout so when i select on last edit text web view gets scroll but last edit text is not displaying focused because of it is hide from input soft keyboard . i want to show last edit text in visible view of web layout. any suggestion?
Xml
<com.salesgyani.android.pos.activities.ScrollWebView
xmlns:android="schemas.android.com/apk/res/android";
android:id="#+id/m_webview"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:focusable="true" />
and JAVA
public class ScrollWebView extends WebView {
public ScrollWebView(Context context) {
super(context);
}
public ScrollWebView(Context context, AttributeSet attrs) {
super(context, attrs);
}
public ScrollWebView(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
}
#Override
public boolean onTouchEvent(MotionEvent event){
requestDisallowInterceptTouchEvent(true);
return super.onTouchEvent(event);
}
}

Custom view not inflating layout when added programmatically

I'm trying to add a custom view to a linear layout programmatically. I want the custom view to inflate a layout I've already created. When I create an instance of the custom view and add it, a spot shows up where the view is, but the layout didn't seem to be inflated (set the background color of my custom layout to green, but I don't see green in the space, nor the image in the layout).
My custom view:
public class AddressView extends View {
public AddressView(Context context) {
super(context);
View.inflate(context, R.layout.place_address, null);
}
public AddressView(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
View.inflate(context, R.layout.place_address, null);
}
public AddressView(Context context, AttributeSet attrs) {
super(context, attrs);
View.inflate(context, R.layout.place_address, null);
}
}
My custom view layout:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/address_view"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="#00ff00" >
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="#drawable/house_1" />
</RelativeLayout>
My instantiation in an activity:
LinearLayout content = (LinearLayout) findViewById(R.id.content);
AddressView addressView = new AddressView(this);
LayoutParams lp = new LayoutParams(LayoutParams.MATCH_PARENT, 400);
content.addView(addressView, 0, lp);
My R.id.content (The linear layout is the only child of a scrollview):
<LinearLayout
android:id="#+id/content"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical" >
<FrameLayout
android:id="#+id/thumbnail_container"
android:layout_width="wrap_content"
android:layout_height="wrap_content" >
<ImageView
android:id="#+id/thumbnail"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:adjustViewBounds="true"
android:scaleType="fitXY"
android:src="#drawable/test_house" />
</FrameLayout>
</LinearLayout>
I eventually worked around this by extending FrameLayout instead of View, and passing this to the inflate call. I think the view was being added and inflating, but it didn't know how to lay out the children correctly, which is resolved if you pass the parent to the inflate call initially:
public class AddressView extends FrameLayout {
public AddressView(Context context) {
super(context);
LayoutInflater.from(context).inflate(R.layout.place_address, this);
}
public AddressView(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
LayoutInflater.from(context).inflate(R.layout.place_address, this);
}
public AddressView(Context context, AttributeSet attrs) {
super(context, attrs);
LayoutInflater.from(context).inflate(R.layout.place_address, this);
}
}

Categories

Resources