cut devmenu
This commit is contained in:
@@ -1,65 +0,0 @@
|
||||
package com.ea.ironmonkey.devmenu;
|
||||
|
||||
import static com.ea.ironmonkey.devmenu.util.ReplacementDataBaseHelper.MAIN_TABLE_NAME;
|
||||
import static com.ea.ironmonkey.devmenu.util.ReplacementDataBaseHelper.PATH_TO_REPLACED_ELEMENT;
|
||||
|
||||
import android.content.Context;
|
||||
import android.database.Cursor;
|
||||
import android.database.sqlite.SQLiteDatabase;
|
||||
import android.view.LayoutInflater;
|
||||
import android.view.View;
|
||||
import android.view.ViewGroup;
|
||||
import android.widget.ArrayAdapter;
|
||||
import android.widget.TextView;
|
||||
import android.widget.TwoLineListItem;
|
||||
|
||||
import com.ea.ironmonkey.devmenu.util.ReplacementDataBaseHelper;
|
||||
import com.ea.ironmonkey.devmenu.util.UtilitiesAndData;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.List;
|
||||
|
||||
class FileAdapter extends ArrayAdapter<File> {
|
||||
|
||||
private static int count = 0;
|
||||
private List files;
|
||||
private Context context;
|
||||
private ReplacementDataBaseHelper dataBaseHelper;
|
||||
private SQLiteDatabase database;
|
||||
|
||||
public FileAdapter(Context context, List files) {
|
||||
super(context, android.R.layout.simple_list_item_2, files);
|
||||
dataBaseHelper = new ReplacementDataBaseHelper(context);
|
||||
database = dataBaseHelper.getDatabase();
|
||||
this.context = context;
|
||||
}
|
||||
|
||||
@Override
|
||||
public View getView(int position, View convertView, ViewGroup parent) {
|
||||
|
||||
View view;
|
||||
LayoutInflater inflater = (LayoutInflater) context.getSystemService( Context.LAYOUT_INFLATER_SERVICE );
|
||||
String name = getItem(position).getName();
|
||||
|
||||
Cursor query = database.query(MAIN_TABLE_NAME, new String[]{PATH_TO_REPLACED_ELEMENT},
|
||||
PATH_TO_REPLACED_ELEMENT + " = \"" + getItem(position).getAbsolutePath() + "\""
|
||||
, null, null, null, null);
|
||||
|
||||
if (query.getCount() > 0) {
|
||||
TwoLineListItem listItem = (TwoLineListItem) inflater.inflate(android.R.layout.simple_list_item_2, null, true);
|
||||
listItem.getText1().setText(name);
|
||||
listItem.getText2().setText("Заменен");
|
||||
view = listItem;
|
||||
} else {
|
||||
TextView textView = (TextView) inflater.inflate(android.R.layout.simple_list_item_1, null, true);
|
||||
textView.setText(name);
|
||||
view = textView;
|
||||
}
|
||||
query.close();
|
||||
return view;
|
||||
}
|
||||
|
||||
public List getFiles() {
|
||||
return files;
|
||||
}
|
||||
}
|
||||
@@ -1,458 +0,0 @@
|
||||
package com.ea.ironmonkey.devmenu;
|
||||
|
||||
import static com.ea.ironmonkey.devmenu.util.UtilitiesAndData.OPEN_FILE_ON_REPLACE_REQUEST;
|
||||
import static com.ea.ironmonkey.devmenu.util.UtilitiesAndData.copy;
|
||||
import static com.ea.ironmonkey.devmenu.util.UtilitiesAndData.generateMD5;
|
||||
import static com.ea.ironmonkey.devmenu.util.UtilitiesAndData.isFirstRun;
|
||||
|
||||
import android.annotation.SuppressLint;
|
||||
import android.app.Activity;
|
||||
import android.app.AlertDialog;
|
||||
import android.content.Intent;
|
||||
import android.content.SharedPreferences;
|
||||
import android.net.Uri;
|
||||
import android.os.Bundle;
|
||||
import android.os.Environment;
|
||||
import android.preference.PreferenceManager;
|
||||
import android.util.Log;
|
||||
import android.view.Menu;
|
||||
import android.view.MenuItem;
|
||||
import android.widget.Button;
|
||||
import android.widget.ListView;
|
||||
import android.widget.RadioGroup;
|
||||
import android.widget.TextView;
|
||||
import android.widget.TwoLineListItem;
|
||||
|
||||
import com.ea.games.nfs13_na.BuildConfig;
|
||||
import com.ea.games.nfs13_na.R;
|
||||
import com.ea.ironmonkey.GameActivity;
|
||||
import com.ea.ironmonkey.devmenu.components.LongPressContextMenu;
|
||||
import com.ea.ironmonkey.devmenu.util.ResultListener;
|
||||
import com.ea.ironmonkey.devmenu.util.UtilitiesAndData;
|
||||
import com.ea.nimble.Utility;
|
||||
|
||||
import java.io.BufferedReader;
|
||||
import java.io.File;
|
||||
import java.io.FileInputStream;
|
||||
import java.io.FileNotFoundException;
|
||||
import java.io.FileOutputStream;
|
||||
import java.io.FileReader;
|
||||
import java.io.IOException;
|
||||
import java.text.SimpleDateFormat;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.Collections;
|
||||
import java.util.Date;
|
||||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
import java.util.Random;
|
||||
|
||||
//TODO сделать нормальный файл сохранения
|
||||
//TODO сделать его нрмальное отображние
|
||||
|
||||
//TODO сделать нормальное отслеживние файлов сохранений
|
||||
//TODO сдлеать настройки отслеживания файла
|
||||
//TODO сделать отображение текущего пути в проводнике
|
||||
//TODO добавить иконки к проводику
|
||||
//TODO сделать динамическое контекстное меню файла
|
||||
|
||||
//TODO реализовать сохранение файлов в память телефона из внутреннего хранилища
|
||||
public class MainActivity extends Activity{
|
||||
|
||||
private final String LOG_TAG = "InjectedActivity";
|
||||
|
||||
private String internalFiles;
|
||||
private String externalFiles;
|
||||
private ResultListener resultListener;
|
||||
private ResultListener openResult = new ResultListener() {};
|
||||
private static Thread observerThread;
|
||||
private String globalPath = "";
|
||||
private ListView fileList;
|
||||
private Button backButton;
|
||||
private static final int READ_FILE_REQUEST_CODE = 101;
|
||||
|
||||
@Override
|
||||
protected void onCreate(Bundle savedInstanceState) {
|
||||
super.onCreate(savedInstanceState);
|
||||
UtilitiesAndData.init(this);
|
||||
internalFiles = UtilitiesAndData.getInternalStorage();
|
||||
externalFiles = UtilitiesAndData.getExternalStorage();
|
||||
|
||||
File replacements = new File(UtilitiesAndData.getReplacementsStorage());
|
||||
if(!replacements.exists()) replacements.mkdir();
|
||||
|
||||
File activityFlag = new File(externalFiles + File.separator + BuildConfig.DEV_MENU_ID);
|
||||
// TODO доделать проверку первого запуска
|
||||
if(isFirstRun()){
|
||||
File data = new File(UtilitiesAndData.getExternalStorage());
|
||||
if(!data.exists()){
|
||||
|
||||
File data1 = new File(Environment.getExternalStorageDirectory().getAbsolutePath() + "/Android/data/" + getPackageName() + "_");
|
||||
if(data1.exists()) {
|
||||
String path = data1.getPath();
|
||||
data1.renameTo(new File(path.substring(0, path.length() - 2)));
|
||||
activityFlag = data1;
|
||||
}
|
||||
}
|
||||
try {
|
||||
File temp = new File(UtilitiesAndData.getInternalStorage() + File.separator + "load");
|
||||
temp.createNewFile();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
if(!activityFlag.exists()){
|
||||
updateLanguage();
|
||||
runGame();
|
||||
return;
|
||||
}
|
||||
|
||||
setContentView(R.layout.custom);
|
||||
|
||||
|
||||
String title = String.format(getString(R.string.dev_menu_title), /*BuildConfig.DEV_MENU_VERSION*/"");
|
||||
|
||||
getActionBar().setTitle(title);
|
||||
|
||||
fileList = (ListView) findViewById(R.id.FileList);
|
||||
|
||||
fileList.setAdapter(new FileAdapter(this, asList(externalFiles)));
|
||||
globalPath = externalFiles;
|
||||
|
||||
RadioGroup group = (RadioGroup) findViewById(R.id.switcherFiles);
|
||||
|
||||
fileList.setOnItemClickListener((parent, view, position, id) -> {
|
||||
String chosenElem =
|
||||
(view instanceof TwoLineListItem) ?
|
||||
((TwoLineListItem) view).getText1().getText().toString() :
|
||||
((TextView) view).getText().toString(); // получаем текст нажатого элемента
|
||||
|
||||
File intermid = new File(globalPath + "/" + chosenElem);
|
||||
if(intermid.isDirectory()) {
|
||||
globalPath += "/" + chosenElem;
|
||||
updateListView();
|
||||
}
|
||||
else{
|
||||
openFile(intermid);
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
fileList.setOnItemLongClickListener((parent, view, position, id) -> {
|
||||
String chosenElem =
|
||||
(view instanceof TwoLineListItem) ?
|
||||
((TwoLineListItem) view).getText1().getText().toString() :
|
||||
((TextView) view).getText().toString();
|
||||
|
||||
|
||||
LongPressContextMenu ninja = new LongPressContextMenu(this, globalPath + "/" + chosenElem);
|
||||
return true;
|
||||
});
|
||||
|
||||
group.setOnCheckedChangeListener((group1, checkedId) -> {
|
||||
globalPath = (checkedId == R.id.externalStoreButton) ? externalFiles : internalFiles;
|
||||
updateListView();
|
||||
});
|
||||
|
||||
backButton = (Button)findViewById(R.id.back_button);
|
||||
|
||||
backButton.setOnClickListener(v -> {
|
||||
if(!( globalPath.equals(internalFiles) | globalPath.equals(externalFiles) )
|
||||
& !globalPath.isEmpty()
|
||||
& (new File(globalPath).exists())) {
|
||||
globalPath = globalPath.substring(0, globalPath.lastIndexOf("/"));
|
||||
updateListView();
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
//Настройка языка игры
|
||||
SharedPreferences preferences = PreferenceManager.getDefaultSharedPreferences(this);
|
||||
|
||||
}
|
||||
|
||||
public void readAndSortNumbersFromFile(String fileName) {
|
||||
List<Integer> numbersList = new ArrayList<>();
|
||||
|
||||
try {
|
||||
File file = new File(fileName);
|
||||
BufferedReader bufferedReader = new BufferedReader(new FileReader(file));
|
||||
String line;
|
||||
|
||||
while ((line = bufferedReader.readLine()) != null) {
|
||||
try {
|
||||
// Попытайтесь преобразовать строку в целое число и добавить его в список
|
||||
int number = Integer.parseInt(line);
|
||||
numbersList.add(number);
|
||||
} catch (NumberFormatException e) {
|
||||
// Если строка не является числом, проигнорируйте ее
|
||||
Log.e("FileOperations", "Ошибка при чтении числа: " + line);
|
||||
}
|
||||
}
|
||||
|
||||
bufferedReader.close();
|
||||
|
||||
// Отсортируйте числа в списке
|
||||
Collections.sort(numbersList);
|
||||
|
||||
} catch (IOException e) {
|
||||
Log.e("Time", "Ошибка при чтении файла: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onBackPressed() {
|
||||
backButton.callOnClick();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onCreateOptionsMenu(Menu menu) {
|
||||
getMenuInflater().inflate(R.menu.options, menu);
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onDestroy() {
|
||||
super.onDestroy();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
|
||||
super.onActivityResult(requestCode, resultCode, data);
|
||||
|
||||
switch (requestCode){
|
||||
case OPEN_FILE_ON_REPLACE_REQUEST:{
|
||||
resultListener.onResult(data);
|
||||
}break;
|
||||
|
||||
case READ_FILE_REQUEST_CODE:{
|
||||
openResult.onResult(data);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@SuppressLint("NonConstantResourceId")
|
||||
@Override
|
||||
public boolean onOptionsItemSelected(MenuItem item) {
|
||||
|
||||
int itemId = item.getItemId();
|
||||
if (itemId == R.id.optionRunTheGame) {
|
||||
updateLanguage();
|
||||
runGame();
|
||||
} else if (itemId == R.id.optionSettings) {
|
||||
Intent goToSettings = new Intent(this, SettingsActivity.class);
|
||||
startActivity(goToSettings);
|
||||
} else if (itemId == R.id.optionDeleteData) {
|
||||
AlertDialog.Builder builder = new AlertDialog.Builder(this);
|
||||
builder.setTitle(getString(R.string.remove_action_title));
|
||||
builder.setMessage(getString(R.string.sure_remove_all_data_title));
|
||||
builder.setPositiveButton(R.string.ok_title, (dialogInterface, i) -> {
|
||||
File[] internals = new File(UtilitiesAndData.getInternalStorage()).listFiles();
|
||||
for (File internal : internals) {
|
||||
if (!UtilitiesAndData.isExclusionName(internal.getName())) {
|
||||
internal.delete();
|
||||
}
|
||||
}
|
||||
});
|
||||
builder.setNegativeButton(R.string.cancel_title, null);
|
||||
builder.show();
|
||||
} else if (itemId == R.id.optionCheckRecovers) {
|
||||
Intent goToRecovers = new Intent(this, RecoverListActivity.class);
|
||||
startActivity(goToRecovers);
|
||||
}
|
||||
|
||||
return super.onOptionsItemSelected(item);
|
||||
}
|
||||
|
||||
public void openFile(File url) {
|
||||
File tempFile = null;
|
||||
Intent intent = new Intent(Intent.ACTION_VIEW);
|
||||
|
||||
if(url.getAbsolutePath().contains(UtilitiesAndData.getInternalStorage())){
|
||||
Log.wtf(LOG_TAG, "WTF, man, you cant read my files!!!");
|
||||
|
||||
//Создаем временный файл, там где можем его прочитать
|
||||
Random random = new Random();
|
||||
tempFile = new File(UtilitiesAndData.getExternalStorage() + File.separator + "temp_" + random.nextInt());
|
||||
|
||||
//Копируем тот файл который хотим посмотреть
|
||||
copy(url.getAbsolutePath(), tempFile.getAbsolutePath());
|
||||
|
||||
//Сохраняем ссылку на окрытый файл, в случае его изменения
|
||||
final File openedFile = url;
|
||||
url = tempFile;
|
||||
File finalTempFile = tempFile;
|
||||
|
||||
//Создаем хеш файла для того чтобы его потом сравнить
|
||||
final byte[] compTemp = generateMD5(finalTempFile);
|
||||
|
||||
openResult = new ResultListener(){
|
||||
@Override
|
||||
public void onResult(Object data) {
|
||||
byte[] bytes = generateMD5(finalTempFile);
|
||||
//Если хеши не одинаковы то заменяем одно на другое
|
||||
if(!Arrays.equals(bytes, compTemp))
|
||||
copy(finalTempFile.getAbsolutePath(), openedFile.getAbsolutePath());
|
||||
finalTempFile.delete();
|
||||
}
|
||||
};
|
||||
intent.putExtra("pathToTemp", tempFile.getAbsolutePath());
|
||||
}
|
||||
// Create URI
|
||||
Uri uri = Uri.fromFile(url);
|
||||
|
||||
if (url.toString().contains(".doc") || url.toString().contains(".docx"))
|
||||
intent.setDataAndType(uri, "application/msword");
|
||||
else if(url.toString().contains(".pdf")) {
|
||||
intent.setDataAndType(uri, "application/pdf");
|
||||
} else if(url.toString().contains(".ppt") || url.toString().contains(".pptx")) {
|
||||
intent.setDataAndType(uri, "application/vnd.ms-powerpoint");
|
||||
} else if(url.toString().contains(".xls") || url.toString().contains(".xlsx")) {
|
||||
intent.setDataAndType(uri, "application/vnd.ms-excel");
|
||||
} else if(url.toString().contains(".zip") || url.toString().contains(".rar")) {
|
||||
intent.setDataAndType(uri, "application/x-wav");
|
||||
} else if(url.toString().contains(".rtf")) {
|
||||
intent.setDataAndType(uri, "application/rtf");
|
||||
} else if(url.toString().contains(".wav") || url.toString().contains(".mp3")) {
|
||||
intent.setDataAndType(uri, "audio/x-wav");
|
||||
} else if(url.toString().contains(".gif")) {
|
||||
intent.setDataAndType(uri, "image/gif");
|
||||
} else if(url.toString().contains(".jpg") || url.toString().contains(".jpeg") || url.toString().contains(".png")) {
|
||||
intent.setDataAndType(uri, "image/jpeg");
|
||||
} else if(url.toString().contains(".txt")) {
|
||||
intent.setDataAndType(uri, "text/plain");
|
||||
} else if(url.toString().contains(".3gp") || url.toString().contains(".mpg") || url.toString().contains(".mpeg") || url.toString().contains(".mpe") || url.toString().contains(".mp4") || url.toString().contains(".avi")) {
|
||||
intent.setDataAndType(uri, "video/*");
|
||||
} else {
|
||||
intent.setDataAndType(uri, "*/*");
|
||||
}
|
||||
|
||||
//intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
|
||||
startActivityForResult(intent, READ_FILE_REQUEST_CODE);
|
||||
|
||||
}
|
||||
|
||||
private void runGame() {
|
||||
|
||||
Intent GoToGame = new Intent(this, GameActivity.class);
|
||||
startActivity(GoToGame);
|
||||
|
||||
}
|
||||
|
||||
// TODO Сделать номальную систему учета измения файлов
|
||||
public static void observ(){
|
||||
File save = new File(UtilitiesAndData.getInternalStorage() + File.separator + "files/var/nfstr_save.sb");
|
||||
File fileOut = new File(UtilitiesAndData.getExternalStorage() + File.separator + "Log.txt");
|
||||
File pathToSave = new File(UtilitiesAndData.getExternalStorage() + File.separator + "saves");
|
||||
pathToSave.mkdir();
|
||||
if(!fileOut.exists()) {
|
||||
try {
|
||||
fileOut.createNewFile();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
SimpleDateFormat format = new SimpleDateFormat("yyyy.MM.dd HH:mm:ss", Locale.getDefault());
|
||||
UtilitiesAndData.setLogger(fileOut);
|
||||
observerThread = new Thread(() -> {
|
||||
int count = 1;
|
||||
byte[] lastMD5 = new byte[10];
|
||||
while (true){
|
||||
byte[] md5 = generateMD5(save);
|
||||
if(!Arrays.equals(md5, lastMD5)) {
|
||||
UtilitiesAndData.printLog(format.format(new Date()) + " | " + Utility.bytesToHexString(md5) + "\n");
|
||||
File change = new File(pathToSave.getAbsolutePath() + File.separator + "nfs_save_change_"+ count +".sb");
|
||||
try {
|
||||
change.createNewFile();
|
||||
copy(save, change);
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
lastMD5 = md5;
|
||||
try {
|
||||
Thread.sleep(1000);
|
||||
} catch (InterruptedException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
count++;
|
||||
}
|
||||
});
|
||||
observerThread.start();
|
||||
}
|
||||
|
||||
private <T> List<T> asList(T[] a){
|
||||
return Arrays.asList(a);
|
||||
}
|
||||
|
||||
// TODO реализовать сокрытие лишних папок
|
||||
private List<File> asList(String path){
|
||||
return asList(new File(path).listFiles());
|
||||
}
|
||||
|
||||
private void updateLanguage(){
|
||||
//Получаем текущий язык
|
||||
SharedPreferences preferences = PreferenceManager.getDefaultSharedPreferences(this);
|
||||
String current_lang = preferences.getString(getString(R.string.current_lang), "00");
|
||||
if(current_lang.equals("00")) {
|
||||
Log.e(LOG_TAG, "Not found currentLang preference(");
|
||||
return;
|
||||
}
|
||||
if(current_lang.equals("sys"))
|
||||
current_lang = Locale.getDefault().getLanguage();
|
||||
|
||||
byte[] current_lang_bytes = current_lang.getBytes();
|
||||
|
||||
//Открываем языковой файл и создаем поток чтения
|
||||
File locale = new File(internalFiles + "/files/var/locale");
|
||||
FileInputStream inputStream;
|
||||
|
||||
//Байтовое представление файла
|
||||
byte[] bytes_locale = new byte[4];
|
||||
try {
|
||||
|
||||
inputStream = new FileInputStream(locale);
|
||||
inputStream.read(bytes_locale);
|
||||
|
||||
} catch (FileNotFoundException e) {
|
||||
Log.wtf(LOG_TAG, "No found locale(((((");
|
||||
return;
|
||||
}catch (IOException e){
|
||||
Log.wtf(LOG_TAG, "Couldn't read the locale file((((((");
|
||||
return;
|
||||
}
|
||||
try {
|
||||
if (
|
||||
bytes_locale[2] != current_lang_bytes[0] &
|
||||
bytes_locale[3] != current_lang_bytes[1]
|
||||
) {
|
||||
bytes_locale[2] = current_lang_bytes[0];
|
||||
bytes_locale[3] = current_lang_bytes[1];
|
||||
} else return;
|
||||
}catch (Exception e){
|
||||
return;
|
||||
}
|
||||
|
||||
FileOutputStream outputStream;
|
||||
try {
|
||||
outputStream = new FileOutputStream(locale, false);
|
||||
outputStream.write(bytes_locale, 0, 4);
|
||||
} catch (FileNotFoundException e) {
|
||||
e.printStackTrace();
|
||||
}catch (IOException e){
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public void setResultListener(ResultListener resultListener) {
|
||||
this.resultListener = resultListener;
|
||||
}
|
||||
|
||||
public void updateListView(){
|
||||
fileList.setAdapter(new FileAdapter(getApplicationContext(), asList(globalPath)));
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,72 +0,0 @@
|
||||
package com.ea.ironmonkey.devmenu;
|
||||
|
||||
import android.app.Activity;
|
||||
import android.content.Intent;
|
||||
import android.os.Bundle;
|
||||
|
||||
import com.ea.nimble.ApplicationLifecycle;
|
||||
|
||||
//Активность-марионетка для проверки работы нативных методов жизненного цикла
|
||||
public class PuppetActivity extends Activity {
|
||||
|
||||
@Override
|
||||
protected void onCreate(Bundle savedInstanceState) {
|
||||
super.onCreate(savedInstanceState);
|
||||
ApplicationLifecycle.onActivityCreate(savedInstanceState, this);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onResume() {
|
||||
super.onResume();
|
||||
ApplicationLifecycle.onActivityResume(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onStart() {
|
||||
super.onStart();
|
||||
ApplicationLifecycle.onActivityStart(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onDestroy() {
|
||||
super.onDestroy();
|
||||
ApplicationLifecycle.onActivityDestroy(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onBackPressed() {
|
||||
super.onBackPressed();
|
||||
ApplicationLifecycle.onBackPressed();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
|
||||
super.onActivityResult(requestCode, resultCode, data);
|
||||
ApplicationLifecycle.onActivityResult(resultCode, requestCode, data, this);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onPause() {
|
||||
super.onPause();
|
||||
ApplicationLifecycle.onActivityPause(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onRestart() {
|
||||
super.onRestart();
|
||||
ApplicationLifecycle.onActivityRestart(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onStop() {
|
||||
super.onStop();
|
||||
ApplicationLifecycle.onActivityStop(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onRestoreInstanceState(Bundle savedInstanceState) {
|
||||
super.onRestoreInstanceState(savedInstanceState);
|
||||
ApplicationLifecycle.onActivityRestoreInstanceState(savedInstanceState, this);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,91 +0,0 @@
|
||||
package com.ea.ironmonkey.devmenu;
|
||||
|
||||
import android.app.Activity;
|
||||
import android.app.AlertDialog;
|
||||
import android.database.Cursor;
|
||||
import android.database.sqlite.SQLiteDatabase;
|
||||
import android.os.Bundle;
|
||||
import androidx.annotation.Nullable;
|
||||
import android.widget.ArrayAdapter;
|
||||
import android.widget.ListView;
|
||||
import android.widget.TextView;
|
||||
|
||||
import com.ea.games.nfs13_na.R;
|
||||
import com.ea.ironmonkey.devmenu.util.ReplacementDataBaseHelper;
|
||||
import com.ea.ironmonkey.devmenu.util.UtilitiesAndData;
|
||||
|
||||
import java.util.ArrayList;
|
||||
|
||||
public class RecoverListActivity extends Activity {
|
||||
|
||||
@Override
|
||||
protected void onCreate(@Nullable Bundle savedInstanceState) {
|
||||
super.onCreate(savedInstanceState);
|
||||
|
||||
boolean flag = true;
|
||||
|
||||
getActionBar().setTitle(R.string.recover_file_title);
|
||||
|
||||
ListView view = new ListView(this);
|
||||
|
||||
SQLiteDatabase database = new ReplacementDataBaseHelper(this).getDatabase();
|
||||
|
||||
Cursor cursor = database.rawQuery("SELECT " + ReplacementDataBaseHelper.PATH_TO_REPLACED_ELEMENT + " FROM " + ReplacementDataBaseHelper.MAIN_TABLE_NAME, null);
|
||||
|
||||
ArrayList<String> arrayList = new ArrayList<>();
|
||||
|
||||
ArrayList<String> fullNames = new ArrayList<>();
|
||||
ArrayList<String> shortNames = new ArrayList<>();
|
||||
|
||||
while (cursor.moveToNext()) {
|
||||
String string = cursor.getString(0);
|
||||
fullNames.add(string);
|
||||
int from = string.lastIndexOf("/files/");
|
||||
shortNames.add(string.substring(from));
|
||||
}
|
||||
if(fullNames.isEmpty()){
|
||||
shortNames.add("Не чего заменять!!");
|
||||
flag = false;
|
||||
}
|
||||
boolean thereIsSmthToRecover = flag;
|
||||
|
||||
ArrayAdapter<String> adapter;
|
||||
|
||||
view.setOnItemClickListener((parent, view1, position, id) -> {
|
||||
if(thereIsSmthToRecover){
|
||||
|
||||
TextView textView = (TextView) view1;
|
||||
String s = textView.getText().toString();
|
||||
|
||||
AlertDialog.Builder dialog = new AlertDialog.Builder(this);
|
||||
|
||||
//TODO сделать нормальные строки
|
||||
dialog.setTitle("Воостановить?");
|
||||
|
||||
dialog.setPositiveButton(R.string.ok_title, (dialog1, which) -> {
|
||||
shortNames.remove(s);
|
||||
view.setAdapter(new ArrayAdapter<>(this, android.R.layout.simple_list_item_1, shortNames));
|
||||
String fullName = fullNames.get(position);
|
||||
fullNames.remove(fullName);
|
||||
UtilitiesAndData.recoverFile(fullName);
|
||||
//System.out.println();
|
||||
//TODO Сделать воостановление
|
||||
});
|
||||
|
||||
dialog.setNegativeButton(R.string.cancel_title, (dialog1, which) -> {
|
||||
|
||||
});
|
||||
|
||||
dialog.show();
|
||||
}
|
||||
});
|
||||
|
||||
adapter = new ArrayAdapter<>(this, android.R.layout.simple_list_item_1, shortNames);
|
||||
|
||||
view.setAdapter(adapter);
|
||||
|
||||
setContentView(view);
|
||||
cursor.close();
|
||||
|
||||
}
|
||||
}
|
||||
@@ -1,136 +0,0 @@
|
||||
package com.ea.ironmonkey.devmenu;
|
||||
|
||||
import android.annotation.TargetApi;
|
||||
import android.app.AlertDialog;
|
||||
import android.content.Context;
|
||||
import android.content.Intent;
|
||||
import android.os.Build;
|
||||
import android.os.Bundle;
|
||||
import android.preference.Preference;
|
||||
import android.preference.PreferenceActivity;
|
||||
import android.view.MenuItem;
|
||||
|
||||
import com.ea.games.nfs13_na.BuildConfig;
|
||||
import com.ea.games.nfs13_na.R;
|
||||
import com.ea.ironmonkey.devmenu.dialog.OpenFileDialog;
|
||||
import com.ea.ironmonkey.devmenu.util.SaveManager;
|
||||
import com.ea.ironmonkey.devmenu.dialog.SvmwCreatorDialog;
|
||||
import com.ea.ironmonkey.devmenu.dialog.SvmwInspectorDialog;
|
||||
import com.ea.ironmonkey.devmenu.util.UtilitiesAndData;
|
||||
import com.ea.nimble.ApplicationLifecycle;
|
||||
|
||||
import java.io.File;
|
||||
|
||||
public class SettingsActivity extends PreferenceActivity {
|
||||
|
||||
public static final String LOG_TAG = "SettingActivity";
|
||||
|
||||
private static final int PICKFILE_REQUEST_CODE = 128;
|
||||
public static final int PICK_SVMW_REQUEST_CODE = 129;
|
||||
public static final int PICK_SVMW_IN_CREATE = 228;
|
||||
|
||||
|
||||
@Override
|
||||
protected void onCreate(Bundle savedInstanceState) {
|
||||
super.onCreate(savedInstanceState);
|
||||
addPreferencesFromResource(R.xml.settings_xml);
|
||||
|
||||
ApplicationLifecycle.onActivityCreate(savedInstanceState, this);
|
||||
|
||||
String title = String.format(getString(R.string.dev_menu_title), BuildConfig.DEV_MENU_VERSION);
|
||||
getActionBar().setTitle(title);
|
||||
|
||||
Preference chooseSaveFileButton = findPreference(getString(R.string.choose_save_file_title));
|
||||
Preference chooseSVMWfileButton = findPreference(getString(R.string.choose_svmw_file_title));
|
||||
Preference createSVMWfileButton = findPreference(getString(R.string.create_svmw_file_title));
|
||||
Preference turnOffTheDevMenuButton = findPreference(getString(R.string.switch_off_devmenu_title));
|
||||
|
||||
final Context myContext = this;
|
||||
|
||||
turnOffTheDevMenuButton.setOnPreferenceClickListener(preference -> {
|
||||
AlertDialog.Builder builder = new AlertDialog.Builder(this);
|
||||
builder.setTitle(R.string.switch_off_devmenu_title);
|
||||
builder.setMessage(R.string.msg_devmenu_off);
|
||||
builder.setPositiveButton(R.string.ok_title, (dialog, which) -> UtilitiesAndData.getDevMenuSwitcher().delete());
|
||||
builder.setNegativeButton(R.string.cancel_title, null);
|
||||
builder.show();
|
||||
return true;
|
||||
});
|
||||
|
||||
chooseSaveFileButton.setOnPreferenceClickListener(preference -> {
|
||||
|
||||
OpenFileDialog fileDialog = new OpenFileDialog(myContext);
|
||||
fileDialog
|
||||
.setFilter(".*\\.sb")
|
||||
.setOpenDialogListener(fileName -> {
|
||||
|
||||
File save = new File(fileName);
|
||||
SaveManager manager = new SaveManager(this);
|
||||
manager.loadSaveFile(save);
|
||||
|
||||
});
|
||||
|
||||
fileDialog.show();
|
||||
|
||||
return true;
|
||||
});
|
||||
|
||||
chooseSVMWfileButton.setOnPreferenceClickListener(preference -> {
|
||||
|
||||
Intent intent = new Intent(Intent.ACTION_GET_CONTENT);
|
||||
intent.setType("file/*");
|
||||
startActivityForResult(intent, PICK_SVMW_REQUEST_CODE);
|
||||
//TODO реализовать выбор svmw
|
||||
return true;
|
||||
});
|
||||
|
||||
//По нажатии на кнопку создания svmw файла осуществляется переход в диалог создания svmw
|
||||
createSVMWfileButton.setOnPreferenceClickListener(preference -> {
|
||||
|
||||
SvmwCreatorDialog dialog = new SvmwCreatorDialog(this);
|
||||
dialog.show();
|
||||
|
||||
return true;
|
||||
});
|
||||
|
||||
|
||||
|
||||
getActionBar().setDisplayHomeAsUpEnabled(true);
|
||||
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
|
||||
super.onActivityResult(requestCode, resultCode, data);
|
||||
if(data != null) {
|
||||
switch (requestCode) {
|
||||
case PICKFILE_REQUEST_CODE: {
|
||||
String s = data.getData().toString();
|
||||
String s1 = s.replaceAll("file://", "");
|
||||
File file = new File(s1);
|
||||
}
|
||||
break;
|
||||
case PICK_SVMW_REQUEST_CODE: {
|
||||
String s = data.getData().toString();
|
||||
String s1 = s.replaceAll("file://", "");
|
||||
File file = new File(s1);
|
||||
SvmwInspectorDialog inspectorDialog = new SvmwInspectorDialog(this, file);
|
||||
inspectorDialog.show();
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onOptionsItemSelected(MenuItem item) {
|
||||
if (item.getItemId() == android.R.id.home) {
|
||||
onBackPressed();
|
||||
return true;
|
||||
}
|
||||
return super.onOptionsItemSelected(item);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,60 +0,0 @@
|
||||
package com.ea.ironmonkey.devmenu.components;
|
||||
|
||||
import android.content.Context;
|
||||
import android.util.Log;
|
||||
import android.widget.ArrayAdapter;
|
||||
import android.widget.ListView;
|
||||
import android.widget.TextView;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
/** Динамический список для контекстного меню файла LongPressContextMenu */
|
||||
public class DynamicOptionsListView extends ListView {
|
||||
|
||||
/** Названия позиций в контекстном меню */
|
||||
private List<String> names = new ArrayList<>();
|
||||
private List<OptionAction> actions = new ArrayList<>();
|
||||
private Context context;
|
||||
|
||||
public DynamicOptionsListView(Context context) {
|
||||
super(context);
|
||||
this.context = context;
|
||||
updateList();
|
||||
setOnItemClickListener((parent, view, position, id) -> {
|
||||
try {
|
||||
actions.get(position).action();
|
||||
}catch (IndexOutOfBoundsException e){
|
||||
Log.i("DynamicListView", "No found action to do( in position " + position);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void updateList(){
|
||||
setAdapter(
|
||||
new ArrayAdapter<>(
|
||||
context,
|
||||
android.R.layout.simple_list_item_1,
|
||||
names
|
||||
));
|
||||
}
|
||||
|
||||
public void addOption(String title, OptionAction action){
|
||||
names.add(title);
|
||||
actions.add(action);
|
||||
updateList();
|
||||
}
|
||||
|
||||
public void deleteOption(String title){
|
||||
boolean removeInt = names.remove(title);
|
||||
actions.remove(removeInt);
|
||||
updateList();
|
||||
}
|
||||
|
||||
public String deleteOption(int position){
|
||||
String result = names.remove(position);
|
||||
actions.remove(position);
|
||||
updateList();
|
||||
return result;
|
||||
}
|
||||
}
|
||||
@@ -1,17 +0,0 @@
|
||||
package com.ea.ironmonkey.devmenu.components;
|
||||
|
||||
public interface FileAction {
|
||||
|
||||
void actionReplaceFile();
|
||||
|
||||
void actionRecoverFile();
|
||||
|
||||
void actionRemoveFile();
|
||||
|
||||
void actionTrackTheFile();
|
||||
|
||||
void actionGetPropsOfFile();
|
||||
|
||||
void actionHideTheFile();
|
||||
//sfhsadfhsdjf
|
||||
}
|
||||
@@ -1,205 +0,0 @@
|
||||
package com.ea.ironmonkey.devmenu.components;
|
||||
|
||||
import static com.ea.ironmonkey.devmenu.util.ReplacementDataBaseHelper.MAIN_TABLE_NAME;
|
||||
import static com.ea.ironmonkey.devmenu.util.ReplacementDataBaseHelper.NAME_OF_BACKUPED_ELEMENT;
|
||||
import static com.ea.ironmonkey.devmenu.util.UtilitiesAndData.OPEN_FILE_ON_REPLACE_REQUEST;
|
||||
import static com.ea.ironmonkey.devmenu.util.UtilitiesAndData.copy;
|
||||
import static com.ea.ironmonkey.devmenu.util.UtilitiesAndData.getFileSize;
|
||||
|
||||
import android.app.AlertDialog;
|
||||
import android.content.ContentValues;
|
||||
import android.content.Intent;
|
||||
import android.database.sqlite.SQLiteDatabase;
|
||||
import android.widget.Toast;
|
||||
|
||||
import com.ea.games.nfs13_na.R;
|
||||
import com.ea.ironmonkey.devmenu.MainActivity;
|
||||
import com.ea.ironmonkey.devmenu.util.ReplacementDataBaseHelper;
|
||||
import com.ea.ironmonkey.devmenu.util.ResultListener;
|
||||
import com.ea.ironmonkey.devmenu.util.UtilitiesAndData;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
import java.text.CharacterIterator;
|
||||
import java.text.SimpleDateFormat;
|
||||
import java.text.StringCharacterIterator;
|
||||
import java.util.Date;
|
||||
import java.util.Random;
|
||||
|
||||
/**
|
||||
* Контекстное меню управления данными
|
||||
*/
|
||||
public class LongPressContextMenu extends AlertDialog.Builder implements FileAction {
|
||||
|
||||
private File chosenFile;
|
||||
private MainActivity activity;
|
||||
private static final String LOG_TAG = "LongPressContextMenu";
|
||||
|
||||
private AlertDialog show;
|
||||
private ReplacementDataBaseHelper dataBaseHelper;
|
||||
private SQLiteDatabase writableDatabase;
|
||||
private ContentValues values;
|
||||
|
||||
private File generateReplacementFile(){
|
||||
Random random = new Random();
|
||||
int index = random.nextInt();
|
||||
index = (index < 0) ? index * -1 : index;
|
||||
String nameReplacedOriginal = "replacement_" + index + "";
|
||||
File original = new File(UtilitiesAndData.getReplacementsStorage() + File.separator + nameReplacedOriginal);
|
||||
try {
|
||||
original.createNewFile();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return original;
|
||||
}
|
||||
|
||||
public static String humanReadableByteCountSI(long bytes) {
|
||||
if (-1000 < bytes && bytes < 1000) {
|
||||
return bytes + " B";
|
||||
}
|
||||
CharacterIterator ci = new StringCharacterIterator("kMGTPE");
|
||||
while (bytes <= -999_950 || bytes >= 999_950) {
|
||||
bytes /= 1000;
|
||||
ci.next();
|
||||
}
|
||||
return String.format("%.1f %cB", bytes / 1000.0, ci.current());
|
||||
}
|
||||
|
||||
public LongPressContextMenu(MainActivity activity, String pathToChosenElem) {
|
||||
super(activity);
|
||||
this.activity = activity;
|
||||
chosenFile = new File(pathToChosenElem);
|
||||
DynamicOptionsListView optionsView = new DynamicOptionsListView(activity);
|
||||
|
||||
this.dataBaseHelper = new ReplacementDataBaseHelper(activity);
|
||||
this.writableDatabase = dataBaseHelper.getDatabase();
|
||||
this.values = new ContentValues();
|
||||
|
||||
optionsView.addOption(activity.getString(R.string.replace_file_title), this::actionReplaceFile);
|
||||
optionsView.addOption(activity.getString(R.string.recover_file_title), this::actionRecoverFile);
|
||||
optionsView.addOption(activity.getString(R.string.remove_file_title), this::actionRemoveFile);
|
||||
optionsView.addOption(activity.getString(R.string.track_file_title), this::actionTrackTheFile);
|
||||
optionsView.addOption(activity.getString(R.string.file_props_title), this::actionGetPropsOfFile);
|
||||
optionsView.addOption(activity.getString(R.string.hide_file_title), this::actionHideTheFile);
|
||||
|
||||
setView(optionsView);
|
||||
setTitle(chosenFile.getName()
|
||||
+ " - " +
|
||||
((chosenFile.isDirectory()) ?
|
||||
activity.getString(R.string.folder_title) :
|
||||
activity.getString(R.string.file_title)));
|
||||
|
||||
this.show = show();
|
||||
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public void actionReplaceFile() {
|
||||
Intent chooseFile = new Intent(Intent.ACTION_GET_CONTENT);
|
||||
chooseFile.addCategory(Intent.CATEGORY_OPENABLE);
|
||||
chooseFile.setType("text/plain");
|
||||
activity.setResultListener(new ResultListener() {
|
||||
@Override
|
||||
public void onResult(Object object) {
|
||||
//Реализовать замену и воостановление данных
|
||||
Intent data;
|
||||
if(object instanceof Intent)
|
||||
data = (Intent) object;
|
||||
else return;
|
||||
|
||||
String selectedFileToReplace = "";
|
||||
selectedFileToReplace = data.getData().getPath();
|
||||
|
||||
//Создание файла куда будет складывться замена
|
||||
File replacement = generateReplacementFile();
|
||||
|
||||
//Копирование выбранного оригинального файла в хранилище замен
|
||||
//Иначе говоря, создание резервной копии
|
||||
String path = chosenFile.getAbsolutePath();
|
||||
copy(path, replacement.getPath());
|
||||
|
||||
//Непосредственная замена
|
||||
copy(selectedFileToReplace, path);
|
||||
|
||||
values.put(NAME_OF_BACKUPED_ELEMENT, replacement.getName());
|
||||
values.put(ReplacementDataBaseHelper.PATH_TO_REPLACED_ELEMENT, path);
|
||||
|
||||
//Запись в бд
|
||||
writableDatabase.insert(MAIN_TABLE_NAME, null, values);
|
||||
|
||||
writableDatabase.close();
|
||||
|
||||
activity.updateListView();
|
||||
show.cancel();
|
||||
//TODO Язык!!!!
|
||||
Toast.makeText(activity, "Заменено!", Toast.LENGTH_LONG).show();
|
||||
}
|
||||
});
|
||||
activity.startActivityForResult(
|
||||
Intent.createChooser(chooseFile, "Choose a file"),
|
||||
OPEN_FILE_ON_REPLACE_REQUEST
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void actionRecoverFile() {
|
||||
String path = chosenFile.getAbsolutePath();
|
||||
UtilitiesAndData.recoverFile(path);
|
||||
activity.updateListView();
|
||||
show.cancel();
|
||||
//дщд
|
||||
}
|
||||
|
||||
@Override
|
||||
public void actionRemoveFile() {
|
||||
AlertDialog.Builder dialog = new AlertDialog.Builder(activity);
|
||||
dialog.setTitle(activity.getString(R.string.remove_file_title));
|
||||
String message = String.format(activity.getString(R.string.sure_remove_title), chosenFile.getName());
|
||||
dialog.setMessage(message);
|
||||
|
||||
dialog.setPositiveButton(R.string.ok_title, (dialog1, which) -> {
|
||||
UtilitiesAndData.deleteRecursive(chosenFile);
|
||||
activity.updateListView();
|
||||
});
|
||||
dialog.setNegativeButton(R.string.cancel_title, null);
|
||||
dialog.show();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void actionTrackTheFile() {}
|
||||
|
||||
@Override
|
||||
public void actionGetPropsOfFile() {
|
||||
AlertDialog.Builder dialog = new AlertDialog.Builder(activity);
|
||||
dialog.setTitle(chosenFile.getName()
|
||||
+ " - " +
|
||||
((chosenFile.isDirectory()) ?
|
||||
activity.getString(R.string.folder_title) :
|
||||
activity.getString(R.string.file_title)));
|
||||
|
||||
long lastModified = chosenFile.lastModified();
|
||||
Date date = new Date(lastModified);
|
||||
|
||||
|
||||
SimpleDateFormat sdf = new SimpleDateFormat("dd.MM.yyyy HH:mm:ss:SS");
|
||||
String formattedDate = sdf.format(date);
|
||||
|
||||
long size = getFileSize(chosenFile);
|
||||
|
||||
|
||||
dialog.setMessage(
|
||||
activity.getString(R.string.file_lastmod_title) + "\n" +
|
||||
formattedDate + "\n\n" +
|
||||
activity.getString(R.string.file_size_title) + "\n" +
|
||||
humanReadableByteCountSI(size) + " (" + size + " B)"
|
||||
);
|
||||
dialog.show();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void actionHideTheFile() {
|
||||
|
||||
}
|
||||
}
|
||||
@@ -1,5 +0,0 @@
|
||||
package com.ea.ironmonkey.devmenu.components;
|
||||
|
||||
public interface OptionAction {
|
||||
void action();
|
||||
}
|
||||
@@ -1,246 +0,0 @@
|
||||
package com.ea.ironmonkey.devmenu.dialog;
|
||||
|
||||
import android.app.AlertDialog;
|
||||
import android.content.Context;
|
||||
import android.graphics.Paint;
|
||||
import android.graphics.Point;
|
||||
import android.graphics.Rect;
|
||||
import android.graphics.drawable.Drawable;
|
||||
import android.os.Environment;
|
||||
import android.util.DisplayMetrics;
|
||||
import android.util.TypedValue;
|
||||
import android.view.Display;
|
||||
import android.view.Gravity;
|
||||
import android.view.View;
|
||||
import android.view.ViewGroup;
|
||||
import android.view.WindowManager;
|
||||
import android.widget.ArrayAdapter;
|
||||
import android.widget.LinearLayout;
|
||||
import android.widget.ListView;
|
||||
import android.widget.TextView;
|
||||
import android.widget.Toast;
|
||||
|
||||
import com.ea.games.nfs13_na.R;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.FilenameFilter;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
|
||||
public class OpenFileDialog extends AlertDialog.Builder {
|
||||
|
||||
private String currentPath = Environment.getExternalStorageDirectory().getPath();
|
||||
private FilenameFilter filenameFilter;
|
||||
private List<File> files = new ArrayList<File>();
|
||||
private TextView title;
|
||||
private ListView listView;
|
||||
private int selectedIndex = -1;
|
||||
|
||||
public OpenFileDialog(Context context) {
|
||||
super(context);
|
||||
title = createTitle(context);
|
||||
changeTitle();
|
||||
LinearLayout linearLayout = createMainLayout(context);
|
||||
linearLayout.addView(createBackItem(context));
|
||||
files.addAll(getFiles(currentPath));
|
||||
listView = createListView(context);
|
||||
listView.setAdapter(new FileAdapter(context, files));
|
||||
linearLayout.addView(listView);
|
||||
setCustomTitle(title)
|
||||
.setView(linearLayout)
|
||||
.setPositiveButton(R.string.ok_title, (dialog, which) -> {
|
||||
if (selectedIndex > -1 && listener != null) {
|
||||
listener.OnSelectedFile(listView.getItemAtPosition(selectedIndex).toString());
|
||||
}
|
||||
})
|
||||
.setNegativeButton(R.string.cancel_title, null);
|
||||
}
|
||||
|
||||
@Override
|
||||
public AlertDialog show() {
|
||||
files.addAll(getFiles(currentPath));
|
||||
listView.setAdapter(new FileAdapter(getContext(), files));
|
||||
return super.show();
|
||||
}
|
||||
|
||||
private <T> List<T> asList(T[] a){
|
||||
return Arrays.asList(a);
|
||||
}
|
||||
|
||||
private List<File> getFiles(String directoryPath){
|
||||
File directory = new File(directoryPath);
|
||||
List<File> fileList = asList(directory.listFiles(filenameFilter));
|
||||
Collections.sort(fileList, (file, file2) -> {
|
||||
if (file.isDirectory() && file2.isFile())
|
||||
return -1;
|
||||
else if (file.isFile() && file2.isDirectory())
|
||||
return 1;
|
||||
else
|
||||
return file.getPath().compareTo(file2.getPath());
|
||||
});
|
||||
return fileList;
|
||||
}
|
||||
|
||||
private TextView createTextView(Context context, int style) {
|
||||
TextView textView = new TextView(context);
|
||||
textView.setTextAppearance(context, style);
|
||||
int itemHeight = getItemHeight(context);
|
||||
textView.setLayoutParams(new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, itemHeight));
|
||||
textView.setMinHeight(itemHeight);
|
||||
textView.setGravity(Gravity.CENTER_VERTICAL);
|
||||
textView.setPadding(15, 0, 0, 0);
|
||||
return textView;
|
||||
}
|
||||
|
||||
private int getItemHeight(Context context) {
|
||||
TypedValue value = new TypedValue();
|
||||
DisplayMetrics metrics = new DisplayMetrics();
|
||||
context.getTheme().resolveAttribute(android.R.attr.rowHeight, value, true);
|
||||
getDefaultDisplay(context).getMetrics(metrics);
|
||||
return (int)TypedValue.complexToDimension(value.data, metrics);
|
||||
}
|
||||
|
||||
public int getTextWidth(String text, Paint paint) {
|
||||
Rect bounds = new Rect();
|
||||
paint.getTextBounds(text, 0, text.length(), bounds);
|
||||
return bounds.left + bounds.width() + 80;
|
||||
}
|
||||
|
||||
private void changeTitle() {
|
||||
String titleText = currentPath;
|
||||
int screenWidth = getScreenSize(getContext()).x;
|
||||
int maxWidth = (int) (screenWidth * 0.99);
|
||||
if (getTextWidth(titleText, title.getPaint()) > maxWidth) {
|
||||
while (getTextWidth("..." + titleText, title.getPaint()) > maxWidth)
|
||||
{
|
||||
int start = titleText.indexOf("/", 2);
|
||||
if (start > 0)
|
||||
titleText = titleText.substring(start);
|
||||
else
|
||||
titleText = titleText.substring(2);
|
||||
}
|
||||
title.setText("..." + titleText);
|
||||
} else {
|
||||
title.setText(titleText);
|
||||
}
|
||||
}
|
||||
|
||||
private TextView createTitle(Context context) {
|
||||
TextView textView = new TextView(context);
|
||||
textView.setTextAppearance(context, android.R.style.TextAppearance_DeviceDefault_DialogWindowTitle);
|
||||
int itemHeight = getItemHeight(context);
|
||||
textView.setLayoutParams(new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, itemHeight));
|
||||
textView.setMinHeight(itemHeight);
|
||||
textView.setGravity(Gravity.CENTER_VERTICAL);
|
||||
textView.setPadding(15, 0, 0, 0);
|
||||
textView.setText(currentPath);
|
||||
return textView;
|
||||
}
|
||||
|
||||
private void RebuildFiles(ArrayAdapter<File> adapter) {
|
||||
try{
|
||||
List<File> fileList = getFiles(currentPath);
|
||||
files.clear();
|
||||
selectedIndex = -1;
|
||||
files.addAll(fileList);
|
||||
adapter.notifyDataSetChanged();
|
||||
changeTitle();
|
||||
} catch (NullPointerException e){
|
||||
Toast.makeText(getContext(), android.R.string.unknownName, Toast.LENGTH_SHORT).show();
|
||||
}
|
||||
}
|
||||
|
||||
public OpenFileDialog setFilter(final String filter) {
|
||||
filenameFilter = (file, fileName) -> {
|
||||
File tempFile = new File(String.format("%s/%s", file.getPath(), fileName));
|
||||
if (tempFile.isFile())
|
||||
return tempFile.getName().matches(filter);
|
||||
return true;
|
||||
};
|
||||
return this;
|
||||
}
|
||||
|
||||
private ListView createListView(Context context) {
|
||||
ListView listView = new ListView(context);
|
||||
listView.setOnItemClickListener((adapterView, view, index, l) -> {
|
||||
FileAdapter adapter = (FileAdapter) adapterView.getAdapter();
|
||||
File file = adapter.getItem(index);
|
||||
if (file.isDirectory()) {
|
||||
currentPath = file.getPath();
|
||||
RebuildFiles(adapter);
|
||||
} else {
|
||||
if (index != selectedIndex)
|
||||
selectedIndex = index;
|
||||
else
|
||||
selectedIndex = -1;
|
||||
adapter.notifyDataSetChanged();
|
||||
}
|
||||
});
|
||||
return listView;
|
||||
}
|
||||
|
||||
private static Display getDefaultDisplay(Context context) {
|
||||
return ((WindowManager)context.getSystemService(Context.WINDOW_SERVICE)).getDefaultDisplay();
|
||||
}
|
||||
|
||||
private static Point getScreenSize(Context context) {
|
||||
Point screeSize = new Point();
|
||||
getDefaultDisplay(context).getSize(screeSize);
|
||||
return screeSize;
|
||||
}
|
||||
|
||||
private LinearLayout createMainLayout(Context context) {
|
||||
LinearLayout linearLayout = new LinearLayout(context);
|
||||
linearLayout.setOrientation(LinearLayout.VERTICAL);
|
||||
linearLayout.setMinimumHeight(750);
|
||||
return linearLayout;
|
||||
}
|
||||
|
||||
private TextView createBackItem(Context context) {
|
||||
TextView textView = createTextView(context, android.R.style.TextAppearance_DeviceDefault_Small);
|
||||
Drawable drawable = getContext().getResources().getDrawable(android.R.drawable.ic_menu_directions);
|
||||
drawable.setBounds(0, 0, 60, 60);
|
||||
textView.setCompoundDrawables(drawable, null, null, null);
|
||||
textView.setLayoutParams(new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT));
|
||||
textView.setOnClickListener(view -> {
|
||||
File file = new File(currentPath);
|
||||
File parentDirectory = file.getParentFile();
|
||||
if (parentDirectory != null) {
|
||||
currentPath = parentDirectory.getPath();
|
||||
RebuildFiles(((FileAdapter) listView.getAdapter()));
|
||||
}
|
||||
});
|
||||
return textView;
|
||||
}
|
||||
|
||||
class FileAdapter extends ArrayAdapter<File> {
|
||||
|
||||
public FileAdapter(Context context, List files) {
|
||||
super(context, android.R.layout.simple_list_item_1, files);
|
||||
}
|
||||
|
||||
@Override
|
||||
public View getView(int position, View convertView, ViewGroup parent) {
|
||||
TextView view = (TextView) super.getView(position, convertView, parent);
|
||||
File file = getItem(position);
|
||||
view.setText(file.getName());
|
||||
if (selectedIndex == position)
|
||||
view.setBackgroundColor(getContext().getResources().getColor(android.R.color.holo_blue_light));
|
||||
else
|
||||
view.setBackgroundColor(getContext().getResources().getColor(android.R.color.background_dark));
|
||||
return view;
|
||||
}
|
||||
}
|
||||
|
||||
public interface OpenDialogListener{
|
||||
void OnSelectedFile(String fileName);
|
||||
}
|
||||
private OpenDialogListener listener;
|
||||
|
||||
public OpenFileDialog setOpenDialogListener(OpenDialogListener listener) {
|
||||
this.listener = listener;
|
||||
return this;
|
||||
}
|
||||
}
|
||||
@@ -1,95 +0,0 @@
|
||||
package com.ea.ironmonkey.devmenu.dialog;
|
||||
|
||||
import android.app.Activity;
|
||||
import android.app.AlertDialog;
|
||||
import android.content.Context;
|
||||
import android.content.Intent;
|
||||
import android.view.LayoutInflater;
|
||||
import android.view.View;
|
||||
import android.widget.Button;
|
||||
import android.widget.CheckBox;
|
||||
import android.widget.EditText;
|
||||
import android.widget.ImageButton;
|
||||
import android.widget.Toast;
|
||||
|
||||
import com.ea.games.nfs13_na.R;
|
||||
import com.ea.ironmonkey.devmenu.util.SaveManager;
|
||||
import com.ea.ironmonkey.devmenu.util.UtilitiesAndData;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
|
||||
/**
|
||||
* Диалог для содания бандлов
|
||||
* Сам умеет их создавать
|
||||
*/
|
||||
public class SvmwCreatorDialog extends AlertDialog {
|
||||
|
||||
private EditText nameEdit;
|
||||
private EditText desEdit;
|
||||
private CheckBox isUseCurSaveBox;
|
||||
private View mainView;
|
||||
|
||||
private boolean useCurrentSave;
|
||||
|
||||
private SaveManager manager;
|
||||
private Context context;
|
||||
|
||||
private File svmwPath;
|
||||
|
||||
public SvmwCreatorDialog(Activity activity) {
|
||||
super(activity);
|
||||
context = activity.getApplicationContext();
|
||||
svmwPath = new File(UtilitiesAndData.getExternalStorage() + File.separator + "svmw");
|
||||
svmwPath.mkdir();
|
||||
setTitle("Создание SVMW");
|
||||
ImageButton a;
|
||||
|
||||
Button s;
|
||||
mainView = LayoutInflater
|
||||
.from(context)
|
||||
.inflate(R.layout.saves, null, false);
|
||||
|
||||
nameEdit = (EditText) mainView.findViewById(R.id.name_svmw);
|
||||
desEdit = (EditText) mainView.findViewById(R.id.des_svmw);
|
||||
|
||||
isUseCurSaveBox = (CheckBox) mainView.findViewById(R.id.isUseCurrentSave);
|
||||
manager = new SaveManager(context);
|
||||
|
||||
//Конпка создания
|
||||
setButton(context.getText(R.string.create_svmw_file_title), (dialog, witch) -> {
|
||||
String name = getTextFrom(nameEdit);
|
||||
String des = getTextFrom(desEdit);
|
||||
if(name.isEmpty() | des.isEmpty()){
|
||||
Toast.makeText(context, context.getText(R.string.toast_strings_must_be_entered), Toast.LENGTH_LONG).show();
|
||||
return;
|
||||
}
|
||||
File to = new File(svmwPath.getAbsolutePath() + File.separator + name + ".svmw");
|
||||
try {
|
||||
to.createNewFile();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
manager.createBundleFile(des, to, UtilitiesAndData.getSaveFile());
|
||||
});
|
||||
//Кнопка отмены
|
||||
setButton2(context.getText(R.string.cancel_title), (OnClickListener) null);
|
||||
//Кнопка выбора отдельного файла
|
||||
setButton3(context.getString(R.string.choose_svmw_file_title), (dialog, witch) -> {
|
||||
Intent intent = new Intent(Intent.ACTION_GET_CONTENT);
|
||||
intent.setType("file/*");
|
||||
getOwnerActivity().startActivityForResult(intent, 228);
|
||||
});
|
||||
|
||||
isUseCurSaveBox.setOnCheckedChangeListener((buttonView, isChecked) -> getButton(AlertDialog.BUTTON3).setEnabled(!isChecked));
|
||||
|
||||
|
||||
// Если включена опция "Использовать текущее сохранение" то заюлокировтаь кнопку выбора файла сохранения
|
||||
|
||||
setView(mainView);
|
||||
}
|
||||
|
||||
private String getTextFrom(EditText editText){
|
||||
return editText.getText().toString();
|
||||
}
|
||||
}
|
||||
@@ -1,66 +0,0 @@
|
||||
package com.ea.ironmonkey.devmenu.dialog;
|
||||
|
||||
import android.app.AlertDialog;
|
||||
import android.content.Context;
|
||||
import android.view.LayoutInflater;
|
||||
import android.view.View;
|
||||
import android.widget.TextView;
|
||||
import android.widget.Toast;
|
||||
|
||||
import com.ea.games.nfs13_na.R;
|
||||
import com.ea.ironmonkey.devmenu.util.SaveManager;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.Date;
|
||||
|
||||
/**
|
||||
* Диалог выбора и просмотра информации об svmw файле
|
||||
*/
|
||||
public class SvmwInspectorDialog extends AlertDialog {
|
||||
|
||||
private SaveManager manager;
|
||||
private View mainView;
|
||||
private boolean isWork;
|
||||
private TextView description;
|
||||
private TextView time;
|
||||
|
||||
public SvmwInspectorDialog(Context context, File svmw) {
|
||||
super(context);
|
||||
manager = new SaveManager(context);
|
||||
//Если пришедший файл - svmw иницализируем работу с ним если нет
|
||||
// то выходим
|
||||
// и ничего интересного не показываем((
|
||||
isWork = manager.isSvmwFile(svmw);
|
||||
if(isWork){
|
||||
|
||||
setTitle("Файл - " + svmw.getName());
|
||||
|
||||
mainView = LayoutInflater
|
||||
.from(context)
|
||||
.inflate(R.layout.inspector, null, false);
|
||||
|
||||
description = (TextView) mainView.findViewById(R.id.description);
|
||||
description.setText(manager.getDescriptionOf(svmw));
|
||||
|
||||
time = (TextView) mainView.findViewById(R.id.date);
|
||||
Date dateOfCreate = manager.getDateOfCreateOf(svmw);
|
||||
String format = SaveManager.dateFormat.format(dateOfCreate);
|
||||
time.setText(time.getText() + ": " + format);
|
||||
|
||||
setButton(context.getString(R.string.title_load_svmw), (dialog, which) -> {
|
||||
manager.loadBundleFile(svmw);
|
||||
});
|
||||
setButton2(context.getString(R.string.cancel_title), (OnClickListener) null);
|
||||
|
||||
setView(mainView);
|
||||
|
||||
|
||||
}else Toast.makeText(context, "Это не svmw!", Toast.LENGTH_LONG).show();
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void show() {
|
||||
if(isWork) super.show();
|
||||
}
|
||||
}
|
||||
@@ -1,110 +0,0 @@
|
||||
package com.ea.ironmonkey.devmenu.util;
|
||||
|
||||
import android.util.Log;
|
||||
|
||||
public class Observer {
|
||||
|
||||
private static final String LOG_TAG = "Observer";
|
||||
|
||||
public static void onCallingMethod(Method... states){
|
||||
StackTraceElement[] stackTrace = Thread.currentThread().getStackTrace();
|
||||
|
||||
Log.i(LOG_TAG, "info{");
|
||||
if(states.length != 0){
|
||||
Log.i(LOG_TAG, "States of method:");
|
||||
for(Method mthd : states){
|
||||
Log.i(LOG_TAG, "\t" + mthd.title);
|
||||
}
|
||||
Log.i(LOG_TAG, "\n");
|
||||
}
|
||||
for(int i = 1; i < stackTrace.length; i++) {
|
||||
Log.i(LOG_TAG, "\t" + stackTrace[i]);
|
||||
}
|
||||
Log.i(LOG_TAG, "}");
|
||||
}
|
||||
|
||||
private interface MethodCallingCounter{
|
||||
|
||||
|
||||
void call();
|
||||
|
||||
}
|
||||
|
||||
/** Перечисление состояний методов при из анализе и изменении, доработке */
|
||||
public enum Method implements MethodCallingCounter{
|
||||
/** Состояние невозможгости декомпиляции */
|
||||
IMPOSSIBLE_TO_DECOMPILE("Impossible to decompile"){
|
||||
@Override
|
||||
public void call() {
|
||||
|
||||
}
|
||||
},
|
||||
|
||||
/** Уровни подозртельности работы методов при их воостановлении после
|
||||
декомпиляции, или их доработке и изменеии.
|
||||
|
||||
/** Зеленая зона. Небольшие подозрения */
|
||||
SUSPICIOUS_METHOD("Suspicious method"){
|
||||
@Override
|
||||
public void call() {
|
||||
|
||||
}
|
||||
},
|
||||
|
||||
/** Желтая зона. уже более подозрительны метод, что ставит под вопрос корректоность отрработки некторого функционала */
|
||||
VERY_SUSPICIOUS_METHOD("Very suspicious Method") {
|
||||
@Override
|
||||
public void call() {
|
||||
|
||||
}
|
||||
},
|
||||
|
||||
/** Красная зона. Опасный метод который может привести к фатальным ошибкам */
|
||||
HAZARD_METHOD("Hazard method") {
|
||||
@Override
|
||||
public void call() {
|
||||
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
/** Уровни воостонавливаемости кода */
|
||||
HARD_TO_RECOVER_LOGIC("Hard to recover logic of method") {
|
||||
@Override
|
||||
public void call() {
|
||||
|
||||
}
|
||||
},
|
||||
|
||||
ON_CATCHING_EXCEPTION("on catching exception") {
|
||||
@Override
|
||||
public void call() {
|
||||
|
||||
}
|
||||
},
|
||||
|
||||
RETURN_NULL("Method returns null") {
|
||||
@Override
|
||||
public void call() {
|
||||
|
||||
}
|
||||
},
|
||||
|
||||
SOME_PACKAGE_IS_DELETED("Some package is deleted"){
|
||||
@Override
|
||||
public void call() {
|
||||
|
||||
}
|
||||
};
|
||||
|
||||
private String title;
|
||||
|
||||
Method(String title) {
|
||||
this.title = title;
|
||||
//this.call();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -1,34 +0,0 @@
|
||||
package com.ea.ironmonkey.devmenu.util;
|
||||
|
||||
import android.content.Context;
|
||||
import android.database.sqlite.SQLiteDatabase;
|
||||
import android.database.sqlite.SQLiteOpenHelper;
|
||||
|
||||
public class ReplacementDataBaseHelper extends SQLiteOpenHelper {
|
||||
|
||||
public static final String MAIN_TABLE_NAME = "Replacements";
|
||||
public static final String PATH_TO_REPLACED_ELEMENT = "Path";
|
||||
public static final String NAME_OF_BACKUPED_ELEMENT = "Original_element";
|
||||
private static final int DATABASE_VERSION = 1;
|
||||
|
||||
public SQLiteDatabase getDatabase() {
|
||||
return database;
|
||||
}
|
||||
|
||||
private SQLiteDatabase database;
|
||||
|
||||
|
||||
public ReplacementDataBaseHelper(Context context) {
|
||||
super(context, MAIN_TABLE_NAME + ".db", (SQLiteDatabase.CursorFactory) (db, masterQuery, editTable, query) -> null, DATABASE_VERSION);
|
||||
database = context.openOrCreateDatabase(MAIN_TABLE_NAME + ".db", Context.MODE_PRIVATE, null);
|
||||
database.execSQL("CREATE TABLE IF NOT EXISTS " + MAIN_TABLE_NAME + " (_id INTEGER PRIMARY KEY AUTOINCREMENT, "
|
||||
+ PATH_TO_REPLACED_ELEMENT + " TEXT,"
|
||||
+ NAME_OF_BACKUPED_ELEMENT + " TEXT);");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onCreate(SQLiteDatabase db) {}
|
||||
|
||||
@Override
|
||||
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {}
|
||||
}
|
||||
@@ -1,7 +0,0 @@
|
||||
package com.ea.ironmonkey.devmenu.util;
|
||||
|
||||
public interface ResultListener {
|
||||
|
||||
default void onResult(Object data){}
|
||||
|
||||
}
|
||||
@@ -1,186 +0,0 @@
|
||||
package com.ea.ironmonkey.devmenu.util;
|
||||
|
||||
import android.content.Context;
|
||||
import android.util.Log;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.FileInputStream;
|
||||
import java.io.FileNotFoundException;
|
||||
import java.io.FileOutputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.io.OutputStream;
|
||||
import java.nio.ByteBuffer;
|
||||
import java.nio.ByteOrder;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
import java.text.ParseException;
|
||||
import java.text.SimpleDateFormat;
|
||||
import java.util.Date;
|
||||
|
||||
/**
|
||||
* Менедженер создания и загрузки сохранений в игру<br/>
|
||||
* Создает bundle-файлы .svmw и загружает их<br/>
|
||||
* Умеет загружать обчные .sb сохранения в игру
|
||||
*/
|
||||
public class SaveManager {
|
||||
|
||||
private Context context;
|
||||
private static final String LOG_TAG = "SaveManager";
|
||||
private static final byte[] svmw_header = "SVMW".getBytes(StandardCharsets.UTF_8);
|
||||
private static final byte[] save_header = "SBIN".getBytes(StandardCharsets.UTF_8);
|
||||
public static final String dateFormatStr = "dd.MM.yy:hh:mm:ss";
|
||||
public static final SimpleDateFormat dateFormat = new SimpleDateFormat(dateFormatStr);
|
||||
|
||||
public SaveManager(Context context) {
|
||||
this.context = context;
|
||||
}
|
||||
|
||||
public File createBundleFile(String description, File fileToSave, File save) {
|
||||
|
||||
if (fileToSave.exists()) fileToSave.delete();
|
||||
|
||||
try {
|
||||
fileToSave.createNewFile();
|
||||
FileOutputStream fos = new FileOutputStream(fileToSave);
|
||||
|
||||
Date date = new Date();
|
||||
|
||||
Long time = date.getTime();
|
||||
|
||||
ByteBuffer bb = ByteBuffer.allocate(Long.SIZE);
|
||||
bb.order(ByteOrder.LITTLE_ENDIAN);
|
||||
bb.putLong(time);
|
||||
bb.flip();
|
||||
//bb.
|
||||
String curDate = dateFormat.format(new Date());
|
||||
|
||||
fos.write(svmw_header);
|
||||
fos.write(curDate.getBytes(StandardCharsets.UTF_8));
|
||||
fos.write(description.getBytes(StandardCharsets.UTF_8));
|
||||
fos.write(UtilitiesAndData.fileAsByteArray(save));
|
||||
} catch (IOException e) {
|
||||
Log.i("lol", fileToSave.getAbsolutePath());
|
||||
//fileToSave.getAbsolutePath()
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
return fileToSave;
|
||||
}
|
||||
|
||||
public void loadBundleFile(File svmw) {
|
||||
|
||||
if(isSvmwFile(svmw)){
|
||||
byte[] byteFile = UtilitiesAndData.fileAsByteArray(svmw);
|
||||
int headerInByteFile = UtilitiesAndData.findHeaderInByteFile(byteFile, save_header);
|
||||
byte[] result = new byte[byteFile.length - headerInByteFile];
|
||||
System.arraycopy(byteFile, headerInByteFile, result, 0, result.length);
|
||||
File dest = new File("/data/data/" + context.getPackageName() + "/files/var/nfstr_save.sb");
|
||||
if(!dest.exists()) {
|
||||
try {
|
||||
dest.createNewFile();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
try {
|
||||
FileOutputStream fos = new FileOutputStream(dest);
|
||||
fos.write(result);
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public String getDescriptionOf(File svmw){
|
||||
if(isSvmwFile(svmw)){
|
||||
int offset = svmw_header.length + dateFormatStr.length();
|
||||
byte[] byteFile = UtilitiesAndData.fileAsByteArray(svmw);
|
||||
int headerInByteFile = UtilitiesAndData.findHeaderInByteFile(byteFile, save_header);
|
||||
return new String(byteFile, offset, headerInByteFile - offset, StandardCharsets.UTF_8);
|
||||
}
|
||||
Log.i(LOG_TAG, "getDescription(), this is not a svmw file((( Return empty description(((");
|
||||
return "";
|
||||
}
|
||||
|
||||
public Date getDateOfCreateOf(File svmw){
|
||||
if(isSvmwFile(svmw)){
|
||||
int offset = svmw_header.length;
|
||||
byte[] byteFile = UtilitiesAndData.fileAsByteArray(svmw);
|
||||
|
||||
String s = new String(byteFile, offset, dateFormatStr.length(), StandardCharsets.UTF_8);
|
||||
|
||||
try {
|
||||
return dateFormat.parse(s);
|
||||
} catch (ParseException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
Log.i(LOG_TAG, "getDateOfCreateOf, this is not a svmw file((( Return null date(((");
|
||||
return null;
|
||||
}
|
||||
|
||||
public void loadSaveFile(File save) {
|
||||
if(isSaveFile(save)){
|
||||
copySave(save);
|
||||
}
|
||||
}
|
||||
|
||||
public boolean isSaveFile(File save) {
|
||||
if(!save.exists() | isEmptyFile(save)) return false;
|
||||
byte[] arr = UtilitiesAndData.fileAsByteArray(save);
|
||||
for (int i = 0; i < save_header.length; i++)
|
||||
if (save_header[i] != arr[i]) return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
public boolean isSvmwFile(File svmw) {
|
||||
if(!svmw.exists() | isEmptyFile(svmw)) return false;
|
||||
byte[] arr = UtilitiesAndData.fileAsByteArray(svmw);
|
||||
for (int i = 0; i < svmw_header.length; i++)
|
||||
if (svmw_header[i] != arr[i]) return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
public boolean isEmptyFile(File file){
|
||||
return UtilitiesAndData.fileAsByteArray(file).length == 0;
|
||||
}
|
||||
|
||||
|
||||
public void copySave(File save){
|
||||
|
||||
File source = save;
|
||||
|
||||
File dest = new File("/data/data/" + context.getPackageName() + "/files/var/nfstr_save.sb");
|
||||
|
||||
|
||||
if(!dest.exists()) {
|
||||
try {
|
||||
dest.createNewFile();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
InputStream is = null;
|
||||
OutputStream os = null;
|
||||
try {
|
||||
is = new FileInputStream(source);
|
||||
os = new FileOutputStream(dest);
|
||||
byte[] buffer = new byte[1024];
|
||||
int length;
|
||||
while ((length = is.read(buffer)) > 0) {
|
||||
os.write(buffer, 0, length);
|
||||
}
|
||||
is.close();
|
||||
os.close();
|
||||
} catch (FileNotFoundException e) {
|
||||
e.printStackTrace();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@@ -1,290 +0,0 @@
|
||||
package com.ea.ironmonkey.devmenu.util;
|
||||
|
||||
import static com.ea.ironmonkey.devmenu.util.ReplacementDataBaseHelper.MAIN_TABLE_NAME;
|
||||
import static com.ea.ironmonkey.devmenu.util.ReplacementDataBaseHelper.NAME_OF_BACKUPED_ELEMENT;
|
||||
import static com.ea.ironmonkey.devmenu.util.ReplacementDataBaseHelper.PATH_TO_REPLACED_ELEMENT;
|
||||
|
||||
import android.content.Context;
|
||||
import android.database.Cursor;
|
||||
import android.database.sqlite.SQLiteDatabase;
|
||||
import android.os.Environment;
|
||||
import android.util.Log;
|
||||
import org.apache.commons.codec.digest.DigestUtils;
|
||||
import java.io.File;
|
||||
import java.io.FileInputStream;
|
||||
import java.io.FileNotFoundException;
|
||||
import java.io.FileOutputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.io.OutputStream;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
import java.util.Arrays;
|
||||
import java.util.HashSet;
|
||||
import java.util.LinkedList;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
public class UtilitiesAndData {
|
||||
|
||||
private static Context context;
|
||||
private static FileOutputStream stream;
|
||||
public static final int OPEN_FILE_ON_REPLACE_REQUEST = 100;
|
||||
public static final int READ_FILE_REQUEST_CODE = 101;
|
||||
|
||||
private static final String LOG_TAG = "UtilitiesAndData";
|
||||
|
||||
public static void init(Context context){
|
||||
UtilitiesAndData.context = context;
|
||||
}
|
||||
|
||||
public static void setLogger(File file){
|
||||
if(file.exists()){
|
||||
try {
|
||||
stream = new FileOutputStream(file);
|
||||
} catch (FileNotFoundException e) {
|
||||
Log.wtf(LOG_TAG, "cant create out stream(((");
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public static void deleteRecursive(File fileOrDirectory) {
|
||||
if (fileOrDirectory.isDirectory())
|
||||
for (File child : fileOrDirectory.listFiles())
|
||||
deleteRecursive(child);
|
||||
|
||||
fileOrDirectory.delete();
|
||||
}
|
||||
|
||||
public static boolean isLoggerEnabled(){
|
||||
return stream != null;
|
||||
}
|
||||
|
||||
public static void printLog(String msg){
|
||||
try{
|
||||
if(isLoggerEnabled())
|
||||
stream.write(msg.getBytes(StandardCharsets.UTF_8));
|
||||
} catch (IOException e) {
|
||||
Log.wtf(LOG_TAG, "cant write to stream(((");
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
public static String getInternalStorage(){
|
||||
return "/data/data/" + context.getPackageName();
|
||||
}
|
||||
|
||||
public static String getExternalStorage(){
|
||||
return Environment.getExternalStorageDirectory().getAbsolutePath() + "/Android/data/" + context.getPackageName() + "/files";
|
||||
}
|
||||
|
||||
public static File getDevMenuSwitcher(){
|
||||
return new File(UtilitiesAndData.getExternalStorage() + File.separator + "DevMenu");
|
||||
}
|
||||
|
||||
public static File getSaveFile(){
|
||||
File save = new File(getInternalStorage() + File.separator + "files" + File.separator + "var" + File.separator + "nfstr_save.sb");
|
||||
if(!save.exists()) {
|
||||
try {
|
||||
save.createNewFile();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
return save;
|
||||
}
|
||||
|
||||
public static String getReplacementsStorage(){
|
||||
return getInternalStorage() + File.separator + "replace";
|
||||
}
|
||||
|
||||
public static boolean isFirstRun(){
|
||||
File temp = new File(getInternalStorage() + File.separator + "load");
|
||||
try {
|
||||
if(!temp.exists()){
|
||||
temp.createNewFile();
|
||||
return true;
|
||||
}
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
private static final String[] exclusionNamesArr = {
|
||||
|
||||
"replace",
|
||||
"lib",
|
||||
"databases"
|
||||
|
||||
};
|
||||
|
||||
public static void copy(File from, File to){
|
||||
copy(from.getAbsolutePath(), to.getAbsolutePath());
|
||||
}
|
||||
|
||||
public static void copy(String from, String to) {
|
||||
File source = new File(from);
|
||||
|
||||
File dest = new File(to);
|
||||
|
||||
|
||||
if (!dest.exists()) {
|
||||
try {
|
||||
dest.createNewFile();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
InputStream is = null;
|
||||
OutputStream os = null;
|
||||
try {
|
||||
is = new FileInputStream(source);
|
||||
os = new FileOutputStream(dest);
|
||||
Math.max(getFileSize(source), getFileSize(dest));
|
||||
byte[] buffer = new byte[1024];
|
||||
int length;
|
||||
while ((length = is.read(buffer)) > 0) {
|
||||
os.write(buffer, 0, length);
|
||||
}
|
||||
is.close();
|
||||
os.close();
|
||||
} catch (FileNotFoundException e) {
|
||||
Log.e("lol", e.toString());
|
||||
e.printStackTrace();
|
||||
} catch (IOException e) {
|
||||
Log.e("lol1", e.toString());
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
public static long getFileSize(final File file) {
|
||||
if (file == null || !file.exists())
|
||||
return 0;
|
||||
if (!file.isDirectory())
|
||||
return file.length();
|
||||
final List<File> dirs = new LinkedList<>();
|
||||
dirs.add(file);
|
||||
long result = 0;
|
||||
while (!dirs.isEmpty()) {
|
||||
final File dir = dirs.remove(0);
|
||||
if (!dir.exists())
|
||||
continue;
|
||||
final File[] listFiles = dir.listFiles();
|
||||
if (listFiles == null || listFiles.length == 0)
|
||||
continue;
|
||||
for (final File child : listFiles) {
|
||||
result += child.length();
|
||||
if (child.isDirectory())
|
||||
dirs.add(child);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
private static final Set<String> exclusionNames = new HashSet<>(Arrays.asList(exclusionNamesArr));
|
||||
|
||||
public static boolean isExclusionName(String name){
|
||||
return exclusionNames.contains(name);
|
||||
}
|
||||
|
||||
|
||||
public static void recoverFile(String path){
|
||||
ReplacementDataBaseHelper dataBaseHelper = new ReplacementDataBaseHelper(context);
|
||||
SQLiteDatabase writableDatabase = dataBaseHelper.getDatabase();
|
||||
Cursor query = writableDatabase.rawQuery("SELECT " + PATH_TO_REPLACED_ELEMENT + " , " + NAME_OF_BACKUPED_ELEMENT + " FROM " + MAIN_TABLE_NAME + " WHERE " + PATH_TO_REPLACED_ELEMENT + " = \"" + path + "\"", null);
|
||||
if(query.getCount() == 1) {
|
||||
query.moveToFirst();
|
||||
//Путь к заменяемому файлу
|
||||
String pathToReplace = query.getString(query.getColumnIndex(PATH_TO_REPLACED_ELEMENT));
|
||||
//Имя бэкапа
|
||||
String nameFile = query.getString(query.getColumnIndex(NAME_OF_BACKUPED_ELEMENT));
|
||||
|
||||
//Файл замены
|
||||
File toReplace = new File(pathToReplace);
|
||||
|
||||
//Файл бэкапа
|
||||
File backup = new File(UtilitiesAndData.getReplacementsStorage() + File.separator + nameFile);
|
||||
|
||||
copy(backup, toReplace);
|
||||
|
||||
writableDatabase.delete(MAIN_TABLE_NAME, PATH_TO_REPLACED_ELEMENT + " = ?", new String[]{path});
|
||||
backup.delete();
|
||||
}
|
||||
|
||||
query.close();
|
||||
}
|
||||
|
||||
public static byte[] generateMD5(File file){
|
||||
try {
|
||||
return DigestUtils.md5(new FileInputStream(file));
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return new byte[1];
|
||||
}
|
||||
|
||||
public static void getInfoAboutFile(File file){
|
||||
Log.i(LOG_TAG, "Info about File -> " + file.getAbsolutePath());
|
||||
if(file.exists()){
|
||||
if(file.isFile()) {
|
||||
Log.i(LOG_TAG, "isCanRead = " + file.canRead());
|
||||
Log.i(LOG_TAG, "isCanWrite = " + file.canWrite());
|
||||
Log.i(LOG_TAG, "isCanExecute = " + file.canExecute());
|
||||
}else
|
||||
Log.i(LOG_TAG, "its dir!");
|
||||
}else
|
||||
Log.wtf(LOG_TAG, "it does not exists!");
|
||||
}
|
||||
|
||||
public static byte[] fileAsByteArray(File file){
|
||||
byte[] b = new byte[(int) file.length()];
|
||||
try {
|
||||
FileInputStream fileInputStream = new FileInputStream(file);
|
||||
fileInputStream.read(b);
|
||||
} catch (Exception e) {
|
||||
return null;
|
||||
}
|
||||
return b;
|
||||
}
|
||||
|
||||
public static void saveBytesToFile(byte[] bytes, File saveTo){
|
||||
try{
|
||||
saveTo.createNewFile();
|
||||
FileOutputStream outputStream = new FileOutputStream(saveTo);
|
||||
outputStream.write(bytes);
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
public static int findHeaderInByteFile(byte[] byteFile, byte[] header){
|
||||
int[] pf = prefix(header);
|
||||
int index = 0;
|
||||
for (int i = 0; i < byteFile.length; i++){
|
||||
while (index > 0 && header[index] != byteFile[i]) index = pf[index - 1];
|
||||
if (header[index] == byteFile[i]) index++;
|
||||
if (index == header.length) return i - index + 1;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
/**
|
||||
* Префикс функция для алгоритма КМП
|
||||
*/
|
||||
private static int[] prefix(byte[] s) {
|
||||
int[] result = new int[s.length];
|
||||
result[0] = 0;
|
||||
int index = 0;
|
||||
|
||||
for (int i = 1; i < s.length; i++) {
|
||||
while (index >= 0 && s[index] != s[i]) { index--; }
|
||||
index++;
|
||||
result[i] = index;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
}
|
||||
Reference in New Issue
Block a user