I'm using realm-android 0.74.0 with android 4.4.2
I create an instance of realm, populate it with objects and commit the transaction.
My objects are saved fine. I can load them and manipulate them.
But each time i restart my application the data is lost
Has anyone run into the same problem ?
Christian from Realm here.
Your login button onClick handler have this method:
button.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
...
// Delete database
Realm.deleteRealmFile(getActivity());
...
}
});
This deletes the default realm file and by that your data. Where you trying to accomplish something else by this line?
I was doing the following
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.fragment_login, container, false);
final Button button = (Button) rootView.findViewById(R.id.connect);
final EditText username = (EditText) rootView.findViewById(R.id.username);
final EditText password = (EditText) rootView.findViewById(R.id.password);
button.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
// Hide keyboard
InputMethodManager inputManager = (InputMethodManager)
getActivity().getSystemService(Context.INPUT_METHOD_SERVICE);
inputManager.hideSoftInputFromWindow(getActivity().getCurrentFocus().getWindowToken(),
InputMethodManager.HIDE_NOT_ALWAYS);
// Call user login service
RestAdapter restAdapter = new RestAdapter.Builder()
.setEndpoint(getString(R.string.app_url_base))
.build();
AppService service = restAdapter.create(AppService.class);
service.login(username.getText().toString(), password.getText().toString(), new Callback<User>() {
#Override
public void success(User user, Response response) {
if (user.isSuccess()) {
SharedPreferences prefs = getActivity().getSharedPreferences(Const.PREFS, Context.MODE_PRIVATE);
SharedPreferences.Editor editor = prefs.edit();
Log.d(TAG, "Logged username: " + user.getUsername());
editor.putString(getString(R.string.pref_username), user.getUsername());
editor.putString(getString(R.string.pref_password), user.getPassword());
editor.putString(getString(R.string.pref_lastname), user.getLastname());
editor.putString(getString(R.string.pref_firstname), user.getFirstname());
editor.putString(getString(R.string.pref_md5), user.getMd5());
editor.commit();
Toast.makeText(getActivity(), getString(R.string.success_login), Toast.LENGTH_SHORT).show();
// Delete database
Realm.deleteRealmFile(getActivity());
// Delete log file
File logFile = new File(Const.LOG_FILE);
if (logFile.exists()) logFile.delete();
getActivity().getFragmentManager().beginTransaction()
.replace(R.id.container, TasksFragment.newInstance(2, 0))
.commit();
//((MainActivity) getActivity()).openDrawer();
} else {
Toast.makeText(getActivity(), getString(R.string.error_login), Toast.LENGTH_SHORT).show();
}
}
#Override
public void failure(RetrofitError retrofitError) {
Log.d(TAG, "retrofitError:" + retrofitError.getMessage());
Toast.makeText(getActivity(), getString(R.string.error_login), Toast.LENGTH_SHORT).show();
}
});
}
});
return rootView;
}
but by moving
Realm.deleteRealmFile(getActivity());
before the retrofit call it's seems to work ok
The TasksFragment is running a Service which persist the RealmObjects
Thanks for your help
Related
I am using anjlab/android-inapp-billing library for my in app purchases.
On first attempt on clicking on Purchase Button in my activity, I was able to see the dialog appearing for buying.
In this dialog I get testingId.
On clicking The BUY button, I have seen two options then Ok.
The first attempt was successful.
Now after first successful bought item if I click on Purchase Button
this dialog does not appear.
Why this dialog is not showing?
this is my code
final AlertDialog.Builder builder2 = new AlertDialog.Builder(StartActivity.this);
LayoutInflater inflater = getLayoutInflater();
View dialogLayout = inflater.inflate(R.layout.adremover_layout, null);
builder2.setTitle("Clear Ads");
builder2.setMessage("Buy Products");
builder2.setView(dialogLayout);
builder2.setIcon(R.drawable.dupiconf);
Button btn_buy1 = (Button)dialogLayout.findViewById(R.id.buyitem_btn1);
Button btn_buy2 = (Button)dialogLayout.findViewById(R.id.buyitem_btn2);
Button btn_buy3 = (Button)dialogLayout.findViewById(R.id.buyitem_btn3);
btn_buy1.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
editor1 = getSharedPreferences(FIRST_BUY, MODE_PRIVATE).edit();
editor1.putString("product", "item1");
editor1.apply();
getpurchaseitem = "itm1";
bp.purchase(StartActivity.this, "android.test.purchased");
}
});
btn_buy2.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
editor1 = getSharedPreferences(FIRST_BUY, MODE_PRIVATE).edit();
editor1.putString("product", "item2");
editor1.apply();
getpurchaseitem = "itm2";
bp.purchase(StartActivity.this, "android.test.purchased");
}
});
btn_buy3.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
editor1 = getSharedPreferences(FIRST_BUY, MODE_PRIVATE).edit();
editor1.putString("product", "item3");
editor1.apply();
getpurchaseitem = "itm3";
bp.purchase(StartActivity.this, "android.test.purchased");
}
});
alert2 = builder2.create();
alert2.show();
Even after uninstalling the app the dialog for buying does not appear.
#Override
public void onProductPurchased(#NonNull String productId, #Nullable TransactionDetails details) {
if(getpurchaseitem == "itm1")
{
CancelAlarm();
}
else if (getpurchaseitem == "itm2")
{
CancelAlarm();
}
else if(getpurchaseitem == "itm3")
{
CancelAlarm();
}
}
My guess is that you are not waiting for the BillingProcessor object to be initialized. this is why it works for the second time.
How to use BillingProcessor.IBillingHandle
How do I write Shared-preference Code that is using Firebase for User authentication and the data that is saved by a user is only accessible for them?
My current application Saves a note and displays it which is the main thing needed in my project but when a user logs out and new user logs in he/she can also view the data so the data is not private. My sir suggested to make nodes for users using shared preference but i couldn't find any solutions
HomeActivity:
public class HomeActivity extends AppCompatActivity {
EditText Descriptionholder;
Button Savebtn;
DatabaseReference DatabaseNote;
ListView listViewNotes;
List<PrivateNote> privateNoteList;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_home);
DatabaseNote = FirebaseDatabase.getInstance().getReference("privatenote");
Descriptionholder = findViewById(R.id.description2);
Savebtn = findViewById(R.id.buttonsave);
listViewNotes= findViewById(R.id.listViewPrivate);
privateNoteList = new ArrayList<>();
Savebtn.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
addnote();
}
});
listViewNotes.setOnItemLongClickListener(new AdapterView.OnItemLongClickListener() {
#Override
public boolean onItemLongClick(AdapterView<?> adapterView, View view, int i, long l) {
PrivateNote privateNote = privateNoteList.get(i); //confusion
showUpdateDialog(privateNote.getNoteId(),privateNote.getNoteDescription());
return false;
}
});
}
public boolean onCreateOptionsMenu (Menu menu){
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.side, menu);
return true;
}
#Override
public boolean onOptionsItemSelected (MenuItem item){
switch (item.getItemId()) {
case R.id.item1:
FirebaseAuth.getInstance().signOut();
finish();
startActivity(new Intent(new Intent(this, MainActivity.class)));
Toast.makeText(this, "Logged out ", Toast.LENGTH_SHORT).show();
return true;
default:
return super.onOptionsItemSelected(item);
}
}
#Override
protected void onStart() {
super.onStart();
DatabaseNote.addValueEventListener(new ValueEventListener() {
#Override
public void onDataChange(#NonNull DataSnapshot dataSnapshot) {
privateNoteList.clear();
for (DataSnapshot privateSnapshot: dataSnapshot.getChildren() ){
PrivateNote privateNote = privateSnapshot.getValue(PrivateNote.class);
privateNoteList.add(privateNote);
}
PrivateList adapter = new PrivateList(HomeActivity.this,privateNoteList);
listViewNotes.setAdapter(adapter);
}
#Override
public void onCancelled(#NonNull DatabaseError databaseError) {
}
});
}
private void showUpdateDialog(final String noteId, String noteDescription){
AlertDialog.Builder dialogBuilder = new AlertDialog.Builder(this);
LayoutInflater inflater = getLayoutInflater();
final View dialogview = inflater.inflate(R.layout.update_dialouge,null);
dialogBuilder.setView(dialogview);
final EditText editDescription = dialogview.findViewById(R.id.editDescription);
final Button buttonUpdate = dialogview.findViewById(R.id.buttonUpdate);
final Button buttonDelete = dialogview.findViewById(R.id.buttonDelete);
dialogBuilder.setTitle("Updating Note: " +noteDescription);
final AlertDialog alertDialog = dialogBuilder.create();
alertDialog.show();
buttonUpdate.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
String description = editDescription.getText().toString().trim();
if (TextUtils.isEmpty(description)){
editDescription.setError(" New information required");
return;
}
updatePrivateNote(noteId,description);
alertDialog.dismiss();
}
});
buttonDelete.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
deletePrivateNote(noteId);
}
});
}
private void deletePrivateNote(String noteId) {
DatabaseReference drPrivateNote = FirebaseDatabase.getInstance().getReference("privatenote").child(noteId);
drPrivateNote.removeValue();
Toast.makeText(this, " Note Deleted", Toast.LENGTH_SHORT).show();
}
private boolean updatePrivateNote(String id,String description){
DatabaseReference databaseReference = FirebaseDatabase.getInstance().getReference("privatenote").child(id);
PrivateNote privateNote = new PrivateNote(id,description);
databaseReference.setValue(privateNote);
Toast.makeText(this, " Note Updated", Toast.LENGTH_SHORT).show();
return true;
}
private void addnote () {
String description = Descriptionholder.getText().toString().trim();
if (!TextUtils.isEmpty(description)){
//generated unique number for id
String id = DatabaseNote.push().getKey();
PrivateNote pNote = new PrivateNote(id, description);
DatabaseNote.child(id).setValue(pNote); //pNote value added in id
Toast.makeText(this, "Note added", Toast.LENGTH_SHORT).show();
}
else {
Toast.makeText(this, " Please Enter a note ", Toast.LENGTH_SHORT).show();
}
}
#Override
public void onBackPressed() {
AlertDialog.Builder builder = new AlertDialog.Builder(this);
builder.setMessage("Are you sure you want to exit?")
.setCancelable(false)
.setPositiveButton("Yes", new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int id) {
FirebaseAuth.getInstance().signOut();
finish();
}
})
.setNegativeButton("No", new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int id) {
dialog.cancel();
}
});
AlertDialog alert = builder.create();
alert.show();
}
Adapter:
public class PrivateList extends ArrayAdapter<PrivateNote> {
private Activity context;
private List<PrivateNote> privateNoteList;
public PrivateList(Activity context, List<PrivateNote> privateNoteList){
super(context, R.layout.list_layout,privateNoteList);
this.context =context;
this.privateNoteList=privateNoteList;
}
#NonNull
#Override
public View getView(int position, #Nullable View convertView, #NonNull ViewGroup parent) {
LayoutInflater inflater = context.getLayoutInflater();
View listViewItem = inflater.inflate(R.layout.list_layout,null,true);
TextView textViewDescription = listViewItem.findViewById(R.id.TextViewDescription);
PrivateNote privateNote = privateNoteList.get(position);
textViewDescription.setText(privateNote.getNoteDescription());
return listViewItem;
}
}
PrivateNote:
public class PrivateNote {
public String noteId;
public String noteDescription;
public PrivateNote(){
}
PrivateNote(String noteId, String noteDescription){
this.noteId = noteId;
this.noteDescription=noteDescription;
}
String getNoteId()
{
return noteId;
}
String getNoteDescription()
{
return noteDescription;
}
}
In Firebase, there are two things,
FirebaseDatabase
FirebaseAuth
Usually, in almost all the apps, user data is stored in the FirebaseDatabase under the key, that is generated while creating a new user in your Firebase app.
So, for example, your database structure will look like this.
-Your_main_database
|____UserId_Of_FirebaseUser
|____stuff_related_to_user
|____More stuff related to user
So, you create a new user in FirebaseAuth, you can find more about it below:
Firebase Custom Auth.
Then, after creating a new user, you create child nodes under your database with the key=userId of your current logged in user.
eg. In your addNote function, the id variable will be equal to
String id = FirebaseAuth.getInstance().getCurrentUser().getUid();
Currently, you're using Push keys which are generated based on Timestamp, which you won't be able to associate with user unless you add a key inside your note object which stored current username, and then find all the child nodes that contain that username, but in that case, your data won't be organized at all.
Then, after you create a node with userId under your main database, you can then push new notes created by your user inside the userId with the push() function. So your database structure will look like below.
___
|
|__users
|__uniqueUserId
| |__note1
| |__note2
|__uniqueUserId2
|__note1
|__note2
|__note3
Next time whenever you want to fetch user created notes, you log in the user, get his ID, and then find the notes corresponding to that ID.
I don't see how you can fit SharedPreferences in there, before there is also function to cache data offline in Firebase once it is loaded.
Securing the notes:
If you implement the database like I said above, you'll be very easily able to secure your database.
Common Database Rules.
If you implement everything correctly like I told, you'll be able to secure your database with the fourth set of rules from above rules.
Since you are using firebase authentication, then you can retrieve the userId, and create the following database:
notes
userId
note : "todo"
description : "study"
Then you can do:
DatabaseReference ref = FirebaseDatabase.getInstance().getReference("notes");
FirebaseUser user = FirebaseAuth.getInstance().getCurrentUser();
String userId = user.getUid();
ref.orderByKey().equalTo(userId).addValueEventListener(new ValueEventListener() {...}
This way you would retrieve the data of the currently logged in user only.
I have this App where I'm trying to store a button clicked state in a Fragment. But no matter how much I try, nothing seems to be getting stored. My code definitely seems alright.
public class ClubHome extends Fragment {
ImageView bell,bellring;
TextView beltext,belringtext;
SharedPreferences saved_values;
#Nullable
#Override
public View onCreateView(LayoutInflater inflater, #Nullable ViewGroup container, #Nullable Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.club_home, container, false);
Bundle args = getArguments();
final String index = args.getString("club", "Party");
saved_values = PreferenceManager.getDefaultSharedPreferences(getActivity().getApplicationContext());
bell= (ImageView) view.findViewById(R.id.bell);
bellring= (ImageView) view.findViewById(R.id.bellring);
beltext= (TextView) view.findViewById(R.id.bellmsg);
belringtext= (TextView) view.findViewById(R.id.bellringmsg);
bell.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
belringtext.setVisibility(View.VISIBLE);
bellring.setVisibility(View.VISIBLE);
bell.setVisibility(View.INVISIBLE);
beltext.setVisibility(View.INVISIBLE);
SharedPreferences.Editor editor=saved_values.edit();
editor.putBoolean(index,true);
editor.apply();
editor.commit();
}
});
bellring.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
belringtext.setVisibility(View.INVISIBLE);
bellring.setVisibility(View.INVISIBLE);
bell.setVisibility(View.VISIBLE);
beltext.setVisibility(View.VISIBLE);
SharedPreferences.Editor editor=saved_values.edit();
editor.putBoolean(index,false);
editor.apply();
editor.commit();
}
});
boolean stat = saved_values.getBoolean(index,false);
if (stat){
belringtext.setVisibility(View.INVISIBLE);
bellring.setVisibility(View.INVISIBLE);
bell.setVisibility(View.VISIBLE);
beltext.setVisibility(View.VISIBLE);
} else {
belringtext.setVisibility(View.VISIBLE);
bellring.setVisibility(View.VISIBLE);
bell.setVisibility(View.INVISIBLE);
beltext.setVisibility(View.INVISIBLE);
}
}
}
Your implementation of saving data in SharedPreference is wrong.
You need to get your preference attribute first.
SharedPreference pref = getActivity().getSharedPreferences("MY_PREFERENCES", Activity.MODE_PRIVATE);
Now in the onClickListener of your buttons do something like this to save the desired value.
bell.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
// .. Set visibility of items.
pref.edit().putBoolean("INDEX", true).apply();
}
});
To get the stored value of INDEX from SharedPreference you need to do something like this
boolean indexStatus = pref.getBoolean("INDEX", false); // false is the default value if nothing is returned.
I am learning Android and came across very strange behavior. I am using Retrofit2 as REST library in android (using asynchronous calls). I want to send authCode and TokenId as Google advise it on my server. When I check if user has set password I do a response. If I return code 206 means that user has not yet set password on my back-end server.
So I want to start a fragment that user will enter password (I am also say that I defined LoginFragment and RegistrationFragment that both work on this Activity). But here is the trick, Fragment get called and when my onCreateView is executed there but TextView and Button has null value why is that? I assume that there is a problem since this is run on background thread but I may be mistaken. Is there a better way to achieve what I want?
My Retrofit call:
private void sendTokenToServer(String idToken, String authCode, String email){
Log.d("APP", authCode);
GoogleTokenRequest googleTokenRequest = new GoogleTokenRequest();
googleTokenRequest.setTokenId(idToken);
googleTokenRequest.setAuthCode(authCode);
googleTokenRequest.setEmail(email);
ApiInterface apiService =
ApiClient.getClient().create(ApiInterface.class);
Call<GoogleTokenRequest> call = apiService.sendTokenToBackend(googleTokenRequest);
Log.d("APP", call.toString());
final SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(this);
call.enqueue(new Callback<GoogleTokenRequest>() {
//execute za sinhroni klic, enqueue za asinhroni
#Override
public void onResponse(Call<GoogleTokenRequest> call, Response<GoogleTokenRequest> response) {
String access_token = response.headers().get("Authorization");
Log.d("APP", access_token);
prefs.edit().putString("access_token",access_token).commit();
int statusCode = response.code();
if (statusCode == 206) {
SetPasswordFragment registerFragment = new SetPasswordFragment();
FragmentTransaction fragmentTransaction = getSupportFragmentManager().beginTransaction();
fragmentTransaction.replace(R.id.fragment_login_container, registerFragment);
fragmentTransaction.commit();
}
else{
Intent intent = new Intent(getApplicationContext(), MainActivity.class);
startActivity(intent);
}
This is my fragment code:
public class SetPasswordFragment extends Fragment {
private OnSetPasswordListener onSetPasswordListener;
public SetPasswordFragment() {
// Required empty public constructor
}
#Override
public void onAttach(Context context) {
super.onAttach(context);
if (context instanceof OnSetPasswordListener) {
onSetPasswordListener = (OnSetPasswordListener) context;
} else {
throw new RuntimeException(context.toString()
+ " must implement OnFragmentInteractionListener");
}
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
super.onCreate(savedInstanceState);
LayoutInflater lf = getActivity().getLayoutInflater();
View rootView = lf.inflate(R.layout.fragment_set_password, container, false);
Button setPasswordButton = (Button) rootView.findViewById(R.id.btn_set_password_ok);
TextView textView = (TextView) rootView.findViewById(R.id.set_password_message);
Log.d("APP",rootView.toString());
SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(getActivity());
String username = prefs.getString("username", "User");
textView.setText(String.format(getString(R.string.set_password_message), username));
setPasswordButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
setPasswordValidate();
}
});
return rootView;
}
this is the logcat:
This should probably fix it :
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
super.onCreate(savedInstanceState);
View rootView = inflater.inflate(R.layout.fragment_set_password, container, false);
return rootView;
}
#Override
public void onViewCreated(View view){
Button setPasswordButton = (Button) view.findViewById(R.id.btn_set_password_ok);
TextView textView = (TextView) view.findViewById(R.id.set_password_message);
SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(getActivity());
String username = prefs.getString("username", "User");
textView.setText(String.format(getString(R.string.set_password_message), username));
setPasswordButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
setPasswordValidate();
}
});
}
Note : I dont rexactly remember the exact parameters for the onViewCreated method but view is definitely there. So I guess this should work.
I know my problem description does not point to the real problem that I found but still I will post it since maybe it will help someone. I my case it was problem in xml file I just removed android:fillViewport="true" or set it to false and it works.
I have redirecting the fragment to activity.Progress wheel rotate before getting the data and then it will stops after getting data from web service.After loading the data from web service the screen gets blinks fraction of seconds.After blinking all the data are displayed in activity.How to remove the blinking effects in android?
`
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_post);
FontChangeCrawler fontChanger = new FontChangeCrawler(getAssets(), "arial.ttf");
fontChanger.replaceFonts((ViewGroup) this.findViewById(android.R.id.content));
SharedPreferences prefs1 = getSharedPreferences(MY_PREFS_NAME, MODE_PRIVATE);
userID= prefs1.getString("userid", null);
System.out.println("userid" + userID);
Intent i = getIntent();
useridpost = i.getStringExtra("postuserid");
subuser=i.getStringExtra("subuserid");
btnBack=(ImageButton)findViewById(R.id.button_back);
btnBack.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
if(checking){
Intent cancel = new Intent(PostActivity.this, MainActivity.class);
cancel.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
cancel.putExtra("testedit", "testedit");
startActivity(cancel);
}
else{
finish();
}
}
});
emptyView=(TextView)findViewById(R.id.empty_view);
if(subuser!=null){
if(subuser.equals(userID)){
emptyView.setText("No Posts for you");
}
else{
emptyView.setText("No Posts to show");
}
}
if(useridpost==null) {
// editor.putString("useridfromprofile", userID);
userID = prefs1.getString("userid", null);
System.out.println("user id from shared preferences"+userID);
}
else
{
userID=useridpost;
System.out.println("user id from arguments"+userID);
}
pw=(ProgressWheel) findViewById(R.id.pw_spinner);
obj.styleRandom(pw,getApplicationContext());
recyclerView=(ListView)findViewById(R.id.recycler_view);
// recyclerView.setLayoutManager(new LinearLayoutManager(this));
adapter=new CustomPostAdapter1(this,feedsList,PostActivity.this);
recyclerView.setAdapter(adapter);
getProfilePosts();
}
try this
On the exiting activity, call getWindow().setExitTransition(null);
On the entering activity, call getWindow().setEnterTransition(null);
It will prevent the fade out of the exiting activity and the fade in of the entering activity, which removes the apparent blinking effect.