Skip to content

Commit

Permalink
Structuring and adding LogView
Browse files Browse the repository at this point in the history
- move classes in sub packages for a better structure
- add a log view
- add log handlers to write log files. The format is one json serialized `LogEntity` per line
  • Loading branch information
BentiGorlich committed Sep 26, 2023
1 parent dc993a2 commit ccf3374
Show file tree
Hide file tree
Showing 22 changed files with 370 additions and 40 deletions.
17 changes: 12 additions & 5 deletions app/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
<uses-permission android:name="android.permission.INTERNET" />

<application
android:name=".Mimic3TTSEngineWrapperApp"
android:name=".tts.Mimic3TTSEngineWrapperApp"
android:allowBackup="true"
android:dataExtractionRules="@xml/data_extraction_rules"
android:fullBackupContent="@xml/backup_rules"
Expand All @@ -16,41 +16,48 @@
android:theme="@style/Theme.Mimic3TTSEngineWrapper"
tools:targetApi="31">
<activity
android:name=".CheckTTSDataActivity"
android:name=".activities.LogActivity"
android:exported="false" />
<activity
android:name=".activities.CheckTTSDataActivity"
android:exported="true"
android:theme="@style/Theme.Mimic3TTSEngineWrapper">
<intent-filter>
<action android:name="android.speech.tts.engine.CHECK_TTS_DATA" />
<action android:name="android.speech.tts.engine.GET_SAMPLE_TEXT" />
<action android:name="android.speech.tts.engine.INSTALL_TTS_DATA" />
<action android:name="android.speech.tts.engine.CONFIGURE_ENGINE" />

<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
</activity>
<activity
android:name=".SettingsActivity"
android:name=".activities.SettingsActivity"
android:exported="false"
android:label="@string/title_activity_settings"
android:theme="@style/Theme.Mimic3TTSEngineWrapper" />
<activity
android:name=".MainActivity"
android:name=".activities.MainActivity"
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.MAIN" />

<category android:name="android.intent.category.LAUNCHER" />

<action android:name="android.speech.tts.engine.CONFIGURE_ENGINE" />
</intent-filter>
</activity>

<service
android:name=".Mimic3TTSEngineWeb"
android:name=".tts.Mimic3TTSEngineWeb"
android:description="@string/service_description"
android:directBootAware="true"
android:enabled="true"
android:exported="true"
android:label="@string/service_name">
<intent-filter>
<action android:name="android.intent.action.TTS_SERVICE" />

<category android:name="android.intent.category.DEFAULT" />
</intent-filter>

Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package de.bentigorlich.mimic3ttsenginewrapper;
package de.bentigorlich.mimic3ttsenginewrapper.activities;

import android.app.Activity;
import android.content.Intent;
Expand All @@ -13,6 +13,9 @@
import java.util.logging.LogManager;
import java.util.logging.Logger;

import de.bentigorlich.mimic3ttsenginewrapper.tts.Mimic3TTSEngineWeb;
import de.bentigorlich.mimic3ttsenginewrapper.entities.MimicVoice;

public class CheckTTSDataActivity extends Activity {

Logger _Logger;
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,125 @@
package de.bentigorlich.mimic3ttsenginewrapper.activities;

import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;

import android.app.Activity;
import android.os.Bundle;
import android.view.MenuItem;
import android.widget.LinearLayout;
import android.widget.TextView;

import com.google.gson.Gson;

import java.io.BufferedReader;
import java.io.File;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Comparator;
import java.util.List;
import java.util.Timer;
import java.util.TimerTask;

import de.bentigorlich.mimic3ttsenginewrapper.R;
import de.bentigorlich.mimic3ttsenginewrapper.entities.LogEntity;

public class LogActivity extends AppCompatActivity {
Timer refreshLogInterval;

@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_log);

Activity parent = this;
refreshLogInterval = new Timer();
refreshLogInterval.schedule(new TimerTask() {
@Override
public void run() {
parent.runOnUiThread(() -> populateLogView());
}
}, 0, 10000);
}

@Override
protected void onDestroy() {
super.onDestroy();
refreshLogInterval.cancel();
}

private void populateLogView() {
Gson gson = new Gson();
List<LogEntity> logs = new ArrayList<>();
for (File logFile : getLogFiles()) {
try {
BufferedReader br = new BufferedReader(new FileReader(logFile));
br.lines().forEach(line -> {
LogEntity lr = gson.fromJson(line, LogEntity.class);
logs.add(lr);
});
br.close();
} catch (IOException ignored) {
}
}

logs.sort(Comparator.comparing(l -> l.Timestamp));

LinearLayout logView = findViewById(R.id.logContainer);
logView.removeAllViews();
for (LogEntity curr : logs) {
TextView t = new TextView(this);
t.setText(curr.GetText(false));
t.setTextColor(getLevelColor(curr.Level));
t.setTextIsSelectable(true);
logView.addView(t);
}
}

private int getLevelColor(String level) {
switch (level.toLowerCase()) {
case "info":
default:
return getResources().getColor(com.google.android.material.R.color.design_default_color_surface, getTheme());

case "warning":
return getResources().getColor(R.color.colorTextWarning, getTheme());

case "severe":
return getResources().getColor(R.color.colorTextSevere, getTheme());
}
}

private List<File> getLogFiles() {
File cacheDir = getDataDir();
List<File> logList = new ArrayList<>();
File[] fileList = cacheDir.listFiles();
for (File f: fileList) {
String fileName = f.getName();
int pointIndex = fileName.lastIndexOf(".");
if(f.exists() && pointIndex > 0) {
String ext = fileName.substring(pointIndex);
if(ext.equals(".log")) {
logList.add(f);
}
}
}
return logList;
}

public void onMenuItemClick(@NonNull MenuItem menuItem) {
if (menuItem.getItemId() == R.id.menu_logs_delete) {
for(File f : getLogFiles()) {
try {
FileWriter fw = new FileWriter(f.getAbsolutePath(), false);
fw.write("");
fw.close();
} catch (IOException e) {
e.printStackTrace();
}
}
populateLogView();
}
}
}
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
package de.bentigorlich.mimic3ttsenginewrapper;
package de.bentigorlich.mimic3ttsenginewrapper.activities;

import static de.bentigorlich.mimic3ttsenginewrapper.Mimic3TTSEngineWrapperApp.PREF_AUDIO_VOLATILITY;
import static de.bentigorlich.mimic3ttsenginewrapper.Mimic3TTSEngineWrapperApp.PREF_CACHE_ACTIVATE;
import static de.bentigorlich.mimic3ttsenginewrapper.Mimic3TTSEngineWrapperApp.PREF_LANGUAGE;
import static de.bentigorlich.mimic3ttsenginewrapper.Mimic3TTSEngineWrapperApp.PREF_PHONEME_VOLATILITY;
import static de.bentigorlich.mimic3ttsenginewrapper.Mimic3TTSEngineWrapperApp.PREF_SERVER_ADDRESS;
import static de.bentigorlich.mimic3ttsenginewrapper.Mimic3TTSEngineWrapperApp.PREF_SPEAKER;
import static de.bentigorlich.mimic3ttsenginewrapper.Mimic3TTSEngineWrapperApp.PREF_SPEED;
import static de.bentigorlich.mimic3ttsenginewrapper.Mimic3TTSEngineWrapperApp.PREF_VOICE;
import static de.bentigorlich.mimic3ttsenginewrapper.tts.Mimic3TTSEngineWrapperApp.PREF_AUDIO_VOLATILITY;
import static de.bentigorlich.mimic3ttsenginewrapper.tts.Mimic3TTSEngineWrapperApp.PREF_CACHE_ACTIVATE;
import static de.bentigorlich.mimic3ttsenginewrapper.tts.Mimic3TTSEngineWrapperApp.PREF_LANGUAGE;
import static de.bentigorlich.mimic3ttsenginewrapper.tts.Mimic3TTSEngineWrapperApp.PREF_PHONEME_VOLATILITY;
import static de.bentigorlich.mimic3ttsenginewrapper.tts.Mimic3TTSEngineWrapperApp.PREF_SERVER_ADDRESS;
import static de.bentigorlich.mimic3ttsenginewrapper.tts.Mimic3TTSEngineWrapperApp.PREF_SPEAKER;
import static de.bentigorlich.mimic3ttsenginewrapper.tts.Mimic3TTSEngineWrapperApp.PREF_SPEED;
import static de.bentigorlich.mimic3ttsenginewrapper.tts.Mimic3TTSEngineWrapperApp.PREF_VOICE;

import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;
Expand All @@ -27,14 +27,23 @@
import android.widget.SeekBar;
import android.widget.Spinner;

import java.io.IOException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.logging.FileHandler;
import java.util.logging.LogManager;
import java.util.logging.Logger;

import de.bentigorlich.mimic3ttsenginewrapper.tts.Mimic3TTSEngineWeb;
import de.bentigorlich.mimic3ttsenginewrapper.tts.Mimic3TTSEngineWrapperApp;
import de.bentigorlich.mimic3ttsenginewrapper.entities.MimicVoice;
import de.bentigorlich.mimic3ttsenginewrapper.R;
import de.bentigorlich.mimic3ttsenginewrapper.tts.SynthesisListener;
import de.bentigorlich.mimic3ttsenginewrapper.util.JsonFormatter;

public class MainActivity extends AppCompatActivity implements SeekBar.OnSeekBarChangeListener,
AdapterView.OnItemSelectedListener, View.OnClickListener, Mimic3TTSEngineWeb.OnVoicesLoadedListener,
SharedPreferences.OnSharedPreferenceChangeListener, Mimic3TTSEngineWeb.OnLoadedListener, Mimic3TTSEngineWeb.OnErrorListener {
Expand All @@ -55,6 +64,7 @@ public class MainActivity extends AppCompatActivity implements SeekBar.OnSeekBar
public MainActivity() {
_Logger = Logger.getLogger(this.getClass().toString());
LogManager.getLogManager().addLogger(_Logger);

}

@Override
Expand All @@ -64,6 +74,18 @@ protected void onCreate(Bundle savedInstanceState) {
setSupportActionBar(findViewById(R.id.toolbar));
setContentView(R.layout.activity_main);

String cacheDir = getDataDir().getAbsolutePath();
try {
FileHandler fileHandler = new FileHandler(cacheDir + "/main_%g.log", 1024 * 1024, 1, true);
fileHandler.setFormatter(new JsonFormatter());
_Logger.addHandler(fileHandler);
} catch (IOException e) {
_Logger.severe("IOException while adding filehandler to logger: " + e.getMessage());
for(StackTraceElement el : e.getStackTrace()) {
_Logger.warning("at: " + el.toString());
}
}

SharedPreferences = PreferenceManager.getDefaultSharedPreferences(Mimic3TTSEngineWrapperApp.getStorageContext());
SharedPreferences.registerOnSharedPreferenceChangeListener(this);
SelectedLanguage = SharedPreferences.getString(PREF_LANGUAGE, "");
Expand All @@ -76,7 +98,7 @@ protected void onCreate(Bundle savedInstanceState) {
Mimic3TTSEngineWeb.s_ServerAddress = SharedPreferences.getString(PREF_SERVER_ADDRESS, "");
Mimic3TTSEngineWeb.addLoadedListener(this);
if (Mimic3TTSEngineWeb.s_RunningService == null) {
Intent startIntent = new Intent(MainActivity.this, de.bentigorlich.mimic3ttsenginewrapper.Mimic3TTSEngineWeb.class);
Intent startIntent = new Intent(MainActivity.this, Mimic3TTSEngineWeb.class);
startIntent.putExtra(PREF_SERVER_ADDRESS, Mimic3TTSEngineWeb.s_ServerAddress);
startService(startIntent);
} else {
Expand Down Expand Up @@ -280,6 +302,8 @@ public void onClick(View view) {
public void onMenuItemClick(@NonNull MenuItem menuItem) {
if (menuItem.getItemId() == R.id.menu_settings) {
startActivity(new Intent(MainActivity.this, SettingsActivity.class));
} else if (menuItem.getItemId() == R.id.menu_logs) {
startActivity(new Intent(MainActivity.this, LogActivity.class));
}
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package de.bentigorlich.mimic3ttsenginewrapper;
package de.bentigorlich.mimic3ttsenginewrapper.activities;

import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;
Expand All @@ -10,6 +10,10 @@
import android.content.SharedPreferences;
import android.os.Bundle;

import de.bentigorlich.mimic3ttsenginewrapper.tts.Mimic3TTSEngineWeb;
import de.bentigorlich.mimic3ttsenginewrapper.tts.Mimic3TTSEngineWrapperApp;
import de.bentigorlich.mimic3ttsenginewrapper.R;

public class SettingsActivity extends AppCompatActivity implements Mimic3TTSEngineWeb.OnErrorListener, Preference.OnPreferenceChangeListener {

@Override
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package de.bentigorlich.mimic3ttsenginewrapper;
package de.bentigorlich.mimic3ttsenginewrapper.activities;

import android.app.AlertDialog;
import android.os.Bundle;
Expand All @@ -7,6 +7,9 @@
import androidx.preference.Preference;
import androidx.preference.PreferenceFragmentCompat;

import de.bentigorlich.mimic3ttsenginewrapper.tts.Mimic3TTSEngineWeb;
import de.bentigorlich.mimic3ttsenginewrapper.R;

public class SettingsFragment extends PreferenceFragmentCompat implements Preference.OnPreferenceClickListener {

@Override
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package de.bentigorlich.mimic3ttsenginewrapper;
package de.bentigorlich.mimic3ttsenginewrapper.entities;

import androidx.annotation.NonNull;

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
package de.bentigorlich.mimic3ttsenginewrapper.entities;

import androidx.annotation.NonNull;

import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.logging.LogRecord;

public class LogEntity implements Cloneable {
public String Message;
public String Level;
public String SourceClassName;
public String SourceMethodName;
public long Timestamp;
public String LoggerName;

public LogEntity(LogRecord record) {
Message = record.getMessage();
Level = record.getLevel().toString();
SourceClassName = record.getSourceClassName();
SourceMethodName = record.getSourceMethodName();
Timestamp = record.getMillis();
LoggerName = record.getLoggerName();
}

public LogEntity() {}

@NonNull
@Override
public LogEntity clone() {
LogEntity copy = new LogEntity();
copy.LoggerName = LoggerName;
copy.Level = Level;
copy.Timestamp = Timestamp;
copy.Message = Message;
copy.SourceClassName = SourceClassName;
copy.SourceMethodName = SourceMethodName;
return copy;
}

public String GetText(boolean includeSource) {
Calendar c = Calendar.getInstance();
c.setTimeInMillis(Timestamp);
SimpleDateFormat formatter = new SimpleDateFormat("dd/MM/yyyy|HH:mm:ss");
String source = "";
if(includeSource) {
if (LoggerName != null && !LoggerName.equals(""))
source += "[" + LoggerName + "]";

if (SourceClassName != null && !SourceClassName.equals(""))
source += "[" + SourceClassName + "]";

if (SourceMethodName != null && !SourceMethodName.equals(""))
source += "[" + SourceMethodName + "]";
}
return "<" + formatter.format(c.getTime()) + " " + Level + ">" + source + " " + Message;
}
}
Loading

0 comments on commit ccf3374

Please sign in to comment.