Extended view not working properly - android

I have extended a RelativeLayout with all its constructor.And I have created a layout in xml that I am inflating in one of constructor of my class.
My Code for MyClass
public class MyClass extends RelativeLayout
{
LayoutInflater inflater = null;
EditText edit_text;
Button btn_clear;
public MyClass(Context context, AttributeSet attrs, int defStyle)
{
super(context, attrs, defStyle);
// TODO Auto-generated constructor stub
}
public MyClass(Context context, AttributeSet attrs)
{
super(context, attrs);
// TODO Auto-generated constructor stub
inflater = (LayoutInflater) getContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE);
inflater.inflate(R.layout.my_class_layout, this, true);
edit_text = (EditText) findViewById(R.id.clearable_edit);
btn_clear = (Button) findViewById(R.id.clearable_button_clear);
btn_clear.setVisibility(RelativeLayout.INVISIBLE);
}
public MyClass(Context context)
{
super(context);
// TODO Auto-generated constructor stub
}
}
My class layout which I inflate
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:orientation="horizontal" >
<EditText
android:id="#+id/clearable_edit"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
/>
<Button
android:id="#+id/clearable_button_clear"
android:layout_width="30dip"
android:layout_height="30dip"
android:layout_alignParentRight="true"
android:background="#drawable/image_clear"
android:layout_centerVertical="true"
android:layout_marginRight="5dip"/>
</RelativeLayout>
And I use MyClass in my activity's layout like this
<com.and.MyClass
android:id="#+id/my_class"
android:layout_width="fill_parent"
android:layout_height="wrap_content" />
This works fine.
but when I inflate my class layout in constructor MyClass(Context context) then it doesn't work.
I am not getting what is the problem. I hope you got my question.

This is OK.
When we use a View in xml
public MyClass(Context context, AttributeSet attrs)
this constructor will be called.
Because all the attributes from XML are passed to this constructor using AttributeSet, so that these values will have effect on View's layout and other fields.
However if you want to use your View in Java also, you should also inflate in all View's constructor (Which is recommended approach).

Please change your code like this
public class MyClass extends RelativeLayout
{
LayoutInflater inflater = null;
EditText edit_text;
Button btn_clear;
public MyClass(Context context, AttributeSet attrs, int defStyle)
{
super(context, attrs, defStyle);
// TODO Auto-generated constructor stub
init();
}
public MyClass(Context context, AttributeSet attrs)
{
super(context, attrs);
// TODO Auto-generated constructor stub
init();
}
public MyClass(Context context)
{
super(context);
// TODO Auto-generated constructor stub
init();
}
public void init() {
inflater = (LayoutInflater) getContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE);
inflater.inflate(R.layout.my_class_layout, this, true);
edit_text = (EditText) findViewById(R.id.clearable_edit);
btn_clear = (Button) findViewById(R.id.clearable_button_clear);
btn_clear.setVisibility(RelativeLayout.INVISIBLE);
}
}

Related

How to add dynamic image view with cross button on top right side

I want to give attachment functionality in app . please see the attach screenshot.
How to create pro grammatically in Android ?
As I can see the solution of your problem. At first create the XML layout of your view. Then create class which will inflating in to it with GET methods. And then create this Views via code and add to container.
layout_custom.xml:
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout android:id="#+id/root"
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="200dp"
android:layout_height="150dp">
<ImageView
android:id="#+id/img_photo"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_margin="12dp"
android:background="#000"/>
<ImageButton
android:id="#+id/btn_close"
android:layout_width="35dp"
android:layout_height="35dp"
android:layout_gravity="end"
android:background="#00000000"
android:scaleType="fitXY"
android:src="#drawable/temp_close"/>
</FrameLayout>
CustomView.class:
public class CustomView extends FrameLayout {
private View mRoot;
private ImageView mImgPhoto;
private View mBtnClose;
private Context mContext;
public CustomView(final Context context) {
this(context, null);
}
public CustomView(final Context context, final AttributeSet attrs) {
this(context, attrs, 0);
}
public CustomView(final Context context, final AttributeSet attrs, final int defStyleAttr) {
super(context, attrs, defStyleAttr);
init(context);
}
private void init(final Context context) {
if (isInEditMode())
return;
final LayoutInflater inflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
View customView = null;
if (inflater != null)
customView = inflater.inflate(R.layout.layout_custom, this);
if (customView == null)
return;
mRoot = customView.findViewById(R.id.root);
mImgPhoto = (ImageView) customView.findViewById(R.id.img_photo);
mBtnClose = customView.findViewById(R.id.btn_close);
}
public View getRoot() {
return mRoot;
}
public ImageView getImgPhoto() {
return mImgPhoto;
}
public View getBtnClose() {
return mBtnClose;
}
}
And finnaly usage of this staff:
final CustomView customView1 = new CustomView(getBaseContext());
final CustomView customView2 = new CustomView(getBaseContext());
final LinearLayout container = (LinearLayout) findViewById(R.id.container);
container.addView(customView1);
container.addView(customView2);
You should create a frameLayout with 2 imageViews one that contains the actual image and one that contains the cross.
Create your custom_view.xml containing your frame layout
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout
....>
<ImageView/>
<ImageView/>
</FrameLayout>
and then create a custom view class like this :
public class MyCustomView extends ViewGroup {
public MyCustomView(Context context, AttributeSet attrs) {
super(context, attrs);
LayoutInflater inflater = LayoutInflater.from(context);
layoutInflater.inflate(R.layout.custom_view, this);
}
}

How to add custom view inside another custom view?

I'm trying to add CustomViewBeta (an extended RelativeLayout) to CustomViewAlpha (an extended LinearLayout) -- the idea being that the CustomViewAlpha will hold a bunch of CustomViewBetas a la a ListView. No matter what I try, it doesn't work. I either see nothing -- no CustomViewBetas, or it gives me an NPE when I try setText on one of the TextViews inside the CustomViewBeta
CustomViewAlpha works fine since it's hard-coded in the Fragment's XML:
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout
...>
<com.path.CustomViewAlpha
android:id="#+id/customviewalpha"
android:orientation="vertical"
android:layout_gravity="center_vertical"
android:layout_width="match_parent"
android:layout_height="match_parent"/>
</FrameLayout>
With the code being:
public class CustomViewAlpha extends LinearLayout {
private Context mContext;
public CustomViewAlpha (Context context) {
super(context);
this.mContext = context;
}
public CustomViewAlpha (Context context, AttributeSet attrs) {
super(context, attrs);
this.mContext = context;
}
public CustomViewAlpha (Context context, AttributeSet attrs, int defStyle){
super(context, attrs,defStyle);
this.mContext = context;
}
public void addCustomViewBeta(String someString){
CustomViewBeta customViewBeta = new CustomViewBeta(mContext);
addView(customViewBeta);
}
CustomViewBeta is not hard-coded in the Fragment's XML and get's added programmatically:
public class CustomViewBeta extends RelativeLayout{
private Context mContext;
private TextView textView;
public CustomViewBeta (Context context) {
super(context);
this.mContext = context;
init();
}
public CustomViewBeta (Context context, AttributeSet attrs) {
super(context, attrs);
this.mContext = context;
init();
}
public CustomViewBeta (Context context, AttributeSet attrs, int defStyle){
super(context, attrs,defStyle);
this.mContext = context;
init();
}
private void init() {
LayoutInflater.from(mContext).inflate(R.layout.customviewbeta, null, false);
textView = (TextView) findViewById(R.id.tripleexpandablelistview_category_name);
textView.setText("ASDASDASDAD");
}
With this XML being:
<?xml version="1.0" encoding="utf-8"?>
<com.path.CustomViewBeta
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<TextView
android:id="#+id/customviewbeta_textview"
android:layout_width="wrap_content"
android:layout_height="wrap_content"/>
</com.path.CustomViewBeta>
I usually get hit with a NPE on the "textView.setText("ASDASDASDAD");" line because the TextView is null. Is there something I'm missing? Should I not try to inflate an XML for the CustomViewBeta and just do it programmatically (adding the textviews one by one programmatically?)? Thanks.
your init is wrong
private void init() {
LayoutInflater.from(mContext).inflate(R.layout.customviewbeta, null, false);
textView = (TextView) findViewById(R.id.tripleexpandablelistview_category_name);
textView.setText("ASDASDASDAD");
}
the last parameter has to be true to add the TextViewto the RelativeLayout.Also ViewGroup, has a static inflate method, so you can avoid LayoutInflater.from(mContext), you can just call inflate(mContext, R.layout.customviewbeta, this);

how to create custom font in android?

How can i use the custom font which we add in asset folder in xml?
I want to create custom font for app..
but I run the programme ,it has exception.
this is my java code:
public class MainActivity extends TextView {
private static final String TAG = "TextView";
public MainActivity(Context context) {
super(context);
}
public MainActivity(Context context, AttributeSet attrs) {
super(context, attrs);
setCustomFont(context, attrs);
}
public MainActivity(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
setCustomFont(context, attrs);
}
private void setCustomFont(Context ctx, AttributeSet attrs) {
TypedArray a = ctx.obtainStyledAttributes(attrs, R.styleable.textfont);
String customFont = a.getString(R.styleable.TextViewPlus_customFont);
setCustomFont(ctx, customFont);
a.recycle();
}
public boolean setCustomFont(Context ctx, String asset) {
Typeface tf = null;
try {
tf = Typeface.createFromAsset(ctx.getAssets(), asset);
} catch (Exception e) {
Log.e(TAG, "Could not get typeface: "+e.getMessage());
return false;
}
setTypeface(tf);
return true;
}
}
and create a folder in res/values/attrs
<?xml version="1.0" encoding="utf-8"?>
<resources>
<declare-styleable name="textfont">
<attr name="customFont" format="string"/>
</declare-styleable>
</resources>
and xml:
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:foo="http://schemas.android.com/apk/res/com.example.changfont"
android:orientation="vertical" android:layout_width="fill_parent"
android:layout_height="fill_parent">
<com.example.changfont.MainActivity
android:id="#+id/textViewPlus1"
android:layout_height="match_parent"
android:layout_width="match_parent"
android:text="helooo"
foo:customFont="aaa.ttf">
</com.example.changfont.MainActivity>
logcat is:
09-09 20:44:28.063: E/AndroidRuntime(11515): FATAL EXCEPTION: main
09-09 20:44:28.063: E/AndroidRuntime(11515): java.lang.RuntimeException: Unable to instantiate activity ComponentInfo{com.example.changfont/com.example.changfont.MainActivity}: java.lang.InstantiationException: can't instantiate class com.example.changfont.MainActivity; no empty constructor
09-09 20:44:28.063: E/AndroidRuntime(11515): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:1891)
I do not know what the problem is ?
please help me.
Your MainActivity is not an Activity but a TextView. It cannot be instantiated as an activity and should not be declared in the manifest.
Looks like you need to:
Rename this MainActivity to something like `MyCustomTextView``
Implement MainActivity as an activity that calls setContentView() with a layout that contains an instance of your MyCustomTextView, such as the XML you posted (with MainActivity renamed).

Custom View Extending Relative Layout

package com.binod.customviewtest;
import android.content.Context;
import android.view.LayoutInflater;
import android.widget.RelativeLayout;
public class CustomView extends RelativeLayout{
public CustomView(Context context) {
super(context);
// TODO Auto-generated constructor stub
// LayoutInflater mInflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
LayoutInflater mInflater = LayoutInflater.from(context);
mInflater.inflate(R.layout.custom_view , this, true);
}
}
Including as
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity" >
<com.binod.customviewtest.CustomView
android:layout_width="match_parent"
android:layout_height="wrap_content"
></com.binod.customviewtest.CustomView>
</RelativeLayout>
Custom View as
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="#string/hello_world" />
</RelativeLayout>
Just started adding a new custom view and got the error once If I clear this then can move forward
I am getting crash "Caused by: android.view.InflateException: Binary XML file line #1: Error inflating class"
You need to have 2 more constructors. To know why
Do I need all three constructors for an Android custom view?
public class CustomView extends RelativeLayout{
LayoutInflater mInflater;
public CustomView(Context context) {
super(context);
mInflater = LayoutInflater.from(context);
init();
}
public CustomView(Context context, AttributeSet attrs, int defStyle)
{
super(context, attrs, defStyle);
mInflater = LayoutInflater.from(context);
init();
}
public CustomView(Context context, AttributeSet attrs) {
super(context, attrs);
mInflater = LayoutInflater.from(context);
init();
}
public void init()
{
View v = mInflater.inflate(R.layout.custom_view, this, true);
TextView tv = (TextView) v.findViewById(R.id.textView1);
tv.setText(" Custom RelativeLayout");
}
}
I am posting an example. My packagename is different
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent" >
<com.example.testall.CustomView
android:id="#+id/timer1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
/>
</RelativeLayout>
custom_view.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent" >
<TextView
android:id="#+id/textView1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentTop="true"
android:layout_centerHorizontal="true"
android:layout_marginTop="60dp"
android:text="My Custom View" />
</RelativeLayout>
MainActivity.java
public class MainActivity extends Activity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
}
}
Snap
As pskink suggested there in a RelativeLayout in activity_main.xml with a child CustomView. Then CustomView extends RealtiveLayout and then again you inflate a customview with RelativeLayout and a child TextView. No need for all these. Just a CustomView. Have a TextView created programatically and then add textview to RelativeLayout
Edit:
activity_main.xml
<com.example.testall.CustomView
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/timer1"
android:layout_width="match_parent"
android:layout_height="match_parent"
/>
CustomView
public class CustomView extends RelativeLayout{
TextView tv;
public CustomView(Context context) {
super(context);
tv = new TextView(context);
init();
}
public CustomView(Context context, AttributeSet attrs, int defStyle)
{
super(context, attrs, defStyle);
tv = new TextView(context);
init();
}
public CustomView(Context context, AttributeSet attrs) {
super(context, attrs);
tv = new TextView(context);
init();
}
public void init()
{
this.addView(tv);
tv.setText(" Custom RelativeLayout");
}
}
Try to get Activity and use this
{
LayoutInflater inflter = activity.getLayoutInflater();
View v = inflter.inflate(R.layout.custom_view,null);
this.addView(v); or addView(v);
}

how to stop horizontal scrolling in case of long press

I have a horizontal list of images. I want, if I long press the image and try to drag the image then...
Extend the Gallery class and override the onLongPress(MotionEvent e) method and where so ever you are placing Gallery view in the xml place your class instead.
Like the following
package com.prac;
import android.content.Context;
import android.util.AttributeSet;
import android.view.MotionEvent;
import android.widget.Gallery;
import android.widget.Toast;
public class MyGallery extends Gallery {
private Context mContext;
public MyGallery(Context context) {
super(context);
mContext = context;
// TODO Auto-generated constructor stub
}
public MyGallery(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
mContext = context;
// TODO Auto-generated constructor stub
}
public MyGallery(Context context, AttributeSet attrs) {
super(context, attrs);
mContext = context;
// TODO Auto-generated constructor stub
}
#Override
public boolean onLongPress(MotionEvent e)
{
// do what ever you want on Long Press Here
return false;
}
}
Now your xml layout should be like this
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
>
<com.prac.MyGallery
android:id="#+id/Gallery"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
/>
</RelativeLayout>
Hope it helps :) And if it helps you out dont forget to accept the answer by clicking the arrow on left side of answer and making it green

Categories

Resources