Let's consider this situation. We are building an app using Mortar and Flow to simplify things and then all of the sudden we see that we can use some of the old fragments. This fragments are a little bit complex so we would like to somehow inject them to our Views.
Would that be possible if we have our Mortar View like this:
<?xml version="1.0" encoding="utf-8"?>
<com.foo.myMortarView xmlns:android="http://schemas.android.com/apk/res/android"
android:id="+id/mortar_view"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:baselineAligned="false"
android:orientation="horizontal" >
<fragment
android:id="#+id/myFragment"
android:layout_width="0dp"
android:layout_weight="2"
android:layout_height="match_parent"
class="com.example.MyFragment" >
</fragment>
</com.foo.myMortarView>
And our Fragment like this:
public class MyFragment extends Fragment{
#Override
public View onCreateView(LayoutInflater inflater,
ViewGroup container, Bundle savedInstanceState) {
/**
* Inflate the layout for this fragment
*/
return inflater.inflate(
R.layout.my_fragment, container, false);
}
}
This of course doesn't work out of the box so how can we accomplish that? Thanks!
Related
I am starting to learn how to develop android apps, more precisely I in trying to make an activity which host a single fragment (that extends DialogFragment) which in turn host a DatePicker Widget. I would like that DatePicker fill all screen width.
The problem is that for an unknown reason it puts a margin in the right of the screen (I want to get rid of the blank space).
This is what i get:
This is DatePicker layout:
<DatePicker
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/dialog_date_date_picker"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:calendarViewShown="false"/>
This is the activity's layout that host the fragment:
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/fragment_container"
android:layout_width="match_parent"
android:layout_height="match_parent"
/>
And this is the fragment code:
public class DatePickerFragment extends DialogFragment {
#Nullable
#Override
public View onCreateView(LayoutInflater inflater, #Nullable ViewGroup container, #Nullable Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.dialog_date, container, false);
return view;
}
}
Notice that I don't want to use 'onCreateDialog', in this particular case I want to use 'onCreateView'.
I have the following Layout with static fragment and RelativeLayout as parent:
<?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"
android:padding="#dimen/activity_vertical_margin">
<fragment
android:id="#+id/list_fragment"
android:name="com.listfragmenttest.MyListFragment"
android:layout_width="match_parent"
android:layout_height="match_parent"/>
</RelativeLayout>
Yet the container or parent comes up null in OnCreateView:
public class MyListFragment extends ListFragment {
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
return inflater.inflate(R.layout.my_list_fragment, container, false);
}
}
Is this the normal behavior for Static fragment?
Yes, that's how it is implemented. Fragments inflated statically from XML get a null as parent container.
For details, consult FragmentManager source. In particular, onCreateView() that handles fragment instantiation from layout inflation, setting mInLayout = true and calls to performCreateView() that are conditional on mInLayout.
I have a Fragment in my MainActivity, that displays a Digital Clock. It works: It shows the current system time. But it looks rather simple. So before I start trying to style this clock I wanted to ask, if there is a way, to use the systems Digital-Clock Widget?
Screenshot of the widget, that I'd like to use in my Fragment:
FragmentClock.java:
public class FragmentClock extends Fragment {
#Override
public View onCreateView(LayoutInflater inflater,
ViewGroup container, Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
View view = inflater.inflate(R.layout.fragment_clock, container, false);
return view;
}
}
fragment_clock.xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/LinearLayoutClockDisplay"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:background="#000000">
<DigitalClock
android:id="#+id/digital_clock"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:visibility="visible"/>
</LinearLayout>
I'm trying to put 2 fragments inside a fragment. I found some code on internet but, as far as I could go, I don't succeed to put 2 fragments in 1 fragment.
I have seen tips dealing with FragmentManager and especially the method getChildFragmentManager() but I don't know how it works with 2 fragments.
For the story, I'm using an activity with ActionBar which creates 3 fragments. In one of them, I need to handle a graph and a kind of menu to change the graph scale. In this way, I need 2 fragments in one fragment.
Here is the code :
The fragment which handles the others:
public class GraphDisplayFragment extends Fragment {
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View myFragmentView = inflater.inflate(R.layout.graph_fragment, container, false);
return myFragmentView;
}
}
The code to draw the graph:
public class GraphFragment extends Fragment {
private static final int SERIES_NR = 1;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
GraphicalView myFragmentView = ChartFactory.getTimeChartView(this.getActivity(), getDateDemoDataset(), getDemoRenderer(),null);
return myFragmentView;
}
//some functions to set graph propreties
}
The XML files :
graph_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:orientation="vertical" >
<fragment
android:id="#+id/graph_fragment"
android:name="com.test.GraphFragment"
android:layout_width="match_parent"
android:layout_height="259dp" >
</fragment>
<fragment
android:name="com.test.GraphDetailFragment"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/graph_detail_fragment">
</fragment>
</LinearLayout>
graph_detail.xml with a test implementation
<?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" >
<TextView
android:id="#+id/textView1"
android:layout_width="211dp"
android:layout_height="wrap_content"
android:text="TextView" />
</LinearLayout>
The weird thing is, it works at the begining when I switch between fragments in the ActionBar but after 3-4 moves, I get this error :
android.view.InflateException: Binary XML file line #7: Error inflating class fragment
If anyone has the solution, it would be awesome!
So first off change your xml for graph_fragment.xml to this
<?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" >
<FrameLayout
android:id="#+id/graph_fragment_holder"
android:layout_width="match_parent"
android:layout_height="259dp" >
</FrameLayout>
<FrameLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/graph_detail_fragment_holder">
</FrameLayout>
</LinearLayout>
Then in code to inflate them from the fragment use something like this
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.graph_fragment,
container, false);
FirstChildFragment frag1 = (FirstChildFragment) getChildFragmentManager()
.findFragmentById(R.id.first_frag_layout);
SecondChildFragment frag1 = (SecondChildFragment) getChildFragmentManager()
.findFragmentById(R.id.second_frag_layout);
if (null == frag1) {
FirstChildFragment = new frag1();
FragmentTransaction transaction = getChildFragmentManager()
.beginTransaction();
transaction.add(R.id.graph_fragment_holder, frag1)
.addToBackStack(null).commit();
}
if (null == frag2) {
SecondChildFragment = new frag2();
FragmentTransaction transaction = getChildFragmentManager()
.beginTransaction();
transaction.add(R.id.graph_detail_fragment_holder, frag2)
.addToBackStack(null).commit();
}
return rootView;
}
MyFragment myFragment = (MyFragment)getChildFragmentManager().findFragmentById(R.id.my_fragment);
You can try to use the method *findFragmentById(fragment_id)* from SupportFragmentManager to get the instance of fragment from your .xml file and insert your fragment there.
Something like:
Fragment myFragment = getSupportFragmentManager().findFragmentById(R.id.myFragmentId);
I hope to help you.
Best regards.
Adriano
Is is possible to use the android dashboard pattern from Google I/O as a fragment so that in landscape mode on a tablet the dashboard is shown on the left while the content of the current category is shown on the right?
I've tried something that looks like the code below but it doesnt work.
main.xml:
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent">
<!-- Include dashboard -->
<include layout="#layout/fragment_dashboard"/>
<!-- Include details -->
<fragment
android:id="#+id/fragment_details"
android:layout_width="match_parent"
android:layout_height="match_parent"
class="com.example.fragments.Details" />
</LinearLayout>
Details.java:
public class Details extends Fragment
{
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState)
{
View view = inflater.inflate(R.layout.details, container, false);
return view;
}
}