I am trying to use RxAndroid to do the same work which is AsyncTask exactly does. I coded a simple example, where I enter a n integer in an edittext and when I press
a button, I make the hread to sleep for 3 seconds using "SystemClock.sleep" and while the thread is sleeping I show a progressbar and when the three seconds
elapsed the progresssbar will adisappear and the value entered in the edittext will be multiplied by 10 and displayed in atextview.
normally, when I use AsyncTask, I show the progressbar in onPreExecute and make it to disappear in onPostExecute. but when I run the below code I receive the
following error:
Only the original thread that created a view hierarchy can touch its views.
how to handle it properly in RxAndroid?
code:
public class MainActivity extends AppCompatActivity {
private static final String TAG = MainActivity.class.getSimpleName();
private EditText mEditTextValueToProcess = null;
private Button mButtonGoAsynchronous = null;
private TextView mTextViewProcessedValue = null;
private ProgressBar mProgressBar = null;
private rx.Observable<String> mAsyncObservable = null;
Subscriber mAsyncSubscriber = new Subscriber<String>() {
#Override
public void onCompleted() {
Log.w(TAG, "onCompleted");
mProgressBar.setVisibility(View.GONE);
}
#Override
public void onError(Throwable e) {
Log.w(TAG, "onError: " + e.getMessage().toString());
mProgressBar.setVisibility(View.GONE);
}
#Override
public void onNext(String o) {
Log.w(TAG, "onNext:->after processing " + o);
mTextViewProcessedValue.setText(o);
}
};
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
intiViews();
mAsyncObservable = rx.Observable.create(new rx.Observable.OnSubscribe<String>() {
#Override
public void call(Subscriber<? super String> subscriber) {
mProgressBar = (ProgressBar) findViewById(R.id.progressDialog);
mProgressBar.setVisibility(View.VISIBLE);
SystemClock.sleep(3000);
subscriber.onNext("" + Integer.valueOf(mEditTextValueToProcess.getText().toString()) * 10);
subscriber.onCompleted();
}
});
}
private void intiViews() {
mEditTextValueToProcess = (EditText) findViewById(R.id.edittext);
mButtonGoAsynchronous = (Button) findViewById(R.id.button_go_asynchronous);
mTextViewProcessedValue = (TextView) findViewById(R.id.textview_processed_value);
//mProgressBar = (ProgressBar) findViewById(R.id.progressDialog);
mButtonGoAsynchronous.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
mAsyncObservable.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(mAsyncSubscriber);
}
});
}
}
Have you tried
private Observable<String> createObservable(final int number) {
return rx.Observable.create(new rx.Observable.OnSubscribe<String>() {
#Override
public void call(Subscriber<? super String> subscriber) {
SystemClock.sleep(3000);
subscriber.onNext("" + number * 10);
subscriber.onCompleted();
}
});
}
private void intiViews() {
mEditTextValueToProcess = (EditText) findViewById(R.id.edittext);
mButtonGoAsynchronous = (Button) findViewById(R.id.button_go_asynchronous);
mTextViewProcessedValue = (TextView) findViewById(R.id.textview_processed_value);
mProgressBar = (ProgressBar) findViewById(R.id.progressDialog);
mButtonGoAsynchronous.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
mProgressBar.setVisibility(View.VISIBLE);
createObservable(Integer.valueOf(mEditTextValueToProcess.getText().toString()))
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.doOnNext((ignored) -> {
mProgressBar.setVisibility(View.GONE);
})
.subscribe(mAsyncSubscriber);
}
});
}
?
You need to change few things to achieve this. Look at mAsyncSubscriber initialization, onStart() method & progressBar initialization. The reason why you are getting the error is you are initializing & making your progressbar visible in another thread then your UI thread (because you specified this -> subscribeOn(Schedulers.io()).
public class MainActivity extends AppCompatActivity {
private static final String TAG = MainActivity.class.getSimpleName();
private EditText mEditTextValueToProcess = null;
private Button mButtonGoAsynchronous = null;
private TextView mTextViewProcessedValue = null;
private ProgressBar mProgressBar = null;
private rx.Observable<String> mAsyncObservable = null;
Subscriber mAsyncSubscriber;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
intiViews();
mAsyncSubscriber = new Subscriber<String>() {
// Override onStart method
#Override
public void onStart() {
mProgressBar.setVisibility(View.VISIBLE);
}
#Override
public void onCompleted() {
Log.w(TAG, "onCompleted");
mProgressBar.setVisibility(View.GONE);
}
#Override
public void onError(Throwable e) {
Log.w(TAG, "onError: " + e.getMessage().toString());
mProgressBar.setVisibility(View.GONE);
}
#Override
public void onNext(String o) {
Log.w(TAG, "onNext:->after processing " + o);
mTextViewProcessedValue.setText(o);
}
};
mAsyncObservable = rx.Observable.create(new rx.Observable.OnSubscribe<String>() {
#Override
public void call(Subscriber<? super String> subscriber) {
SystemClock.sleep(3000);
subscriber.onNext("" + Integer.valueOf(mEditTextValueToProcess.getText().toString()) * 10);
subscriber.onCompleted();
}
});
}
private void intiViews() {
// Init your progressbar
mProgressBar = (ProgressBar) findViewById(R.id.progressDialog);
mEditTextValueToProcess = (EditText) findViewById(R.id.edittext);
mButtonGoAsynchronous = (Button) findViewById(R.id.button_go_asynchronous);
mTextViewProcessedValue = (TextView) findViewById(R.id.textview_processed_value);
//mProgressBar = (ProgressBar) findViewById(R.id.progressDialog);
mButtonGoAsynchronous.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
mAsyncObservable.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(mAsyncSubscriber);
}
});
}
Related
My app has a post layout which have an edit button and the send button. All i want to do is to show only edit button if current user is viewing his/her post and not the send button. Just like a stackoverflow post, you can't edit other's post and can't send a message to yourself. I have tried boolean methods but still no solution. Thanks.
Activity that have showButtonsForCurrentUser() method ;
public class ViewPostActivity extends AppCompatActivity {
private static final String TAG = "ViewPostActivity";
//widgets
private TextView mTitle, mDescription, mPrice, mLocation;
//vars
private String mPostId;
private String userId;
private Post mPost;
private PostImages mPostImages;
private ViewPager viewPager;
private ImageView editPostIcon;
private WormDotsIndicator wormDotsIndicator;
public ViewAdapter viewAdapter;
public DatabaseReference reference;
public FirebaseUser currentUser;
public ArrayList<String> IMAGES = new ArrayList<>();
public ArrayList<Uri> mImageUris = new ArrayList<>();
private SquareImageView postImageView;
private User user;
//Dialog and Sheet vars
private Dialog deleteDialog;
private Button deleteBtnDialog;
private Button deleteBtnSheet;
private Button updateBtn;
private Button sendBtn;
private TextView titleTv, messageTv;
private ImageView closeIcon;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_view_post);
mPostId = getIntent().getStringExtra(getString(R.string.arg_post_id));
mTitle = (TextView) findViewById(R.id.post_title);
mDescription = (TextView) findViewById(R.id.post_description);
mPrice = (TextView) findViewById(R.id.post_price);
mLocation = (TextView) findViewById(R.id.post_location);
postImageView = findViewById(R.id.post_image);
sendBtn = findViewById(R.id.send_msg);
viewPager = findViewById(R.id.view_pager_images);
editPostIcon = findViewById(R.id.edit_post_btn);
wormDotsIndicator = findViewById(R.id.dotsindicator);
editPostIcon.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
showBottomSheetDialog();
}
});
getPostInfo();
showButtonsForCurrentUser();
////MyPosts Layout/////
deleteBtnDialog = findViewById(R.id.dialog_btn);
deleteDialog = new Dialog(this);
////MyPosts Layout/////
sendBtn.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
Intent intent = new Intent(ViewPostActivity.this, MessageActivity.class);
intent.putExtra("userId", userId);
startActivity(intent);
}
});
}
public void showButtonsForCurrentUser(){
currentUser = FirebaseAuth.getInstance().getCurrentUser();
//sendBtn and editPostIcon are set to GONE.
if (currentUser.equals(userId)){
sendBtn.setVisibility(View.VISIBLE);
}else{
editPostIcon.setVisibility(View.VISIBLE);
}
}
private void getPostInfo(){
Log.d(TAG, "getPostInfo: getting the post information.");
reference = FirebaseDatabase.getInstance().getReference();
Query query = reference.child(getString(R.string.node_posts))
.orderByKey()
.equalTo(mPostId);
query.addListenerForSingleValueEvent(new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
DataSnapshot singleSnapshot = dataSnapshot.getChildren().iterator().next();
if(singleSnapshot != null){
mPost = singleSnapshot.getValue(Post.class);
Log.d(TAG, "onDataChange: found the post: " + mPost.getTitle());
mTitle.setText(mPost.getTitle());
mDescription.setText(mPost.getDescription());
String price = "FREE";
if(mPost.getPrice() != null){
price = "$" + mPost.getPrice();
}
mPrice.setText(price);
String location = mPost.getCity();
mLocation.setText(location);
userId = mPost.getUser_id();
if (mPost.getImage() != null){
wormDotsIndicator.setVisibility(View.INVISIBLE);
postImageView.setVisibility(View.VISIBLE);
Picasso.get().load(mPost.getImage()).into(postImageView);
}else {
IMAGES = mPost.getPostImages();
for (int i = 0; i <IMAGES.size(); i++){
Uri myUri = Uri.parse(IMAGES.get(i));
mImageUris.add(myUri);
}
viewAdapter = new ViewAdapter(getApplication(), IMAGES);
viewPager.setAdapter(viewAdapter);
wormDotsIndicator.setViewPager(viewPager);
}
}
}
#Override
public void onCancelled(DatabaseError databaseError) {
}
});
}
private void showBottomSheetDialog() {
final BottomSheetDialog bottomSheetDialog = new BottomSheetDialog(ViewPostActivity.this, R.style.BottomSheetDialogTheme);
LinearLayout linearLayout = findViewById(R.id.bottom_sheet_update_container);
View bottomSheetView = LayoutInflater.from(getApplicationContext()).inflate(R.layout.bottom_sheet_update, linearLayout);
updateBtn = bottomSheetView.findViewById(R.id.update_btnn);
deleteBtnSheet = bottomSheetView.findViewById(R.id.delete_btnn);
bottomSheetDialog.setContentView(bottomSheetView);
bottomSheetDialog.show();
updateBtn.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
Intent updateActivityIntent = new Intent(ViewPostActivity.this, UpdateActivity.class);
if (IMAGES != null){
updateActivityIntent.putStringArrayListExtra("IMAGES", IMAGES);
updateActivityIntent.putParcelableArrayListExtra("IMAGEURIS", mImageUris);
}else {
String singlePhotoUrl = mPost.getImage();
updateActivityIntent.putExtra("Single Photo url", singlePhotoUrl);
}
updateActivityIntent.putExtra("Başlık", mTitle.getText());
updateActivityIntent.putExtra("Açıklama", mDescription.getText());
updateActivityIntent.putExtra("Fiyat", mPrice.getText());
updateActivityIntent.putExtra("mPostId", mPostId);
startActivity(updateActivityIntent);
bottomSheetDialog.dismiss();
}
});
deleteBtnSheet.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
showDeleteDialog();
}
});
}
public void showDeleteDialog(){
deleteDialog.setContentView(R.layout.positive_dialog);
closeIcon = deleteDialog.findViewById(R.id.close_dialog);
deleteBtnDialog = deleteDialog.findViewById(R.id.dialog_btn);
titleTv = deleteDialog.findViewById(R.id.titleTv);
messageTv = deleteDialog.findViewById(R.id.message_dialog);
closeIcon.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
deleteDialog.dismiss();
}
});
deleteDialog.getWindow().setBackgroundDrawable(new ColorDrawable(Color.TRANSPARENT));
deleteDialog.show();
deleteBtnDialog.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
deletePost(mPostId);
finish();
overridePendingTransition( 0, 0);
startActivity(getIntent());
overridePendingTransition( 0, 0);
deleteDialog.dismiss();
}
});
}
private void deletePost(String deletePostId){
Bundle args = new Bundle();
args.putString(getString(R.string.arg_post_id), deletePostId);
Query deleteQuery = reference.child("posts").orderByChild("post_id").equalTo(deletePostId);
deleteQuery.addListenerForSingleValueEvent(new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
for(DataSnapshot delData: dataSnapshot.getChildren()){
delData.getRef().removeValue();
Intent backIntent = new Intent(ViewPostActivity.this, SearchActivity.class);
startActivity(backIntent);
}
Toast.makeText(ViewPostActivity.this,"Data Deleted",Toast.LENGTH_LONG).show();
}
#Override
public void onCancelled(DatabaseError databaseError) {
Toast.makeText(ViewPostActivity.this,databaseError.getMessage(),Toast.LENGTH_LONG).show();
}
});
}
private void status(String status){
currentUser = FirebaseAuth.getInstance().getCurrentUser();
reference = FirebaseDatabase.getInstance().getReference("users").child(currentUser.getUid());
HashMap<String, Object> hashMap = new HashMap<>();
hashMap.put("status", status);
reference.updateChildren(hashMap);
}
#Override
protected void onResume() {
super.onResume();
status("online");
}
#Override
protected void onPause() {
super.onPause();
status("offline");
}
}
what are the values for mPostId?
I would log the userID and currentuser values thats being retrieved, to check if there is no issue your query. The boolean part should work
Is there any way to stop the progress bar from other class which is started in mainActivity
Kindly find the code
I am starting the progress bar in the main activity and then calling the method of other java class
where I am inserting data in firebase
I just want that after firebase insertion is successful progress bar should stop
but didn't find any way to do that
public class ProductDetails extends AppCompatActivity {
ProgressBar progressbar;
Button btn;
FirebaseDatabase firebaseDatabase;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_product_details);
progressbar = findViewById(R.id.btnprogressbar);
btn = findViewById(R.id.submit_btn);
firebaseDatabase = FirebaseDatabase.getInstance();
btn.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
progressbar.setVisibility(View.VISIBLE);
submitForm();
}
});
}
private void submitForm() {
FormDetailsServices formDetailsServices = new FormDetailsServices(ProductDetails.this);
FormDTO formDTO=generateForDTO();
formDetailsServices.submitForm(formDTO,firebaseDatabase);
}
}
My FormDetailsServices:
public class FormDetailsServices {
Context context;
final String TAG = "FormDetailsServices";
public FormDetailsServices(Context context) {
this.context = context;
}
public Context getContext() {
return context;
}
public void setContext(Context context) {
this.context = context;
}
public void submitForm(FormDTO formDTO,FirebaseDatabase firebaseDatabase) {
firebaseDatabase
.getReference()
.child("test")
.setValue(formDTO)
.addOnSuccessListener(new OnSuccessListener<Void>() {
#Override
public void onSuccess(Void aVoid) {
Log.d(TAG,"form submitted Successfully");
//here i want to stop progressbar
}
}).addOnFailureListener(new OnFailureListener() {
#Override
public void onFailure(#NonNull Exception e) {
Log.d(TAG,"form submittion Failed exception msg= " + e.getMessage());
}
});
}
}
Everything is working fine its getting inserted to Firebase but progressbar is still visible
You can create an interface in FormDetailsServices class and implement it to your main class, and then you can hide the progress bar by calling its methods in main class as below -
public class ProductDetails extends AppCompatActivity implements FormDetailsServices.OnFormSubmissionListener{
ProgressBar progressbar;
Button btn;
FirebaseDatabase firebaseDatabase;
OnFormSubmissionListener listener;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_product_details);
progressbar = findViewById(R.id.btnprogressbar);
btn = findViewById(R.id.submit_btn);
firebaseDatabase = FirebaseDatabase.getInstance();
btn.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
progressbar.setVisibility(View.VISIBLE);
submitForm();
}
});
}
private void submitForm() {
FormDetailsServices formDetailsServices = new
FormDetailsServices(ProductDetails.this);
formDetailsServices.setOnFormSubmissionListener(this);
FormDTO formDTO=generateForDTO();
formDetailsServices.submitForm(formDTO,firebaseDatabase);
}
#Override
public void onSubmissionSuccess() {
progressbar.setVisibility(View.GONE);
}
#Override
public void onSubmissionFailure() {
progressbar.setVisibility(View.GONE);
}
}
and for FormDetailsServices
public class FormDetailsServices {
Context context;
final String TAG = "FormDetailsServices";
OnFormSubmissionListener listener;
public FormDetailsServices(Context context) {
this.context = context;
}
public Context getContext() {
return context;
}
public void setContext(Context context) {
this.context = context;
}
void setOnFormSubmissionListener(OnFormSubmissionListener listener){
this.listener = listener;
}
public void submitForm(FormDTO formDTO,FirebaseDatabase firebaseDatabase) {
firebaseDatabase
.getReference()
.child("test")
.setValue(formDTO)
.addOnSuccessListener(new OnSuccessListener<Void>() {
#Override
public void onSuccess(Void aVoid) {
Log.d(TAG,"form submitted Successfully");
//here i want to stop progressbar
listener.onSubmissionSuccess();
}
}).addOnFailureListener(new OnFailureListener() {
#Override
public void onFailure(#NonNull Exception e) {
listener.onSubmissionFailure();
Log.d(TAG,"form submittion Failed exception msg= " + e.getMessage());
}
});
}
interface OnFormSubmissionListener {
void onSubmissionSuccess();
void onSubmissionFailure();
}
}
How do I check if the download completed in onCreate fetch library?
The following code work without problem, but maybe user cancel the download operation before completion and incomplete file exists in the path.
public class MainActivity extends AppCompatActivity implements FetchObserver<Download> {
private Button Edame, tavaghof, DownloadImage, online;
public static TextView etaTextView;
public static TextView downloadSpeedTextView;
public static Request request;
public static Fetch fetch;
public static ProgressBar progressBar;
public static TextView progressTextView;
private LinearLayout dllaye;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
try {
File root = android.os.Environment.getExternalStorageDirectory();
File path = new File(root.getAbsolutePath() + "/telavat/" + "naba.mp3");
if (path.exists()) {
dllaye.setVisibility(View.GONE);
}
} catch (Exception e) {
}
FetchConfiguration fetchConfiguration = new FetchConfiguration.Builder(this)
.setDownloadConcurrentLimit(3)
.build();
fetch = Fetch.Impl.getInstance(fetchConfiguration);
DownloadImage.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
enqueueDownload();
}
});
Edame.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
fetch.resume(request.getId());
}
});
tavaghof.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
fetch.pause(request.getId());
}
});
//EndOnceate
}
private void enqueueDownload() {
File root = android.os.Environment.getExternalStorageDirectory();
final String url = "https://amoozesh3.ir/play/naba.mp3";
final String filePath = root.getAbsolutePath() + "/telavatquran/" + Uri.parse(url).getLastPathSegment();
request = new Request(url, filePath);
request.setExtras(getExtrasForRequest(request));
fetch.attachFetchObserversForDownload(request.getId(), this)
.enqueue(request, new Func<Request>() {
#Override
public void call(#NotNull Request result) {
request = result;
}
}, new Func<Error>() {
#Override
public void call(#NotNull Error result) {
}
});
}
#Override
protected void onResume() {
super.onResume();
if (request != null) {
fetch.attachFetchObserversForDownload(request.getId(), this);
}
}
#Override
protected void onPause() {
super.onPause();
if (request != null) {
fetch.removeFetchObserversForDownload(request.getId(), this);
}
}
#Override
protected void onDestroy() {
super.onDestroy();
fetch.close();
}
#Override
public void onChanged(Download data, #NotNull Reason reason) {
updateViews(data, reason);
}
private Extras getExtrasForRequest(Request request) {
final MutableExtras extras = new MutableExtras();
extras.putBoolean("testBoolean", true);
extras.putString("testString", "test");
extras.putFloat("testFloat", Float.MIN_VALUE);
extras.putDouble("testDouble", Double.MIN_VALUE);
extras.putInt("testInt", Integer.MAX_VALUE);
extras.putLong("testLong", Long.MAX_VALUE);
return extras;
}
private void updateViews(#NotNull Download download, Reason reason) {
if (request.getId() == download.getId()) {
if (reason == Reason.DOWNLOAD_COMPLETED) {
dllaye.setVisibility(View.GONE);
Toast.makeText(getApplicationContext(), "File download successful",
Toast.LENGTH_LONG).show();
}
setProgressView(download.getStatus(), download.getProgress());
etaTextView.setText(Utils.getETAString(this, download.getEtaInMilliSeconds()));
downloadSpeedTextView.setText(Utils.getDownloadSpeedString(this, download.getDownloadedBytesPerSecond()));
}
}
private void setProgressView(#NonNull final Status status, final int progress) {
switch (status) {
case QUEUED: {
progressTextView.setText(R.string.queued);
progressBar.setProgress(progress);
break;
}
case ADDED: {
progressTextView.setText(R.string.added);
progressBar.setProgress(progress);
break;
}
case DOWNLOADING: {
if (progress == -1) {
progressTextView.setText(R.string.downloading);
progressBar.setProgress(progress);
} else {
final String progressString = getResources().getString(R.string.percent_progress, progress);
progressTextView.setText(progressString);
progressBar.setProgress(progress);
}
break;
}
case COMPLETED: {
break;
}
default: {
progressTextView.setText(R.string.status_unknown);
progressBar.setProgress(progress);
break;
}
}
}
}
I want to free up more space on the screen after downloading
How can I understand the download is completed?
I’d appreciate your cooperation.
My settext do not update after I have updated it's value from database. But if I logout and login into my app settext is refreshed.I get the value of settext by SharedPreferences.
public class MySettingsActivity extends AppCompatActivity {
private TextView settingsDisplayName;
private TextView settingsDisplayStatus;
private User user = SharedPrefManager.getInstance(this).getUser();
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_my_settings);
settingsDisplayName = (TextView) findViewById (R.id.settings_username);
settingsDisplayStatus = (TextView) findViewById(R.id.settings_status);
settingsChangeUsername.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
String old_name = settingsDisplayName.getText().toString();
Intent usernameIntent = new Intent(MySettingsActivity.this, UsernameActivity.class);
usernameIntent.putExtra("user_name",old_name );
startActivity(usernameIntent);
}
});
}
#Override
protected void onStart() {
MySettingsActivity.this.runOnUiThread(new Runnable() {
#Override
public void run() {
settingsDisplayName.setText(user.getName());
settingsDisplayStatus.setText(user.getEmail());
}
});
super.onStart();
}
}
I'm new to this concept. I read several threads but I block so thanks in advance for your patience!
In a fragment (frag1) I launch an async task. I want to prevent the user of doing anything while the task is not completed so I want to communicate the % of the task completed so the user waits informed.
I've defined an interface in a java SetVal.java:
interface SetVal {
void setVal(int val);
}
My async task:
class AsyncCounter extends AsyncTask<Void, Integer, Void> {
private SetVal sender;
public AsyncCounter(SetVal sv){
this.sender = sv;
}
#Override
protected Void doInBackground(Void... params) {
for(int i=0;i<60;i++){
publishProgress(i);
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
return null;
}
#Override
protected void onProgressUpdate(Integer... values) {
Log.i("ASYNC TASK","val: "+values[0]);
sender.setVal(values[0]);
}
#Override
protected void onPostExecute(Void result) {
super.onPostExecute(result);
}
public interface SetVal {
public void setVal(int val);
}
public void setListener(SetVal listener) {
this.sender = listener;
}
}
I'm struggling to know how to pass the interface to the task.
Is my code correct?
How do I instantiate the async task?
fragment:
public class Frag1 extends android.app.Fragment implements SetVal {
private static TextView txt;
private int counter;
SetVal listener;
public Frag1() {
// Required empty public constructor
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
return inflater.inflate(R.layout.fragment_frag1, container, false);
}
#Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
txt = (TextView) getActivity().findViewById(R.id.txt);
Button btn = (Button) getActivity().findViewById(R.id.btn1);
btn.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
Log.i("Frag1", "val: " + counter);
if (counter > 0) return;
FragmentTransaction ft = getFragmentManager().beginTransaction();
Frag2 f2 = new Frag2();
ft.replace(R.id.content_frame, f2);
ft.addToBackStack("f2");
ft.commit();
}
});
Button btn2 = (Button) getActivity().findViewById(R.id.btn2);
btn2.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
AsyncCounter ac = new AsyncCounter(???????);
ac.execute();
}
});
}
#Override
public void setVal(int val) {
counter = val;
}
}
Not sure what and why you are trying to do that, but you can pass the Fragment :
Try to create a private method:
public void onClick(View v) {
startMyAsync();
}
private void startMyAsync() {
new AsyncCounter(this).execute();
}
finally:
public AsyncCounter(Frag1 context){
this.sender = (SetVal)context;
}