android fragment running in the background - android-fragments

i have the following chain of call
in a fragment i call zxing integrator to scan qr code which returns the result in
onActivityResult(int requestCode,int resultCode,Intent data)
of the fragment
The onActivityResult calls an Asynctask,
new getStaffIdTask(choosen_schema_for_scanning,userid).execute((Void)null);
whose onPostExecute(final Boolean success) calls the fragments listener as..
if(mListener!=null)
mListener.onScannedStaff(tableName,Integer.parseInt(id),Integer.parseInt(userid));
Back on the host activity the onScannedStaff function is called and in it replaces a fragment
#Override
public void onScannedStaff(String tableName, int staffid,int staffUid)
{
getSupportActionBar().setTitle("Staff Profile");
Fragment fragment= StaffProfileFragment.newInstance(tableName,staffid,staffUid);
FragmentTransaction transaction=getSupportFragmentManager().beginTransaction();
transaction.replace(R.id.home_boss_base,fragment,"scannedstaff");
transaction.addToBackStack(null);
transaction.commit();
}
The problem is that this fragment runs in the background and its not showing any UI at all. I cant figure out how to show it

I have also faced the same issue. Use LinearLayout in the fragment. Background color should be white and it should be clickable.
And don't call UI element from OnPostExecute().that will give you some major memory leaks or errors.

Related

Custom ListPreference in AndroidX

I have customized my Android Application Setting page, I use API 21 or 26. I have added a CustomListPreference java class which was inherited from ListPreference and integrated it into the SettingActivity.
But, I relisted the system doesn't work, as SettingActivity has Setting fragment inherited from androidx.preference.PreferenceFragmentCompat and packages used for the Setting Activity are as follows:
androidx.preference.Preference
androidx.preference.ListPreference
androidx.preference.PreferenceFragmentCompat
If I use packages android.preference.Preference and android.preference.ListPreference for my Custom ListPreference, all my code stops working when Android creates objects for the Setting Activity. It crashes just after the custom ListPreference constructorwith error "Error inflating class com.signatact.doorbell.dialog.preference.AppListPreference".
Digging into details I found the reason of the crash as the last step for new object creation for Setting Activity is the cast to androidx.preference.Preference:
from PreferenceInflater.java:
import androidx.preference;
...
return (Preference) constructor.newInstance(args); // line 242
It is clear, the system fails with cast between android.preference.Preference and androidx.preference.Preference.
However, if I move my custom ListPreference file implementation to androidx, almost all method I used before for customization are not available, hereby is a list of methods which are not available, where I put my custom logic:
// Error(s): Methods don't override methods from its superclass
#Override
protected void onPrepareDialogBuilder(AlertDialog.Builder builder)
...
#Override
protected void onDialogClosed(boolean positiveResult)
It looks like Google dramatically changed their API, can anybody give idea how in AndroidX one can customize ListPreference?
In general, I need standard customization things as follows:
In a row I have a custom set of controls (3 ones - 2x text boxes and 1 checkbox) - I build a custom layout for each row in onPrepareDialogBuilder with my custom ArrayAdapter for the list
I need dynamically update the CustomListPreference values. I populate those values in onResume in SettingActivity
I need to get callback when the list is pressed and new value is selected
I found only one practical guidance here for my case which is as follows: How can I change the appearance of ListPreference Dialog but it is limited and short. I analysed the AndroidX API and it looks like I need more time to come out with a solution and thus any help / idea appreciated...
Thx, Vlad.
Simply override onClick() function to pop out an AlertDialog with custom layout. Remember to call setValue() when anything selected in the dialog.
public class ColorPreference extends ListPreference {
private CharSequence[] mEntries;
private CharSequence[] mEntryValues;
private String mValue;
private String mSummary;
private AlertDialog mDialog;
public ColorPreference(Context context) {
this(context, null);
}
public ColorPreference(Context context, AttributeSet attrs) {
super(context, attrs);
setDefaultValue(Options.DEFAULT_PRIMARY_COLOR_STRING);
}
#Override
protected void onClick() {
mEntries = getEntries();
mEntryValues = getEntryValues();
mSummary = getSummary().toString();
mValue = getValue();
mClickedDialogEntryIndex = findIndexOfValue(mValue);
AlertDialog.Builder builder = new AlertDialog.Builder(getContext());
builder.setSingleChoiceItems(new ColorAdapter(getContext(), R.layout.pref_color_item),mClickedDialogEntryIndex,null);
mDialog = builder.create();
mDialog.show();
}
}

In Kotlin ..How I can return from fragment to MainActivity

in my program I have MainActivity and many fragments..
I try the following code to return from fragment to MainActivity by
onBackpressed() method
override fun onBackPressed() {
if(drawer_layout.isDrawerOpen(GravityCompat.START)) {
drawer_layout.closeDrawer(GravityCompat.START)
}
else if (fragment != null) {
val intent = Intent(applicationContext, MainActivity::class.java)
intent.flags = Intent.FLAG_ACTIVITY_CLEAR_TOP
startActivity(intent)
}
else {
super.onBackPressed()
}
}
My first problem is:
it working good with Drawer and also open MainActivity
but program not closed ..these main that
super.onBackPressed()
not working ..why
My second problem is:
after else If I need to use
getActivity().onBackpressed()
instead of the old one..
Thanks All
Activities navigate to Activities via onBackPressed(). Fragments have to reside in an Activity (They are basically sub-Activities), so it doesn't make sense to navigate from a Fragment to an Activity via super.onBackPressed(). You should be navigating from Fragment to Fragment, or if you forgo Fragments then Activity to Activity.
To navigate back to the previous Fragment:
activity?.fragmentManager?.popBackStack()
To navigate to the previous activity:
activity?.finish()
or
onBackPressed()
or, from the activity if you have overriden the onBackPressed() method:
super.onBackPressed()
Without more context to your code I can't say either why it seems your final else statement is never called. It seems like you've got a bug with your if else statement as super.onBackPressed() would provide the desired result of closing whatever activity you were in (MainActivity?).
else if (fragment != null) {
val intent = Intent(applicationContext, MainActivity::class.java)
intent.flags = Intent.FLAG_ACTIVITY_CLEAR_TOP
startActivity(intent)
}
My guess is it has something to do with you creating another instance of MainActivity. On first back pressed you close the drawer. On the second you create another instance of MainActivity and navigate to it. On the third, even if super.onBackPressed() gets called it will navigate back to the first instance of MainActivity where fragment will probably never be null unless you're specifically assigning such, so on the fourth you create another instance of MainActivity and navigate to it. This is a loop that will never navigate back from the first MainActivity.
Suggestions: However you're displaying MainActivity, convert it to a Fragment and handle it accordingly. Another approach is instead of creating another instance of MainActivity hide the fragmentView and show the MainActivity view. I don't suggest setting your fragment to null as the fragmentManager may throw and error, so you should also change your if else logic to check for something else. Say maybe fragment.view.visibility == View.Visible if you go the route described.
For your first question as far as I can understand you should use
val activity = activity as MainActivity
activity.onBackPressed()
because super for your fragment is not MainActivity.
The easiest and most concise way (Kotlin):
requireActivity().addOnBackPressedCallback(viewLifecycleOwner,
OnbackPressedCallback{
startMainActivity() // Your action here...
true
}
)

Unity - GameObject.Find() works only on server

I am making a simple networking game. The scene has a button named 'ReloadButton' and i am trying to find this button and add a listener to it through my script attached on the player.
private Button reloadBtn;
void Start()
{
GameObject tempGO = GameObject.Find("ReloadButton");
if (tempGO != null)
{
reloadBtn = tempGO.GetComponent<Button>();
reloadBtn.onClick.AddListener(weaponManager.Reload);
}
}
I am doing it this way because direct referencing of 'ReloadButton' to the script through public Buttonvariable is not possible.
The code works fine on the server, the listener is also added correctly. but on the client, the GameObject.Find("ReloadButton") throws a NullReferenceException.
Seems like the client cannot find the Button itself.
I cannot proceed further in my project without solving this problem, I hope some of you can point me towards the problem.

RequestCode changes along the way

I have a fragment within a fragment
both fragments load fine, except in one of the fragments i have a start camera intent with activity for result
if (photoFile != null) {
takePictureIntent.putExtra(MediaStore.EXTRA_OUTPUT,
Uri.fromFile(photoFile));
startActivityForResult(takePictureIntent, REQ_TAKE_PHOTO);
}
now my REQ_TAKE_PHOTO is defined as follows :
public static final int REQ_TAKE_PHOTO=301;
however, in my onActivityResult the request code i get when returning from the camera intent is
131373 -> not the code i sent the request with
what could be changing the code along the way ?
note that when the inner fragment (the one that is incharge of taking the picture) is run separately, the code returns as 301 normally
to make the requestCode be what it was when i started the startActivityForResult
I need to do requestCode&0xffff
This is apparently a bug in the android support library
according to this: https://code.google.com/p/android/issues/detail?id=15394

How to deal with FragmentPagerAdapter reusing Fragments?

So, I'm trying to use a ViewPager from Android's support v4 library, but there's some serious issues with how it (or FragmentPagerAdapter) deals with Fragments. For instance, I subclassed FragmentPagerAdapter to do the following:
public class MyPagerAdapter extends FragmentPagerAdapter
{
private ArrayList<Fragment> fragments = null;
private ArrayList<Data> data = null;
public MyPagerAdapter(FragmentManager fragmentManager, ArrayList<Data> data)
{
super(fragmentManager);
this.data = data;
fragments = new ArrayList<Fragment>();
for(Data datum : data)
{
MyDataFragment fragment = new MyDataFragment();
fragment.setData(datum);
fragments.add(fragment);
}
}
#Override
public Fragment getItem(int i)
{
return fragments.get(i);
}
#Override
public int getCount()
{
return fragments.size();
}
}
Now, I thought this would be sufficient, and that I could go on and implement MyDataFragment using the onCreateView method that Fragments typically implement. But I ran into an interesting problem. When I would navigate away from the Activity, and then back to it, the ViewPager would appear blank. Somehow, it was reusing Fragments by calling findFragmentByTag, then simply not even calling getItem, etc. What's worse, the Fragment would get no onCreateView event. So I figured I could utilize the ViewPager's Fragment caching by moving my onCreateView code, which primarily grabs references to the various Views the fragment inflates, to onAttach. The only problem is, that during onAttach, MyDataFragment's getView method always returns null. All of the examples for Fragments online describe that onCreateView should have all of your view setup code. Ok, fine. But then, when I create a method like MyDataFragment.setSomeField(String value), I need to use a reference to a TextView. Since onCreateView doesn't always get called (like, when Fragments are magically recycled by FragmentPagerAdapter, for instance), it's better to grab that reference in onAttach. However, during onAttach, the root view for the Fragment is still null (probably because onCreateView wasn't called in the first place)! No additional events happen after that (with the exception of onActivityCreated, which has nothing to do with the Fragment itself), so there's no place to do setup code. How is this supposed to work? Am I missing something important here, or was the Fragment system designed by a monkey?
I'm not sure that this is the right use case for a FragmentPagerAdapter (it sounds more like something you'd want to do with a ListAdapter).
From the FragmentPagerAdapter docs:
Implementation of PagerAdapter that represents each page as a Fragment
that is persistently kept in the fragment manager as long as the user
can return to the page.
This version of the pager is best for use when there are a handful of
typically more static fragments to be paged through, such as a set of
tabs. The fragment of each page the user visits will be kept in
memory, though its view hierarchy may be destroyed when not visible.
This can result in using a significant amount of memory since fragment
instances can hold on to an arbitrary amount of state. For larger sets
of pages, consider FragmentStatePagerAdapter.
I'd consider switching to the FragmentStatePagerAdapter or perhaps a ListAdapter.
If you want the createView to be called it will have to be recreated each time (destroy the old fragment and create new ones), but again I don't think that's quite what you want.

Resources