I am trying to implement pageviewer in my app using this tutorial. But my app force closes. It shows android.view.InflateException: Binary XML file line #2: Error inflating class com.example.viewpager.ScrollView. Where I am going wrong? I am a beginner in android so please guide me. I thought I might have imported wrong libs as my app is supporting API 10. So I searched other answers but of no use. Here is my code:
MainActvity.java
package com.example.viewpager;
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentActivity;
import android.support.v4.app.FragmentManager;
import android.support.v4.app.FragmentStatePagerAdapter;
import android.support.v4.view.PagerAdapter;
import android.support.v4.view.ViewPager;
public class MainActivity extends FragmentActivity {
/**
* The number of pages (wizard steps) to show in this demo.
*/
private static final int NUM_PAGES = 5;
/**
* The pager widget, which handles animation and allows swiping horizontally to access previous
* and next wizard steps.
*/
private ViewPager mPager;
/**
* The pager adapter, which provides the pages to the view pager widget.
*/
private PagerAdapter mPagerAdapter;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
// Instantiate a ViewPager and a PagerAdapter.
mPager = (ViewPager) findViewById(R.id.pager);
mPagerAdapter = new ScreenSlidePagerAdapter(getSupportFragmentManager());
mPager.setAdapter(mPagerAdapter);
}
#Override
public void onBackPressed() {
if (mPager.getCurrentItem() == 0) {
// If the user is currently looking at the first step, allow the system to handle the
// Back button. This calls finish() on this activity and pops the back stack.
super.onBackPressed();
} else {
// Otherwise, select the previous step.
mPager.setCurrentItem(mPager.getCurrentItem() - 1);
}
}
/**
* A simple pager adapter that represents 5 ScreenSlidePageFragment objects, in
* sequence.
*/
private class ScreenSlidePagerAdapter extends FragmentStatePagerAdapter {
public ScreenSlidePagerAdapter(android.support.v4.app.FragmentManager fm) {
super(fm);
}
#Override
public Fragment getItem(int position) {
return new ScreenSlidePageFragment();
}
#Override
public int getCount() {
return NUM_PAGES;
}
}
}
ScreenSlidePagerFragment.java
package com.example.viewpager;
import android.support.v4.app.Fragment;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
public class ScreenSlidePageFragment extends Fragment {
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
ViewGroup rootView = (ViewGroup) inflater.inflate(R.layout.fragment_screen_slide_page, container, false);
return rootView;
}
}
actvity_main.xml
<?xml version="1.0" encoding="utf-8"?><android.support.v4.view.ViewPager
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/pager"
android:layout_width="match_parent"
android:layout_height="match_parent" />
fragment_slide_screen_page.xml
<?xml version="1.0" encoding="utf-8"?>
<com.example.viewpager.ScrollView
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/content"
android:layout_width="match_parent"
android:layout_height="match_parent">
<TextView style="?android:textAppearanceMedium"
android:padding="16dp"
android:lineSpacingMultiplier="1.2"
android:textColor="#000000"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Page 1" />
</com.example.viewpager.ScrollView>
Log cat:
android.view.InflateException: Binary XML file line #2: Error inflating class com.example.viewpager.ScrollView
at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:581)
at android.view.LayoutInflater.inflate(LayoutInflater.java:386)
at android.view.LayoutInflater.inflate(LayoutInflater.java:320)
at com.example.viewpager.ScreenSlidePageFragment.onCreateView(ScreenSlidePageFragment.java:14)
at android.support.v4.app.Fragment.performCreateView(Fragment.java:1478)
at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:927)
at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1104)
at android.support.v4.app.BackStackRecord.run(BackStackRecord.java:682)
at android.support.v4.app.FragmentManagerImpl.execPendingActions(FragmentManager.java:1460)
at android.support.v4.app.FragmentManagerImpl.executePendingTransactions(FragmentManager.java:472)
at android.support.v4.app.FragmentStatePagerAdapter.finishUpdate(FragmentStatePagerAdapter.java:163)
at android.support.v4.view.ViewPager.populate(ViewPager.java:1068)
at android.support.v4.view.ViewPager.populate(ViewPager.java:914)
at android.support.v4.view.ViewPager.onMeasure(ViewPager.java:1436)
at android.view.View.measure(View.java:8313)
at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:3138)
at android.widget.FrameLayout.onMeasure(FrameLayout.java:250)
at android.view.View.measure(View.java:8313)
at android.widget.LinearLayout.measureVertical(LinearLayout.java:531)
at android.widget.LinearLayout.onMeasure(LinearLayout.java:309)
at android.view.View.measure(View.java:8313)
at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:3138)
at android.widget.FrameLayout.onMeasure(FrameLayout.java:250)
at android.view.View.measure(View.java:8313)
at android.view.ViewRoot.performTraversals(ViewRoot.java:845)
at android.view.ViewRoot.handleMessage(ViewRoot.java:1865)
at android.os.Handler.dispatchMessage(Handler.java:99)
at android.os.Looper.loop(Looper.java:130)
at android.app.ActivityThread.main(ActivityThread.java:3687)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:507)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:867)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:625)
at dalvik.system.NativeStart.main(Native Method)
Caused by: java.lang.ClassNotFoundException: com.example.viewpager.ScrollView in loader dalvik.system.PathClassLoader[/data/app/com.example.viewpager-2.apk]
at dalvik.system.PathClassLoader.findClass(PathClassLoader.java:240)
at java.lang.ClassLoader.loadClass(ClassLoader.java:551)
at java.lang.ClassLoader.loadClass(ClassLoader.java:511)
at android.view.LayoutInflater.createView(LayoutInflater.java:471)
at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:570)
... 33 more
change adapter to:
private class ScreenSlidePagerAdapter extends FragmentStatePagerAdapter {
int layouts[];
public ScreenSlidePagerAdapter(android.support.v4.app.FragmentManager fm) {
super(fm);
layouts=new int[]{R.layout.fragment_slide_screen_page1,R.layout.fragment_slide_screen_page2,R.layout.fragment_slide_screen_page3,R.layout.fragment_slide_screen_page4,R.layout.fragment_slide_screen_page5};
}
#Override
public Fragment getItem(int position) {
ScreenSlidePageFragment fragment=new ScreenSlidePageFragment();
fragment.setContent(layouts[position]);
return fragment;
}
#Override
public int getCount() {
return NUM_PAGES;
}
}
and in fragment:
public class ScreenSlidePageFragment extends Fragment {
int layout;
public void setContent(int layout){
this.layout=layout;
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
ViewGroup rootView = (ViewGroup) inflater.inflate(layout, container, false);
return rootView;
}
}
Although not sure what change you want in each fragment but the above will require you to create 5 layout xmls that you can set every time you create a new Fragment.
Even I encountered crash.
This is because I was calling mAdapter.notifyDataSetChanged(); inside
#Override
public void onPageScrolled(int arg0, float arg1, int arg2) {
}
Later I shifted the method to
#Override
public void onPageSelected(int arg0) {
mAdapter.notifyDataSetChanged();
}
So that did the trick
Related
I have an app that simply displays 1 picture, implemented through Picasso. The onClick works fine if I replace the contents with a simple toast, so it must be the MediaPlayer calls. I don't know why it keeps crashing though.
package com.example.andrew.crossfade;
import android.media.MediaPlayer;
import android.support.v7.app.ActionBarActivity;
import android.support.v4.app.Fragment;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import com.squareup.picasso.Picasso;
public class MainActivity extends ActionBarActivity{
MediaPlayer mp;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
getSupportActionBar().hide();
setContentView(R.layout.activity_main);
if (savedInstanceState == null) {
getSupportFragmentManager().beginTransaction()
.add(R.id.container, new PlaceholderFragment())
.commit();
}
ImageView imageView = (ImageView) findViewById(R.id.imageView);
imageView.setClickable(true);
Picasso.with(this)
.load("http://i.imgur.com/vpeH7S2.jpg")
.into(imageView);
imageView.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
mp = MediaPlayer.create(MainActivity.this, R.raw.later);
mp.start();
}
});
}
public static class PlaceholderFragment extends Fragment {
public PlaceholderFragment() {
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.fragment_main, container, false);
return rootView;
}
}
}
The XML:
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools" android:id="#+id/container"
android:layout_width="match_parent" android:layout_height="match_parent"
tools:context=".MainActivity" tools:ignore="MergeRootFrame" >
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/imageView"
android:layout_alignParentTop="true"
android:layout_centerHorizontal="true"
/>
And finally, the log cat:
10-29 12:12:07.343 18409-18409/com.example.andrew.crossfade W/dalvikvm﹕ threadid=1: thread exiting with uncaught exception (group=0x41f38da0)
10-29 12:12:07.343 18409-18409/com.example.andrew.crossfade E/AndroidRuntime﹕ FATAL EXCEPTION: main
Process: com.example.andrew.crossfade, PID: 18409
java.lang.NullPointerException
at com.example.andrew.crossfade.MainActivity$1.onClick(MainActivity.java:47)
at android.view.View.performClick(View.java:4633)
at android.view.View$PerformClick.run(View.java:19330)
at android.os.Handler.handleCallback(Handler.java:733)
at android.os.Handler.dispatchMessage(Handler.java:95)
at android.os.Looper.loop(Looper.java:157)
at android.app.ActivityThread.main(ActivityThread.java:5356)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:515)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1265)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1081)
at dalvik.system.NativeStart.main(Native Method)
something is null in your code
java.lang.NullPointerException
call mp.prepare() before start
and make sure R.raw.later is playable audio for media player
I always get a NullPointerException when I try to access a fragment from inside my main activity. No matter what I do.
The issue is that I use TabsPagerAdapter and ViewPager and I don't know how to get the inflated views (the fragment's onCreate() method returns the inflated view already).
The goal is to get access to an element inside the fragment and hide or show it dynamically by a single background thread which should also do this for more fragments.
MainActivity.java
public class MainActivity extends FragmentActivity implements
ActionBar.TabListener
{
/* swipe view */
private ViewPager viewPager;
private TabsPagerAdapter mAdapter;
private android.app.ActionBar actionBar;
// tab titles
private String[] tabs = { "Basic", "Advanced", "Settings"};
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
/* init swipe views */
mAdapter = new TabsPagerAdapter(getSupportFragmentManager());
viewPager = (ViewPager) findViewById(R.id.pager);
viewPager.setAdapter(mAdapter);
actionBar = getActionBar();
actionBar.setHomeButtonEnabled(false);
actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS);
/* addTab returns void, how to geht my fragements and their views???*/
for (String tabName : tabs)
actionBar.addTab(actionBar.newTab().setText(tabName).setTabListener(this));
viewPager.setOnPageChangeListener(new ViewPager.OnPageChangeListener() {
#Override
public void onPageSelected(int position) {
actionBar.setSelectedNavigationItem(position);
}
#Override
public void onPageScrolled(int arg0, float arg1, int arg2) {}
#Override
public void onPageScrollStateChanged(int arg0) {}
});
}
public void testFunction()
{
FragmentPage1 fragmentPage1 = (FragmentPage1) getSupportFragmentManager().findFragmentById(R.layout.fragment_page1);
GridLayout gridlayout = (GridLayout) fragmentPage1.getRootView().findViewById(R.id.adBannerBasicLayout);
gridlayout.setVisibility(GridLayout.VISIBLE); /* THATS MY GOAL */
}
FragmentPage1.java
public class FragmentPage1 extends Fragment {
private View rootView;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
rootView = inflater.inflate(R.layout.fragment_page1, container, false);
/* HERE IT IS WORKING FINE,
but later I want to make it visible again
from code OUTSIDE FragmentPage1 ??? */
GridLayout gridlayout = (GridLayout) rootView.findViewById(R.id.adBannerBasicLayout);
gridlayout.setVisibility(GridLayout.GONE);
return rootView;
}
/* so I tried this, but also get always NullPointerException */
public View getRootView()
{
return rootView;
}
}
fragment_page1.xml
<?xml version="1.0" encoding="utf-8"?>
<ScrollView
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:ads="http://schemas.android.com/apk/res-auto"
android:id="#+id/settings_scroll_view"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
>
<GridLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:ads="http://schemas.android.com/apk/res-auto"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="#000000"
android:orientation="vertical"
android:rowCount="12"
android:columnCount="5"
>
<!-- Some Banner Ads I want to hide show -->
<!-- I want to access this from everywhere! -->
<GridLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:ads="http://schemas.android.com/apk/res-auto"
android:id="#+id/adBannerBasicLayout"
android:orientation="vertical"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="fill"
android:rowCount="3"
android:columnCount="1"
android:layout_row="0"
android:layout_column="0"
android:layout_columnSpan="5">
<Space
android:layout_width="0dp"
android:layout_height="5dp"
android:layout_row="0"
android:layout_column="0"
/>
<com.google.android.gms.ads.AdView
android:id="#+id/adBannerBasic"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="fill"
ads:adSize="BANNER"
ads:adUnitId="xxxxxxxxxxxxxxxxxxxxxxxxxx"
android:layout_row="1"
android:layout_column="0"
>
</com.google.android.gms.ads.AdView>
<Space
android:layout_width="0dp"
android:layout_height="5dp"
android:layout_row="2"
android:layout_column="0"
/>
</GridLayout>
<!-- more stuff... -->
</GridLayout>
</ScrollView>
Please help me out, I'm totally stuck!
THANKS!
EDIT:
The scond line in testFunction() throws the NullPointerException:
GridLayout gridlayout = (GridLayout) fragmentPage1.getRootView().findViewById(R.id.adBannerBasicLayout);
because getSupportFragmentManager() always returns null:
FragmentPage1 fragmentPage1 = (FragmentPage1) getSupportFragmentManager().findFragmentById(R.layout.fragment_page1);
Logcat Outoput
java.lang.IllegalStateException: Could not execute method of the activity
at android.view.View$1.onClick(View.java:3969)
at android.view.View.performClick(View.java:4633)
at android.view.View$PerformClick.run(View.java:19330)
at android.os.Handler.handleCallback(Handler.java:733)
at android.os.Handler.dispatchMessage(Handler.java:95)
at android.os.Looper.loop(Looper.java:157)
at android.app.ActivityThread.main(ActivityThread.java:5356)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:515)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1265)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1081)
at de.robv.android.xposed.XposedBridge.main(XposedBridge.java:132)
at dalvik.system.NativeStart.main(Native Method)
Caused by: java.lang.reflect.InvocationTargetException
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:515)
at android.view.View$1.onClick(View.java:3964)
at android.view.View.performClick(View.java:4633)
at android.view.View$PerformClick.run(View.java:19330)
at android.os.Handler.handleCallback(Handler.java:733)
at android.os.Handler.dispatchMessage(Handler.java:95)
at android.os.Looper.loop(Looper.java:157)
at android.app.ActivityThread.main(ActivityThread.java:5356)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:515)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1265)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1081)
at de.robv.android.xposed.XposedBridge.main(XposedBridge.java:132)
at dalvik.system.NativeStart.main(Native Method)
Caused by: java.lang.NullPointerException
at org.tzapp.smote.MainActivity.testFuntion(MainActivity.java:393)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:515)
at android.view.View$1.onClick(View.java:3964)
at android.view.View.performClick(View.java:4633)
at android.view.View$PerformClick.run(View.java:19330)
at android.os.Handler.handleCallback(Handler.java:733)
at android.os.Handler.dispatchMessage(Handler.java:95)
at android.os.Looper.loop(Looper.java:157)
at android.app.ActivityThread.main(ActivityThread.java:5356)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:515)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1265)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1081)
at de.robv.android.xposed.XposedBridge.main(XposedBridge.java:132)
at dalvik.system.NativeStart.main(Native Method)
You are using the wrong static value from the auto generated R file!
Instead of using R.layout.fragment_page1 which references the XML resource you should use R.id.fragment_page1 which should be the id of the fragment in your R.layout.activity_main XML file at /res/layout/activity_main.xml
R.layout references XML layout files
R.id references individual XML nodes (Views, Fragments etc.)
So in short, change:
FragmentPage1 fragmentPage1 = (FragmentPage1) getSupportFragmentManager().findFragmentById(R.layout.fragment_page1);
To:
FragmentPage1 fragmentPage1 = (FragmentPage1) getSupportFragmentManager().findFragmentById(R.id.fragment_page1);
And make sure that your fragment id in /res/layout/activity_main.xml is set to R.id.fragment_page1 like so:
<fragment android:name="com.example.yourpackage.FragmentPage1"
android:id="#+id/fragment_page1"
android:layout_weight="1"
android:layout_width="0dp"
android:layout_height="match_parent" />
you use getSupportFragmentManager() to get fragment.
Please double check if your FragmentPage1 extends a android.support.v4.app.Fragment;
not a
android.Fragment;
After updating SDK and repository, there is new trouble. I cant build anymore and I dont want to compile on level 23 :(
Information:Gradle tasks [clean, :app:generateDebugSources, :app:generateDebugTestSources]
:app:clean
:app:preBuild
:app:preDebugBuild
:app:checkDebugManifest
:app:preReleaseBuild
:app:prepareComAndroidSupportAppcompatV72300Library
:app:prepareComAndroidSupportSupportV42300Library
:app:prepareComGoogleAndroidGmsPlayServicesAds750Library
:app:prepareComGoogleAndroidGmsPlayServicesAnalytics750Library
:app:prepareComGoogleAndroidGmsPlayServicesBase750Library
:app:prepareComInstabugLibraryInstabugcore161Library
:app:prepareComInstabugLibraryInstabugsupport161Library
:app:prepareDebugDependencies
:app:compileDebugAidl
:app:compileDebugRenderscript
:app:generateDebugBuildConfig
:app:generateDebugAssets UP-TO-DATE
:app:mergeDebugAssets
:app:generateDebugResValues UP-TO-DATE
:app:generateDebugResources
:app:mergeDebugResources
:app:processDebugManifest
:app:processDebugResources
C:\Users\Tom\AndroidStudioProjects\SSMote\app\build\intermediates\exploded-aar\com.android.support\appcompat-v7\23.0.0\res\values-v23\values-v23.xml
Error:(1) Error retrieving parent for item: No resource found that matches the given name 'android:TextAppearance.Material.Widget.Button.Inverse'.
Error:(1) Error retrieving parent for item: No resource found that matches the given name 'android:Widget.Material.Button.Colored'.
Error:Execution failed for task ':app:processDebugResources'.
> com.android.ide.common.internal.LoggedErrorException: Failed to run command:
C:\Users\Tom\AppData\Local\Android\sdk\build-tools\21.1.2\aapt.exe package -f --no-crunch -I C:\Users\Tom\AppData\Local\Android\sdk\platforms\android-21\android.jar -M C:\Users\Tom\AndroidStudioProjects\SSMote\app\build\intermediates\manifests\full\debug\AndroidManifest.xml -S C:\Users\Tom\AndroidStudioProjects\SSMote\app\build\intermediates\res\debug -A C:\Users\Tom\AndroidStudioProjects\SSMote\app\build\intermediates\assets\debug -m -J C:\Users\Tom\AndroidStudioProjects\SSMote\app\build\generated\source\r\debug -F C:\Users\Tom\AndroidStudioProjects\SSMote\app\build\intermediates\res\resources-debug.ap_ --debug-mode --custom-package org.tzapp.smote -0 apk --output-text-symbols C:\Users\Tom\AndroidStudioProjects\SSMote\app\build\intermediates\symbols\debug
Error Code:
1
Output:
C:\Users\Tom\AndroidStudioProjects\SSMote\app\build\intermediates\res\debug\values-v23\values.xml:5: error: Error retrieving parent for item: No resource found that matches the given name 'android:TextAppearance.Material.Widget.Button.Inverse'.
C:\Users\Tom\AndroidStudioProjects\SSMote\app\build\intermediates\res\debug\values-v23\values.xml:20: error: Error retrieving parent for item: No resource found that matches the given name 'android:Widget.Material.Button.Colored'.
Information:BUILD FAILED
Information:Total time: 40.157 secs
Information:3 errors
Information:0 warnings
Also I found another answer, which is I think most satisfying :)
I forgot to mention that there is another class. It all comes from that stupid piece of example code for Swipe Views which is avaible somewhere on developers.google.com ...
Everytime I tried to access the FragmentPages via my TabPagerAdapter class using the stupid getItem(int i) method, I created a new Fragment() :-/ Very irritating!
Class TabsPagerAdapter from bad google example
public class TabsPagerAdapter extends FragmentPagerAdapter {
public TabsPagerAdapter(FragmentManager fm, MainActivity mainActivity){
super(fm);
}
// page index, fragment selector
#Override
public Fragment getItem(int index) {
switch (index)
{
case 0: return new FragmentPage1(); // bad practice
case 1: return new FragmentPage2(); // why should one do that?
case 2: return new FragmentPage3();
}
return null;
}
#Override
public int getCount() {
return 3;
}
}
What a piece of crap ^^ And I just copied it over and then totally forgot about it's existence ;)
Moved instanciation of fragments to constructor and keeped them for later use. Works perfectly now.
Class TabsPagerAdapter after optimization
public class TabsPagerAdapter extends FragmentPagerAdapter {
// hosted fragments
private FragmentPage fragmentPageBasic;
private FragmentPage fragmentPageAdvanced;
private FragmentPage fragmentPageSettings;
//constructor
public TabsPagerAdapter(FragmentManager fm, MainActivity mainActivity){
super(fm);
fragmentPageBasic = new FragmentPage();
fragmentPageBasic.setMainActivity(mainActivity);
fragmentPageBasic.setLayoutResource(R.layout.fragment_page1);
fragmentPageBasic.setAdBannerResource(R.id.adBannerBasic);
fragmentPageBasic.setAdBannerLayoutResource(R.id.adBannerBasicLayout);
fragmentPageAdvanced = new FragmentPage();
fragmentPageAdvanced.setMainActivity(mainActivity);
fragmentPageAdvanced.setLayoutResource(R.layout.fragment_page2);
fragmentPageAdvanced.setAdBannerResource(R.id.adBannerAdvanced);
fragmentPageAdvanced.setAdBannerLayoutResource(R.id.adBannerAdvancedLayout);
fragmentPageSettings = new FragmentSettingsPage();
fragmentPageSettings.setMainActivity(mainActivity);
fragmentPageSettings.setLayoutResource(R.layout.fragment_page3);
fragmentPageSettings.setAdBannerResource(R.id.adBannerSettings);
fragmentPageSettings.setAdBannerLayoutResource(R.id.adBannerSettingsLayout);
}
// page index, fragment selector
#Override
public Fragment getItem(int index) {
switch (index)
{
case 0: return fragmentPageBasic;
case 1: return fragmentPageAdvanced;
case 2: return fragmentPageSettings;
}
return null;
}
#Override
public int getCount() {
return 3;
}
// GETTERS
public FragmentPage getFragmentPageBasic() {return fragmentPageBasic;}
public FragmentPage getFragmentPageAdvanced() {return fragmentPageAdvanced;}
public FragmentPage getFragmentPageSettings() {return fragmentPageSettings;}
}
Instead of having redundant FragmentPage1, Fragment2, FragmentPage3 classes, of course now there is only FragmentPage and FragmentSettingsPage (extends FragmentPage to override OnCreateView method), which results in a much cleaner and more understandable code.
Class FragmentPage
public class FragmentPage extends Fragment {
protected MainActivity mainActivity;
// layout resource
protected int layoutResource;
// view
protected View rootView;
//Admob
protected AdView adBanner;
protected int adBannerResource;
protected int adBannerLayoutResource;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
onCreate(inflater, container);
return rootView;
}
// manage common onCreate things
protected void onCreate(LayoutInflater inflater, ViewGroup container)
{
rootView = inflater.inflate(layoutResource, container, false);
// admob banner
adBanner = (AdView) rootView.findViewById(adBannerResource);
adBanner.setAdListener(new AdListener() {
#Override
public void onAdLoaded() {
}
#Override
public void onAdOpened() {
}
#Override
public void onAdClosed() {
newAdBannerRequest();
}
#Override
public void onAdFailedToLoad(int errorCode) {
newAdBannerRequest();
}
#Override
public void onAdLeftApplication() {
}
});
if(mainActivity.showAdBanners())
{
newAdBannerRequest();
showAdBanner();
}
else
hideAdBanner();
}
// ADMOB
public void newAdBannerRequest()
{
AdRequest request = new AdRequest.Builder()
.addTestDevice(AdRequest.DEVICE_ID_EMULATOR) // All emulators
.addTestDevice("XXXXXXXXXXXXXXXXXXXXXXXXXX") // My Galaxy Nexus test phone
.build();
adBanner.loadAd(request);
}
public void showAdBanner()
{
GridLayout adBannerLayout = (GridLayout) rootView.findViewById(adBannerLayoutResource);
if(adBannerLayout.getVisibility() == GridLayout.GONE)
adBannerLayout.setVisibility(GridLayout.VISIBLE);
}
public void hideAdBanner()
{
GridLayout adBannerLayout = (GridLayout) rootView.findViewById(adBannerLayoutResource);
if(adBannerLayout.getVisibility() == GridLayout.VISIBLE)
adBannerLayout.setVisibility(GridLayout.GONE);
}
// GETTERS
public AdView getAdBanner() { return adBanner;}
public View getRootView() { return rootView;}
// SETTERS
public void setMainActivity(MainActivity mainActivity) {this.mainActivity = mainActivity;}
public void setLayoutResource(int layoutResource){this.layoutResource = layoutResource;}
public void setAdBannerResource(int adBannerResource){this.adBannerResource = adBannerResource;}
public void setAdBannerLayoutResource(int adBannerLayoutResource){this.adBannerLayoutResource = adBannerLayoutResource;}
}
Class FragmentSettingsPage
public class FragmentSettingsPage extends FragmentPage {
// Preferences
public static final String PREFS_NAME = "Preferences";
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
super.onCreate(inflater, container);
SharedPreferences preferences = mainActivity.getSharedPreferences(PREFS_NAME, 0);
// do some other top secret stuff here ;)
return rootView;
}
}
Any ideas how to improve this further ?
Use import android.support.v4.app.Fragment instead import android.app.Fragment
Please add this in your gradle dependencies
compile 'com.android.support:support-v4:22.1.1'
Edit : please use findFragmentById(R.id.fragment_page1) instead R.layout
FragmentPage1 fragmentPage1 = (FragmentPage1) getSupportFragmentManager().findFragmentById(R.id.fragment_page1);
I have an activity holding a fragment, in this fragment there is a button , when it is clicked, a dialog is popped out.
In this dialog, there is a Viewpager, which holds some fragments to display.
Here are the code and the error, please spare your valuable time to show me where I am wrong. I much appreciate your help.
MainActivity.class
import android.os.Bundle;
import android.support.v4.app.FragmentActivity;
import android.support.v4.app.FragmentManager;
import android.support.v4.app.FragmentTransaction;
public class MainActivity extends FragmentActivity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
FragmentManager fm = getSupportFragmentManager();
FragmentTransaction fragmentTransaction = fm.beginTransaction();
MyFragment fragment = new MyFragment();
fragmentTransaction.add(R.id.container, fragment);
fragmentTransaction.commit();
}
}
MyFragment.class
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.view.LayoutInflater;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.ViewGroup;
import android.widget.Button;
public class MyFragment extends Fragment {
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View v = inflater.inflate(R.layout.fragment_sandbox, container, false);
Button button = (Button) v.findViewById(R.id.button);
button.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View arg0) {
PagerDialog dialog = new PagerDialog(getActivity(),
getChildFragmentManager());
dialog.show();
}
});
return v;
}
}
PagerDialog.class
import android.app.Dialog;
import android.content.Context;
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentManager;
import android.support.v4.app.FragmentStatePagerAdapter;
import android.support.v4.view.ViewPager;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
public class PagerDialog extends Dialog {
ViewPager mViewPager;
FragmentStatePagerAdapter mAdapter;
FragmentManager mFragmentManager;
public PagerDialog(Context context, FragmentManager fm) {
super(context);
mFragmentManager = fm;
}
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.dialog);
mViewPager = (ViewPager) findViewById(R.id.pager);
mAdapter = new MyAdapter(mFragmentManager);
mViewPager.setAdapter(mAdapter);
}
private class MyAdapter extends FragmentStatePagerAdapter {
public MyAdapter(FragmentManager fm) {
super(fm);
}
#Override
public Fragment getItem(int index) {
return new DummyFragment();
}
#Override
public int getCount() {
return 2;
}
}
private class DummyFragment extends Fragment {
#Override
public View onCreateView(LayoutInflater inflater,
#Nullable ViewGroup container,
#Nullable Bundle savedInstanceState) {
View v = inflater.inflate(R.layout.fragment_dummy_layout,
container, false);
return v;
}
}
}
Here is the dialog.xml:
<?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" >
<android.support.v4.view.ViewPager
android:id="#+id/pager"
android:layout_width="match_parent"
android:layout_height="match_parent" />
</LinearLayout>
Here is the error
03-06 19:43:38.487: E/AndroidRuntime(1167): FATAL EXCEPTION: main
03-06 19:43:38.487: E/AndroidRuntime(1167): Process: com.me.sandbox, PID: 1167
03-06 19:43:38.487: E/AndroidRuntime(1167): java.lang.IllegalArgumentException: No view found for id 0x7f05003d (com.mochimira.sandbox:id/pager) for fragment DummyFragment{b2d9f8c8 #0 id=0x7f05003d}
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:939)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1126)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.support.v4.app.BackStackRecord.run(BackStackRecord.java:739)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.support.v4.app.FragmentManagerImpl.execPendingActions(FragmentManager.java:1489)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.support.v4.app.FragmentManagerImpl.executePendingTransactions(FragmentManager.java:486)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.support.v4.app.FragmentStatePagerAdapter.finishUpdate(FragmentStatePagerAdapter.java:163)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.support.v4.view.ViewPager.populate(ViewPager.java:1073)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.support.v4.view.ViewPager.populate(ViewPager.java:919)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.support.v4.view.ViewPager.onMeasure(ViewPager.java:1441)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.View.measure(View.java:16497)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:5125)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.widget.LinearLayout.measureChildBeforeLayout(LinearLayout.java:1404)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.widget.LinearLayout.measureVertical(LinearLayout.java:695)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.widget.LinearLayout.onMeasure(LinearLayout.java:588)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.View.measure(View.java:16497)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:5125)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.widget.FrameLayout.onMeasure(FrameLayout.java:310)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.View.measure(View.java:16497)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:5125)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.widget.FrameLayout.onMeasure(FrameLayout.java:310)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.View.measure(View.java:16497)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:5125)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.widget.LinearLayout.measureChildBeforeLayout(LinearLayout.java:1404)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.widget.LinearLayout.measureVertical(LinearLayout.java:695)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.widget.LinearLayout.onMeasure(LinearLayout.java:588)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.View.measure(View.java:16497)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:5125)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.widget.FrameLayout.onMeasure(FrameLayout.java:310)
03-06 19:43:38.487: E/AndroidRuntime(1167): at com.android.internal.policy.impl.PhoneWindow$DecorView.onMeasure(PhoneWindow.java:2291)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.View.measure(View.java:16497)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.ViewRootImpl.performMeasure(ViewRootImpl.java:1916)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.ViewRootImpl.measureHierarchy(ViewRootImpl.java:1113)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.ViewRootImpl.performTraversals(ViewRootImpl.java:1295)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.ViewRootImpl.doTraversal(ViewRootImpl.java:1000)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.ViewRootImpl$TraversalRunnable.run(ViewRootImpl.java:5670)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.Choreographer$CallbackRecord.run(Choreographer.java:761)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.Choreographer.doCallbacks(Choreographer.java:574)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.Choreographer.doFrame(Choreographer.java:544)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographer.java:747)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.os.Handler.handleCallback(Handler.java:733)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.os.Handler.dispatchMessage(Handler.java:95)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.os.Looper.loop(Looper.java:136)
03-06 19:43:38.487: E/AndroidRuntime(1167): at android.app.ActivityThread.main(ActivityThread.java:5017)
03-06 19:43:38.487: E/AndroidRuntime(1167): at java.lang.reflect.Method.invokeNative(Native Method)
03-06 19:43:38.487: E/AndroidRuntime(1167): at java.lang.reflect.Method.invoke(Method.java:515)
03-06 19:43:38.487: E/AndroidRuntime(1167): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:779)
03-06 19:43:38.487: E/AndroidRuntime(1167): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:595)
03-06 19:43:38.487: E/AndroidRuntime(1167): at dalvik.system.NativeStart.main(Native Method
I have found a solution to the problem and have modified your classes so that this error no longer occurs.
The only major difference was that you should use a DialogFragment instead of a Dialog, that way you have access to call getChildFragmentManager() and receive the correct FragmentManager from the DialogFragment.
Even though you were using getChildFragmentManager() before, it was coming from MyFragment and the PagerDialog class was not a child fragment in MyFragment.
I have tested the code below, and it should be working fine now.
MyFragment
public class MyFragment extends Fragment {
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View v = inflater.inflate(R.layout.fragment_sandbox, container, false);
Button button = (Button) v.findViewById(R.id.button);
button.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View arg0) {
DialogFragment newFragment = PagerDialog.newInstance();
newFragment.show(getChildFragmentManager(), "dialog");
}
});
return v;
}
}
PagerDialog
public class PagerDialog extends DialogFragment {
public static PagerDialog newInstance() {
return new PagerDialog();
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View v = inflater.inflate(R.layout.dialog_fragment, container, false);
ViewPager mViewPager = (ViewPager) v.findViewById(R.id.view_pager);
/* Use childFragmentManager here provided from the PagerDialog */
MyAdapter mAdapter = new MyAdapter(getChildFragmentManager());
mViewPager.setAdapter(mAdapter);
return v;
}
private class MyAdapter extends FragmentStatePagerAdapter {
public MyAdapter(FragmentManager fm) {
super(fm);
}
#Override
public Fragment getItem(int index) {
return new DummyFragment();
}
#Override
public int getCount() {
return 2;
}
}
}
DummyFragment
public class DummyFragment extends Fragment {
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View v = inflater.inflate(R.layout.fragment_dummy_layout, container, false);
return v;
}
}
fragment_sandbox.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:gravity="center">
<Button
android:id="#+id/button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Test Fragment Dialog Pager"
android:textSize="24sp"
android:padding="20dp" />
</LinearLayout>
dialog_fragment.xml
<?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:gravity="center"
android:orientation="vertical" >
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Fragment Dialog Title Text "
android:padding="10dp"
android:textColor="#333"
android:textSize="24sp"/>
<android.support.v4.view.ViewPager
android:id="#+id/view_pager"
android:layout_width="match_parent"
android:layout_height="200dp"/>
</LinearLayout>
fragment_dummy_layout.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:gravity="center">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Fragment Dummy Text"
android:textSize="24sp"
android:textColor="#ff0000"/>
</LinearLayout>
I found in Google a blog post, it says that viewpager doesn't work on Dialog.
It also says we should use DialogFragment instead.
Here is the link to that blog: http://www.intellicode.in/viewpager-inside-dialog/
getChildFragmentManager() is available since API 17 while you're using the v4 support library. Try using the support fragment manager instead:
PagerDialog dialog = new PagerDialog(getActivity(),
getActivity().getSupportFragmentManager());
The Dialog class is the base class for dialogs, but you should avoid instantiating Dialog directly. Instead, use one of the following subclasses:
AlertDialogA dialog that can show a title, up to three buttons, a list of selectable items, or a custom layout. And also DatePickerDialog or TimePickerDialog.
These classes define the style and structure for your dialog, but you should use a DialogFragment as a container for your dialog. The DialogFragment class provides all the controls you need to create your dialog and manage its appearance, instead of calling methods on the Dialog object.
For more detail please go through Dialog Design
The error sounds like it's looking for the id pager in the xml file for DummyFragment (fragment_dummy_layout.xml). I wonder if this is due to calling View v = inflater.inflate(R.layout.fragment_dummy_layout, container, false); in the same file as setContentView(R.layout.dialog);. Have you tried separating DummyFragment into it's own file?
You could also try
View v = getActivity().getLayoutInflater().inflate(R.layout.fragment_dummy_layout,
container, false);
Try using DialogFragment and pass getChildFragmentManager() to your FragmentPagerAdapter's constructor.
DialogFragment:
public static class MyDialogFragment extends DialogFragment {
private ViewPager viewPager;
MySectionPagerAdapter mAdapter;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.m_layout, container);
viewPager = (ViewPager) view.findViewById(R.id.viewpager);
mAdapter = new MySectionPagerAdapter(getChildFragmentManager());
viewPager.setAdapter(mAdapter);
return view;
}
}
so far, we can't figure out why there is an error, but I have a way to work around this, using this tip:
Tip: If you want a custom dialog, you can instead display an Activity as a dialog instead of using the Dialog APIs. Simply create an activity and set its theme to Theme.Holo.Dialog in the manifest element:
<activity android:theme="#android:style/Theme.Holo.Dialog"
Based on this tip, I don't make PagerDialog extend Dialog but from Fragment. And then put this Fragment inside an Activity , set the theme of this activity as above in AndroidManifest.xml.
The updated code for the PagerDialog is as followed.
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentManager;
import android.support.v4.app.FragmentStatePagerAdapter;
import android.support.v4.view.ViewPager;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
public class PagerDialog extends Fragment {
ViewPager mViewPager;
FragmentStatePagerAdapter mAdapter;
#Override
public View onCreateView(LayoutInflater inflater,
#Nullable ViewGroup container, #Nullable Bundle savedInstanceState) {
View v = inflater.inflate(R.id.dialog, container, false);
mViewPager = (ViewPager) v.findViewById(R.id.pager);
mAdapter = new MyAdapter(getFragmentManager());
mViewPager.setAdapter(mAdapter);
return v;
}
private class MyAdapter extends FragmentStatePagerAdapter {
public MyAdapter(FragmentManager fm) {
super(fm);
}
#Override
public Fragment getItem(int index) {
return new DummyFragment();
}
#Override
public int getCount() {
return 2;
}
}
private class DummyFragment extends Fragment {
#Override
public View onCreateView(LayoutInflater inflater,
#Nullable ViewGroup container,
#Nullable Bundle savedInstanceState) {
View v = inflater.inflate(R.layout.fragment_dummy_layout,
container, false);
return v;
}
}
}
If you have any better solutions or you can find out why the original code in my question does not work, please teach me. I am a newbie in Android programing and I am happy to learn from you all.
Cheers.
I think you used
Dialog dialog = new Dialog(context);
Instends this.
1st Step: Used DialogFragment
public class MyCustomDialog extends DialogFragment {
Button mButton;
EditText mEditText;
List<MasterPageModel> listdata;
int position;
ViewPager viewpager;
public MyCustomDialog(List<MasterPageModel> listdata, int position) {
this.listdata = listdata;
this.position = position;
}
#Nullable
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
final View dialog = inflater.inflate(R.layout.dailoglayout, container);
final Dialog dailog = getDialog();
dailog.getWindow().setLayout(LinearLayout.LayoutParams.FILL_PARENT, LinearLayout.LayoutParams.MATCH_PARENT);
dailog.getWindow().requestFeature(Window.FEATURE_NO_TITLE);
dailog.getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
WindowManager.LayoutParams.FLAG_FULLSCREEN);
ImageView closebtn = (ImageView) dialog.findViewById(R.id.closeimgeview);
closebtn.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
dailog.dismiss();
}
});
viewpager = (ViewPager) dialog.findViewById(R.id.dailog_viewpager);
**viewpager.setAdapter(new PagerAdapter(getChildFragmentManager(), listdata));** //This Line is Very important
viewpager.setCurrentItem(position);
return dialog;
}
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setStyle(DialogFragment.STYLE_NORMAL, android.R.style.Theme_Black_NoTitleBar_Fullscreen); //For Full Screen of DailogBox
}
}
2nd Step :set The FragmentViewPager
public class PagerAdapter extends FragmentPagerAdapter {
private final List<MasterPageModel> pages;
public PagerAdapter(FragmentManager fm, List<MasterPageModel> pages) {
super(fm);
this.pages = pages;
}
#Override
public Fragment getItem(int position) {
return new ViewPagerFragment(pages.get(position));
}
#Override
public int getCount() {
return pages.size();
}
}
3rd Step : Fragment View For ViewPager:
public class ViewPagerFragment extends Fragment {
MasterPageModel masteDetailModel;
public ViewPagerFragment(MasterPageModel questionItem) {
this.masteDetailModel = questionItem;
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View v = inflater.inflate(R.layout.pagerlayout, container, false);
ImageView image = (ImageView) v.findViewById(R.id.pager_imageview);
Log.i("Image", "=>" + masteDetailModel.imagelarge);
Picasso.with(getActivity()).load(masteDetailModel.imagethumb).error(R.drawable.img).into(image);
return v;
}
4th How to Use this dialogfragment:
MyCustomDialog fragment1 = new MyCustomDialog(listdata, position);
EditionDetailActivity act = (EditionDetailActivity) context;
FragmentManager fm = act.getSupportFragmentManager();
fragment1.show(fm, "");
When I add a TextView to a LinearLayout, I'm generating NullPointerExceptions. I'm calling this...
public void loadPlayers() {
LinearLayout lv = (LinearLayout) findViewById(R.id.player_list);
TextView tv = new TextView(this);
for (int i = 0; i < Game.getPlayers().length; i++) {
tv.setText(String.valueOf(Game.getPlayers()[i]));
tv.setPadding(8, 8, 8, 8);
tv.setTextSize(20);
tv.setBackgroundColor(0xD0D0D0);
System.out.println("Got here!");
lv.addView(tv);
}
}
At the end of onCreate, and I'm getting "Got here!" printed on my console. The error is coming from
lv.addView(tv);
But I don't see why that is a problem. Is the layout not loaded yet? If so, how do I fix that? Below is the complete activity, xml, and logs.
MainActivity.java:
package com.example.lineupcreator;
import android.app.Activity;
import android.support.v7.app.ActionBarActivity;
import android.support.v7.app.ActionBar;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentManager;
import android.content.Context;
import android.os.Build;
import android.os.Bundle;
import android.view.Gravity;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.support.v4.widget.DrawerLayout;
import android.widget.ArrayAdapter;
import android.widget.EditText;
import android.widget.LinearLayout;
import android.widget.TextView;
public class MainActivity extends ActionBarActivity
implements NavigationDrawerFragment.NavigationDrawerCallbacks {
/* My Methods */
/**
* Adds a player, gets input from button
* #return
*/
public void addPlayer(View view) {
EditText editText = (EditText) findViewById(R.id.edit_message);
String name = editText.getText().toString();
LinearLayout lv = (LinearLayout) findViewById(R.id.player_list);
TextView tv = new TextView(this);
tv.setText(String.valueOf(name));
tv.setPadding(8, 8, 8, 8);
tv.setTextSize(20);
tv.setBackgroundColor(0xD0D0D0);
lv.addView(tv);// not InformationActivity.tv just write tv
Game.newPlayer(name);
}
/**
* Loads all of the players
*/
public void loadPlayers() {
LinearLayout lv = (LinearLayout) findViewById(R.id.player_list);
TextView tv = new TextView(this);
for (int i = 0; i < Game.getPlayers().length; i++) {
tv.setText(String.valueOf(Game.getPlayers()[i]));
tv.setPadding(8, 8, 8, 8);
tv.setTextSize(20);
tv.setBackgroundColor(0xD0D0D0);
System.out.println("Got here!");
lv.addView(tv);
}
}
/* Prebuilt Methods */
/**
* Fragment managing the behaviors, interactions and presentation of the navigation drawer.
*/
private NavigationDrawerFragment mNavigationDrawerFragment;
/**
* Used to store the last screen title. For use in {#link #restoreActionBar()}.
*/
private CharSequence mTitle;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mNavigationDrawerFragment = (NavigationDrawerFragment)
getSupportFragmentManager().findFragmentById(R.id.navigation_drawer);
mTitle = getTitle();
// Set up the drawer.
mNavigationDrawerFragment.setUp(
R.id.navigation_drawer,
(DrawerLayout) findViewById(R.id.drawer_layout));
/* My Code */
Game.init();
this.loadPlayers();
}
#Override
public void onNavigationDrawerItemSelected(int position) {
// update the main content by replacing fragments
FragmentManager fragmentManager = getSupportFragmentManager();
fragmentManager.beginTransaction()
.replace(R.id.container, PlaceholderFragment.newInstance(position + 1))
.commit();
}
public void onSectionAttached(int number) {
switch (number) {
case 1:
mTitle = getString(R.string.title_section1);
break;
case 2:
mTitle = getString(R.string.title_section2);
break;
case 3:
mTitle = getString(R.string.title_section3);
break;
}
}
public void restoreActionBar() {
ActionBar actionBar = getSupportActionBar();
actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_STANDARD);
actionBar.setDisplayShowTitleEnabled(true);
actionBar.setTitle(mTitle);
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
if (!mNavigationDrawerFragment.isDrawerOpen()) {
// Only show items in the action bar relevant to this screen
// if the drawer is not showing. Otherwise, let the drawer
// decide what to show in the action bar.
getMenuInflater().inflate(R.menu.main, menu);
restoreActionBar();
return true;
}
return super.onCreateOptionsMenu(menu);
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
// Handle action bar item clicks here. The action bar will
// automatically handle clicks on the Home/Up button, so long
// as you specify a parent activity in AndroidManifest.xml.
return super.onOptionsItemSelected(item);
}
/**
* A placeholder fragment containing a simple view.
*/
public static class PlaceholderFragment extends Fragment {
/**
* The fragment argument representing the section number for this
* fragment.
*/
private static final String ARG_SECTION_NUMBER = "section_number";
/**
* Returns a new instance of this fragment for the given section
* number.
*/
public static PlaceholderFragment newInstance(int sectionNumber) {
PlaceholderFragment fragment = new PlaceholderFragment();
Bundle args = new Bundle();
args.putInt(ARG_SECTION_NUMBER, sectionNumber);
fragment.setArguments(args);
return fragment;
}
public PlaceholderFragment() {
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.fragment_main, container, false);
return rootView;
}
#Override
public void onAttach(Activity activity) {
super.onAttach(activity);
((MainActivity) activity).onSectionAttached(
getArguments().getInt(ARG_SECTION_NUMBER));
}
}
}
fragment_main.xml:
<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="com.example.lineupcreator.MainActivity$PlaceholderFragment" >
<EditText android:id="#+id/edit_message"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_toLeftOf="#+id/button"
android:hint="#string/player_name" />
<Button
android:id="#+id/button"
android:layout_width="64dp"
android:layout_height="wrap_content"
android:layout_alignBottom="#+id/edit_message"
android:layout_alignParentRight="true"
android:onClick="addPlayer"
android:text="#string/add" />
<ScrollView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_below="#+id/edit_message" >
<LinearLayout
android:id="#+id/player_list"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="#android:color/darker_gray"
android:orientation="vertical" />
</ScrollView>
</RelativeLayout>
Logs:
07-24 17:30:48.274: D/ActivityThread(22173): handleBindApplication:com.example.lineupcreator
07-24 17:30:48.274: D/ActivityThread(22173): setTargetHeapUtilization:0.75
07-24 17:30:48.274: D/ActivityThread(22173): setTargetHeapMinFree:2097152
07-24 17:30:48.548: I/System.out(22173): Got here!
07-24 17:30:48.548: D/AndroidRuntime(22173): Shutting down VM
07-24 17:30:48.548: W/dalvikvm(22173): threadid=1: thread exiting with uncaught exception (group=0x418f1ce0)
07-24 17:30:48.555: E/AndroidRuntime(22173): FATAL EXCEPTION: main
07-24 17:30:48.555: E/AndroidRuntime(22173): Process: com.example.lineupcreator, PID: 22173
07-24 17:30:48.555: E/AndroidRuntime(22173): java.lang.RuntimeException: Unable to start activity ComponentInfo{com.example.lineupcreator/com.example.lineupcreator.MainActivity}: java.lang.NullPointerException
07-24 17:30:48.555: E/AndroidRuntime(22173): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2215)
07-24 17:30:48.555: E/AndroidRuntime(22173): at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2265)
07-24 17:30:48.555: E/AndroidRuntime(22173): at android.app.ActivityThread.access$800(ActivityThread.java:145)
07-24 17:30:48.555: E/AndroidRuntime(22173): at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1206)
07-24 17:30:48.555: E/AndroidRuntime(22173): at android.os.Handler.dispatchMessage(Handler.java:102)
07-24 17:30:48.555: E/AndroidRuntime(22173): at android.os.Looper.loop(Looper.java:136)
07-24 17:30:48.555: E/AndroidRuntime(22173): at android.app.ActivityThread.main(ActivityThread.java:5144)
07-24 17:30:48.555: E/AndroidRuntime(22173): at java.lang.reflect.Method.invokeNative(Native Method)
07-24 17:30:48.555: E/AndroidRuntime(22173): at java.lang.reflect.Method.invoke(Method.java:515)
07-24 17:30:48.555: E/AndroidRuntime(22173): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:795)
07-24 17:30:48.555: E/AndroidRuntime(22173): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:611)
07-24 17:30:48.555: E/AndroidRuntime(22173): at dalvik.system.NativeStart.main(Native Method)
07-24 17:30:48.555: E/AndroidRuntime(22173): Caused by: java.lang.NullPointerException
07-24 17:30:48.555: E/AndroidRuntime(22173): at com.example.lineupcreator.MainActivity.loadPlayers(MainActivity.java:64)
07-24 17:30:48.555: E/AndroidRuntime(22173): at com.example.lineupcreator.MainActivity.onCreate(MainActivity.java:96)
07-24 17:30:48.555: E/AndroidRuntime(22173): at android.app.Activity.performCreate(Activity.java:5231)
07-24 17:30:48.555: E/AndroidRuntime(22173): at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1087)
07-24 17:30:48.555: E/AndroidRuntime(22173): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2169)
07-24 17:30:48.555: E/AndroidRuntime(22173): ... 11 more
07-24 17:35:48.735: I/Process(22173): Sending signal. PID: 22173 SIG: 9
EDIT:
It seemed to me that quaternion was on the right path, but his solution didn't work. I also tried to creating an array of TextViews, as seen below, but that also didn't work.
public void loadPlayers() {
LinearLayout lv = (LinearLayout) findViewById(R.id.player_list);
TextView[] tv = new TextView[Game.getPlayers().length];
for (int i = 0; i < Game.getPlayers().length; i++) {
tv[i] = new TextView(this);
tv[i].setText(String.valueOf(Game.getPlayers()[i]));
tv[i].setPadding(8, 8, 8, 8);
tv[i].setTextSize(20);
tv[i].setBackgroundColor(0xD0D0D0);
System.out.println("Got here!");
lv.addView(tv[i]);
}
}
Update:
I tried calling loadPlayers from addPlayer and not onCreate, and it works perfectly. The only problem is created when loadPlayers is called from onCreate
Caused by: java.lang.NullPointerException
at com.example.lineupcreator.MainActivity.loadPlayers(MainActivity.java:64)
The reason why you're getting NullPointerException is because you're trying to get a LinearLayout which is inflated in Fragment, from the Activity, specifically these lines:
public void loadPlayers() {
LinearLayout lv = (LinearLayout) findViewById(R.id.player_list);
// R.id.player_list is not inside activity_main.xml
// lv is null
...
lv.addView(tv[i]); // NullPointerException
}
}
One way to solve this is to move all the logic inside the Fragment.
Add onActivityCreated(Bundle savedInstanceState) inside the PlaceholderFragment and move both lines from onCreate() to there. This is to ensure that the code will be called after the activity is already set-up.
#Override
public void onActivityCreated (Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
/* My Code */
Game.init();
this.loadPlayers();
}
Then move loadPlayers() inside the PlaceholderFragment. However, there is no findViewById() inside a Fragment. Instead, you have to initialize the views inside onCreateView(). Don't forget to declare the variables inside the Fragment.
LinearLayout lv;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.fragment_main, container, false);
lv = (LinearLayout) rootView.findViewById(R.id.player_list);
return rootView;
}
Lastly, Fragment use Context from its Activity. While you can use this in Activity to refer to its Context, in Fragment you cannot. Instead, use getActivity().
public void loadPlayers() {
// LinearLayout lv = (LinearLayout) findViewById(R.id.player_list);
TextView tv;
for (int i = 0; i < Game.getPlayers().length; i++) {
tv = new TextView(getActivity());
tv.setText(String.valueOf(Game.getPlayers()[i].getName()));
tv.setPadding(8, 8, 8, 8);
tv.setTextSize(20);
tv.setBackgroundColor(0xD0D0D0);
lv.addView(tv);
}
}
Ok, the Error is that you are trying inflate a layout component from the main activity, but your are inflating a Fragment, so, your main layout is not showing in your screen, is the fragment layout that is the top. You need move
<LinearLayout
android:id="#+id/player_list"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="#android:color/darker_gray"
android:orientation="vertical" />
to Fragment Layout.
If this donsn't work just tell me.
I don't think you can add the same view to a parent multiple times. You will need to move you instantiation of the new TextView into the for loop.
Your loadPlayers function should look like this:
public void loadPlayers() {
LinearLayout lv = (LinearLayout) findViewById(R.id.player_list);
for (int i = 0; i < Game.getPlayers().length; i++) {
TextView tv = new TextView(this);
tv.setText(String.valueOf(Game.getPlayers()[i]));
tv.setPadding(8, 8, 8, 8);
tv.setTextSize(20);
tv.setBackgroundColor(0xD0D0D0);
System.out.println("Got here!");
lv.addView(tv);
}
}
Hope this helps, if not you may have a bigger issue at hand =(
Closed. This question is not reproducible or was caused by typos. It is not currently accepting answers.
This question was caused by a typo or a problem that can no longer be reproduced. While similar questions may be on-topic here, this one was resolved in a way less likely to help future readers.
Closed 8 years ago.
Improve this question
So I added a <WebView> to the standard navigation drawer template and added some code to the java file. However, now the app keeps on crashing. The error it throws in the console is Error inflating class fragment
It does compile though. So how can I fix this? Should I add the <WebView> somewhere else?
activity_login.xml
<android.support.v4.widget.DrawerLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="#+id/drawer_layout"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".login">
<WebView xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/main_webview"
android:layout_width="match_parent"
android:layout_height="match_parent" />
<fragment android:id="#+id/navigation_drawer"
android:layout_width="#dimen/navigation_drawer_width"
android:layout_height="match_parent"
android:layout_gravity="start"
android:name="test.vwebviewdrawer.NavigationDrawerFragment"
tools:layout="#layout/fragment_navigation_drawer" />
</android.support.v4.widget.DrawerLayout>
main.java
package test.webviewdrawer;
import android.support.v4.app.FragmentActivity;
import android.support.v7.app.ActionBarActivity;
import android.support.v7.app.ActionBar;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentManager;
import android.support.v4.widget.DrawerLayout;
import android.view.View.OnClickListener;
//...
public class login extends ActionBarActivity
implements NavigationDrawerFragment.NavigationDrawerCallbacks {
private NavigationDrawerFragment mNavigationDrawerFragment;
private CharSequence mTitle;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_login);
mNavigationDrawerFragment = (NavigationDrawerFragment)
getSupportFragmentManager().findFragmentById(R.id.navigation_drawer);
mTitle = getTitle();
// Set up the drawer.
mNavigationDrawerFragment.setUp(
R.id.navigation_drawer,
(DrawerLayout) findViewById(R.id.drawer_layout));
}
#Override
public void onNavigationDrawerItemSelected(int position) {
WebView myWebView = (WebView) findViewById(R.id.main_webview);
String pageUrl = "http://www.google.com";
myWebView.loadUrl(pageUrl);
}
public void onSectionAttached(int number) {
switch (number) {
case 1:
mTitle = getString(R.string.title_section1);
break;
case 2:
mTitle = getString(R.string.title_section2);
break;
case 3:
mTitle = getString(R.string.title_section3);
break;
case 4:
mTitle = getString(R.string.title_section4);
break;
}
}
public void restoreActionBar() {
ActionBar actionBar = getSupportActionBar();
actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_STANDARD);
actionBar.setDisplayShowTitleEnabled(true);
actionBar.setTitle(mTitle);
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
if (!mNavigationDrawerFragment.isDrawerOpen()) {
getMenuInflater().inflate(R.menu.login, menu);
restoreActionBar();
return true;
}
return super.onCreateOptionsMenu(menu);
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
int id = item.getItemId();
if (id == R.id.action_settings) {
return true;
}
return super.onOptionsItemSelected(item);
}
public static class PlaceholderFragment extends Fragment {
private static final String ARG_SECTION_NUMBER = "section_number";
public static PlaceholderFragment newInstance(int sectionNumber) {
PlaceholderFragment fragment = new PlaceholderFragment();
Bundle args = new Bundle();
args.putInt(ARG_SECTION_NUMBER, sectionNumber);
fragment.setArguments(args);
return fragment;
}
public PlaceholderFragment() {
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.fragment_login, container, false);
return rootView;
}
#Override
public void onAttach(Activity activity) {
super.onAttach(activity);
((login) activity).onSectionAttached(
getArguments().getInt(ARG_SECTION_NUMBER));
}
}
}
UPDATE:
I added the error message as requested in the comment section.
06-21 19:42:52.109 17625-17625/test.webviewdrawer E/AndroidRuntime﹕ FATAL EXCEPTION: main
Process: test.webviewdrawer, PID: 17625
java.lang.RuntimeException: Unable to start activity ComponentInfo{test.webviewdrawer/test.webviewdrawer.login}: android.view.InflateException: Binary XML file line #28: Error inflating class fragment
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2596)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2653)
at android.app.ActivityThread.access$800(ActivityThread.java:156)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1355)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:157)
at android.app.ActivityThread.main(ActivityThread.java:5872)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:515)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:852)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:668)
at dalvik.system.NativeStart.main(Native Method)
Caused by: android.view.InflateException: Binary XML file line #28: Error inflating class fragment
at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:713)
at android.view.LayoutInflater.rInflate(LayoutInflater.java:755)
at android.view.LayoutInflater.inflate(LayoutInflater.java:492)
at android.view.LayoutInflater.inflate(LayoutInflater.java:397)
at android.view.LayoutInflater.inflate(LayoutInflater.java:353)
at com.android.internal.policy.impl.PhoneWindow.setContentView(PhoneWindow.java:375)
at android.app.Activity.setContentView(Activity.java:1997)
at android.support.v7.app.ActionBarActivity.superSetContentView(ActionBarActivity.java:216)
at android.support.v7.app.ActionBarActivityDelegateICS.setContentView(ActionBarActivityDelegateICS.java:110)
at android.support.v7.app.ActionBarActivity.setContentView(ActionBarActivity.java:76)
at test.webviewdrawer.login.onCreate(login.java:46)
at android.app.Activity.performCreate(Activity.java:5312)
at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1111)
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2552)
There's a typo in your XML layout, at this line:
android:name="test.vwebviewdrawer.NavigationDrawerFragment"
It should be:
android:name="test.webviewdrawer.NavigationDrawerFragment"
instead :-)