Androidの場合ファイルの読み書きは初回起動時はStreamingAssetsフォルダから読み込み、
2回目以降はApplication.persistentDataPathで読み書きするようにします。
しかもAndroid のみ StreamingAssetsフォルダから読み込む場合 WWW クラスを使わないと読み込めないのが面倒くさいところです。
なぜこういう作りにするのか
StreamingAssetsフォルダを作っておけばビルド先のプラットフォームの、特定のフォルダーに何も変換されない状態で保持されます。しかし読み込みしかできず書き込みができないので
Application.persistentDataPathを使います。読み書きができるデータパスなので
初回はStreamingAssetsから読み込みそれ以降は、Application.persistentDataPathでデータのやり取りをします。
プロジェクトをGitHubに上げておきました。
Unityバージョン 5.5.0f3
https://github.com/templa00/FIleTest
一応ソースコードも貼っておきます。
以下ソースコード
// データを初期化するか?
//#define DATA_INIT
using UnityEngine;
using System.IO;
using System.Text;
using System.Collections;
using System;
/// ファイル管理
public class FIleManager
{
// StreamingAssetsパス
#if UNITY_EDITOR
// StreamingAssetsのパス
public static string StreamingAssetsPath = Application.dataPath + "/StreamingAssets";
// Android
#elif UNITY_ANDROID
// パス(Android)
public static string StreamingAssetsPath = "jar:file://" + Application.dataPath + "!/assets";
// iOS
#elif UNITY_IPHONE
public static string StreamingAssetsPath = path = Application.dataPath + "/Raw";
#else
public static string StreamingAssetsPath = Application.dataPath + "/StreamingAssets";
#endif
/// ファイル読み込み
public static IEnumerator ReadFileText (Action callback, string _file_path)
{
// 結果
string result = string.Empty;
// ファイル
FileInfo file;
// 初回読み込みか?
bool is_init_load = false;
// 保存データパス
var save_file_path = Application.persistentDataPath + _file_path;
// 初回起動時ロードパス
var init_file_path = StreamingAssetsPath + _file_path;
// 読み込み先パス
string load_path = string.Empty;
// 保存先にデータがある場合
if (File.Exists(save_file_path))
{
// データを初期化する場合
#if DATA_INIT
Debug.Log("強制的に初回読み込み");
// 初回起動時と同じ処理をするようにする
is_init_load = true;
// セーブデータ読み込み
file = new FileInfo(save_file_path);
// ファイル削除
file.Delete();
// 初回パスデータを取得する
load_path = init_file_path;
#else
Debug.Log("2回目以降の読み込み");
// セーブデータのパスを設定する
load_path = save_file_path;
#endif
}
// 初回起動時
else
{
Debug.Log("初回読み込み");
is_init_load = true;
// 初回パスデータを取得する
load_path = init_file_path;
}
Debug.Log("データ読込パス : " + load_path);
// win or ios
#if UNITY_EDITOR || UNITY_IPHONE
// JSONファイルを読み込む
file = new FileInfo(load_path);
using (StreamReader sr = new StreamReader(file.OpenRead(), Encoding.UTF8))
{
result = sr.ReadToEnd();
}
yield return new WaitForSeconds(0f);
// Android
#elif UNITY_ANDROID
// 初回ロードの場合
if (init_load_data)
{
WWW www = new WWW(path);
/// wwwの通信が終わるまで待機
yield return www;
string txtBuffer = string.Empty;
TextReader txtReader = new StringReader(www.text);
string description = string.Empty;
while ((txtBuffer = txtReader.ReadLine()) != null)
{
description = description + txtBuffer + "\r\n";
Debug.Log("description : " + description);
}
result = description;
}
// 初回ロードではない場合
else
{
// ファイルを読み込む
file = new FileInfo(path);
using (StreamReader sr = new StreamReader(file.OpenRead(), Encoding.UTF8))
{
result = sr.ReadToEnd();
}
yield return new WaitForSeconds(0f);
}
#endif
callback(result);
}
/// ファイルを上書きする
public static void WriteText (string _folda_path, string _file_name, string _contents)
{
// 保存フォルダパス
var save_folda_path = Application.persistentDataPath + _folda_path;
// 保存データパス
var save_path = Application.persistentDataPath + _folda_path + _file_name;
// フォルダがある場合
if (Directory.Exists(save_folda_path))
{
Debug.Log("フォルダがあります");
}
else
{
Debug.Log("フォルダが無いので作成します");
// ディレクトリ作成
Directory.CreateDirectory(save_folda_path);
}
// 保存先 persistentDataPath
// [win] : C:/Users/HomePC/AppData/LocalLow/DefaultCompany/プロジェクト名/save_data.json
// [Android] : /data/app/xxxx.apk
// [ios] : /var/mobile/Applications/xxxxxx/myappname.app/Data
FileInfo file = new FileInfo(save_path);
Debug.Log("保存先パス : " + save_path);
// ファイルがある場合
if (File.Exists(save_path))
{
// 削除
file.Delete();
}
// 書き込み用ストリーム
StreamWriter stream;
stream = file.AppendText(); // StreamWriter を作成
stream.WriteLine(_contents); // 書き込み
stream.Flush(); // バッファ書き込み
stream.Close(); // 閉じる
}
}
以下、使用方法
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class FileTest : MonoBehaviour {
// Use this for initialization
IEnumerator Start ()
{
// テストデータの文字列
string test_data_str = string.Empty;
// TestData読み込み(ロード)
yield return FIleManager.ReadFileText(r => test_data_str = r, "/Data/TestData.txt");
// 読み込んだテストデータの文字列を表示
Debug.Log(test_data_str);
// TestData書き込み(セーブ)
FIleManager.WriteText("/Data", "/TestData.txt", "テストデータに書き込みました!");
// 書き込んだTestDataを読み込み(ロード)
yield return FIleManager.ReadFileText(r => test_data_str = r, "/Data/TestData.txt");
// 読み込んだテストデータの文字列を表示
Debug.Log(test_data_str);
}
}
実行したら以下のようなログが出力されればOKです。
windowsでデバッグしました。
Androidでデバッグする場合はMonitorなどを使用するとログが表示されます。
初回起動時 |
2回目以降の起動時 |
0 件のコメント :
コメントを投稿