-1

I have been searching the internet to find a resolution to my answer, have gone through all the documentation, and have looked through multiple forums before posting my own question on this. I need to save information through a file because my function

@Override
protected void onSaveInstanceState(Bundle savedInstanceState) {
    savedInstanceState.putInt("PointCount", pointCount);
    savedInstanceState.putInt("UpOneCost", upOne);
    savedInstanceState.putInt("UpTwoCost", upTwo);
    savedInstanceState.putInt("TimerTime", upgradeTime);
    super.onSaveInstanceState(savedInstanceState);
    Toast.makeText(this, "Saving", Toast.LENGTH_LONG).show();
}

onSaveInstanceState only works at specific intervals at which I'm not entirely clear on. However, I know it doesn't get called when the activity is destroyed. The function above is mySaveInstanceState function and below is my restoreInstanceState function

@Override
protected void onRestoreInstanceState(Bundle savedInstanceState) {
    super.onRestoreInstanceState(savedInstanceState);
    Toast.makeText(this, "Restoring", Toast.LENGTH_LONG).show();
    if(savedInstanceState != null){
        pointCount = savedInstanceState.getInt("PointCount");
        upOne = savedInstanceState.getInt("UpOneCost");
        upTwo = savedInstanceState.getInt("UpTwoCost");
        upgradeTime = savedInstanceState.getInt("TimerTime");
        if(upgradeTime < 5500){
            startTimer();
        }

        TextView pointCountText = (TextView)findViewById(R.id.myTextView1);
        pointCountText.setText("Points: " + Integer.toString(pointCount));

        TextView pointCountText2 = (TextView)findViewById(R.id.upgradeScreenPointText);
        pointCountText2.setText("Points: " + Integer.toString(pointCount));

        Button upButtonOne = (Button)findViewById(R.id.upButton1);
        upButtonOne.setText("Cost: " + Integer.toString(upOne));

        Button upButtonTwo = (Button)findViewById(R.id.upButton2);
        upButtonTwo.setText("Cost: " + Integer.toString(upTwo));

        TextView myTimerValue = (TextView)findViewById(R.id.myTimerValueText);
        myTimerValue.setText("Current Time: " + Integer.toString(upgradeTime));
    }
}

There is a bit of useless info in there but overall this doesn't run when I hit the back button on the android device, so after a bit of research, i decided I should just save it into a file directory. This is where I created a file in my android project file named "saveFile" It is a text file, and it is in the same directory as my mainActivity.java file in order to remove file scope complications. In an effort to reach this file I came to the conclusion of overriding the onDestroy() function and try

String fileName = "saveFile";
FileOutputStream outputStream;

@Override
protected void onDestroy() {
    super.onDestroy();
    outputStream.openFileOutput(fileName, Context.MAKE_PRIVATE);
}

At which point I was already stopped because it couldn't find the file. The documentation is not clear on where this file should go directory wise, and as far as creation and then writing it is also very vague. If anyone could give a very clear explanation as to how all of it works I would be very appreciative of it. Thank you =) Note some of the code may contain minor errors since I typed some of it instead of copy paste but the idea is there. The only error I receive in the editor is on the outputStream.openFileOutput() line, which says it can't find the file.

KishuDroid
  • 5,411
  • 4
  • 30
  • 47
  • And at what point do you intend to call this file writer method? As that would be the same as calling the method you already have? [Check](http://stackoverflow.com/questions/4096169/onsaveinstancestate-and-onrestoreinstancestate) – Skynet Dec 31 '15 at 04:29
  • i was going to write to the file in the onDestroy() method and then retain it within the onCreate() method. – theBeastiest1398 Dec 31 '15 at 04:30
  • 1
    Pressing back button does not call the onDestroy method. Calling of onDestroy method is entirely upto the OS and the contention it is facing. Need a bit brushup, go read the activity life cycle. Your best friend here is the onPause and onStop method. You can test this by just making a skeleton of lifecycle methods and printing out something, you will get to know exactly which method is called in what order. – Skynet Dec 31 '15 at 04:31
  • I created a basic application to show me the state changes and hitting the back button called the state changes is this order: onPause, onStop, onDestroy. So understandably i would need to start saving within onPause or onStop anyway regardless of onDestroy. In which case i dont know how. – theBeastiest1398 Dec 31 '15 at 04:40
  • onPause / onResume is your friend here. – Skynet Dec 31 '15 at 04:41
  • To save some var's value i think you can try use SharedPreferences with guide url http://developer.android.com/intl/vi/training/basics/data-storage/shared-preferences.html – GiapLee Dec 31 '15 at 04:44
  • Ya i was taking a look at using SharedPreferences for the application i need it for. As shown in the code above i really only need to save 4 variables during the state changes for now, possibly more in the future. – theBeastiest1398 Dec 31 '15 at 04:51
  • If you are interested in an indepth coverage of this, [read](https://github.com/spacecowboy/AndroidTutorialContentProvider). However be warned its an overkill for your use case. – Skynet Dec 31 '15 at 04:53
  • Also remember the state you save at `onSaveInstanceState()` is later available at `onCreate()` method invocation. So use `onCreate` (and its `Bundle` parameter) to restore state of your activity. – Skynet Dec 31 '15 at 04:55

4 Answers4

2

In order to do file operations you should specify complete file path. Passing only the filename will throw FileNotFoundException.

You can do one of the following; 1. Save the file in app cache. filePath = appContext.getCacheDir( ).getAbsolutePath( )+"yourFileName";

  1. Save the file in app data directory. filePath = Environment.getDataDirectory( ).getPath( ) + File.separator + "data" + File.separator + appContext.getPackageName( ) + File.separator+"yourFileName";

  2. Save the file in some folder on SD card. File sdCard = Environment.getExternalStorageDirectory( ); String filePath = sdCard.getAbsolutePath( ) + File.separator + BASE_FOLDER_ON_SD_CARD + File.separator+"yourFileName";

For the third option you may need to add WRITE_EXTERNAL_STORAGE permission in AndroidManifest.xml of your application.

Also, saving the file should happen in onStop() method of your activity and reading the file content should happen in onResume() Use the file from stored location.

abidfs
  • 49
  • 3
  • Is there any chance you can give more of a breakdown of the second option? I am looking to save to the devices internal storage and im not entirely sure what you are getting at with the code you have shown. Possibly edit the post to be more clear if you can. Thanks =) – theBeastiest1398 Dec 31 '15 at 04:48
  • See, Environment.getDataDirectory( ).getPath( ) this returns the path to "/data" directory where android stores all the applications data. Your applications data will be stored under the directory "/data/data/yourpackagename" The above path only accessible to your application. I mean you can not access other application's data directory even if you know the complete package name. Under this directory you can create your files. – abidfs Dec 31 '15 at 07:28
0

You can do like this.

private void writeToFile(String data) {
try {
    OutputStreamWriter outputStreamWriter = new OutputStreamWriter(context.openFileOutput("config.txt", Context.MODE_PRIVATE));
    outputStreamWriter.write(data);
    outputStreamWriter.close();
}
catch (IOException e) {
    Log.e("Exception", "File write failed: " + e.toString());
} 
}
private String readFromFile() {

String ret = "";

try {
    InputStream inputStream = openFileInput("config.txt");

    if ( inputStream != null ) {
        InputStreamReader inputStreamReader = new InputStreamReader(inputStream);
        BufferedReader bufferedReader = new BufferedReader(inputStreamReader);
        String receiveString = "";
        StringBuilder stringBuilder = new StringBuilder();

        while ( (receiveString = bufferedReader.readLine()) != null ) {
            stringBuilder.append(receiveString);
        }

        inputStream.close();
        ret = stringBuilder.toString();
    }
}
catch (FileNotFoundException e) {
    Log.e("login activity", "File not found: " + e.toString());
} catch (IOException e) {
    Log.e("login activity", "Can not read file: " + e.toString());
}

return ret;
}

but for each object you have to create separate file with different name.

hope this will help you..

V-rund Puro-hit
  • 5,518
  • 9
  • 31
  • 50
  • it does help in a sense as i can understand whats happening, however im looking for more of a break down of how the file opening and writing operation works, and when to do it, which i have learned from above would be withing the onResume, onStop, and onPause methods. – theBeastiest1398 Dec 31 '15 at 04:45
0

below is way to store data in android:

  • shared preferences(data will keep until user uninstall the app or clear the app cache in setting application manager)
  • sqlite(permanent storage)
  • create a file to store(permanent storage) or if your data doesn't need to store permanently you may just create a singleton class to store your data. the data stored will gone after user close the app.
MinFu
  • 353
  • 1
  • 13
0
 public void Save(String fileName) {
    try {
        OutputStreamWriter out = new OutputStreamWriter(openFileOutput(fileName, 0));
        out.write(EditText1.getText().toString());
        out.close();
        Toast.makeText(this, fileName + " saved!", Toast.LENGTH_SHORT).show();
    } catch (Throwable t) {
        Toast.makeText(this, "Exception: " + t.toString(), Toast.LENGTH_LONG).show();
    }
}
HomieZ2
  • 31
  • 1