Skip to content

Commit

Permalink
initial version
Browse files Browse the repository at this point in the history
  • Loading branch information
arobro committed Apr 27, 2022
1 parent 6bfff21 commit b04aa07
Show file tree
Hide file tree
Showing 126 changed files with 16,113 additions and 0 deletions.
2 changes: 2 additions & 0 deletions AUTHORS
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
Authors:
Aidan Brown
2,579 changes: 2,579 additions & 0 deletions Doxyfile

Large diffs are not rendered by default.

15 changes: 15 additions & 0 deletions MythAppsServices/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
*.iml
.gradle
/local.properties
/.idea/caches
/.idea/libraries
/.idea/modules.xml
/.idea/workspace.xml
/.idea/navEditor.xml
/.idea/assetWizardSettings.xml
.DS_Store
/build
/captures
.externalNativeBuild
.cxx
local.properties
3 changes: 3 additions & 0 deletions MythAppsServices/.idea/.gitignore

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions MythAppsServices/.idea/.name

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

6 changes: 6 additions & 0 deletions MythAppsServices/.idea/compiler.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

20 changes: 20 additions & 0 deletions MythAppsServices/.idea/gradle.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

19 changes: 19 additions & 0 deletions MythAppsServices/.idea/misc.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions MythAppsServices/app/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
/build
41 changes: 41 additions & 0 deletions MythAppsServices/app/build.gradle
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
plugins {
id 'com.android.application'
}

android {
compileSdk 32

defaultConfig {
applicationId "com.mythtv.mythappsservices"
minSdk 26
targetSdk 32
versionCode 1
versionName "1.0"

testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
}

buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
}
}
compileOptions {
sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}
}

dependencies {

implementation 'androidx.appcompat:appcompat:1.4.1'
implementation 'com.google.android.material:material:1.5.0'
implementation 'androidx.constraintlayout:constraintlayout:2.1.3'

implementation 'org.java-websocket:Java-WebSocket:1.5.3'

testImplementation 'junit:junit:4.13.2'
androidTestImplementation 'androidx.test.ext:junit:1.1.3'
androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0'
}
21 changes: 21 additions & 0 deletions MythAppsServices/app/proguard-rules.pro
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
# Add project specific ProGuard rules here.
# You can control the set of applied configuration files using the
# proguardFiles setting in build.gradle.
#
# For more details, see
# http://developer.android.com/guide/developing/tools/proguard.html

# If your project uses WebView with JS, uncomment the following
# and specify the fully qualified class name to the JavaScript interface
# class:
#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
# public *;
#}

# Uncomment this to preserve the line number information for
# debugging stack traces.
#-keepattributes SourceFile,LineNumberTable

# If you keep the line number information, uncomment this to
# hide the original source file name.
#-renamesourcefileattribute SourceFile
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
package com.mythtv.mythappsservices;

import android.content.Context;

import androidx.test.platform.app.InstrumentationRegistry;
import androidx.test.ext.junit.runners.AndroidJUnit4;

import org.junit.Test;
import org.junit.runner.RunWith;

import static org.junit.Assert.*;

/**
* Instrumented test, which will execute on an Android device.
*
* @see <a href="http://d.android.com/tools/testing">Testing documentation</a>
*/
@RunWith(AndroidJUnit4.class)
public class ExampleInstrumentedTest {
@Test
public void useAppContext() {
// Context of the app under test.
Context appContext = InstrumentationRegistry.getInstrumentation().getTargetContext();
assertEquals("com.mythtv.mythappsservices", appContext.getPackageName());
}
}
32 changes: 32 additions & 0 deletions MythAppsServices/app/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.mythtv.mythappsservices">

<uses-permission android:name="android.permission.REQUEST_IGNORE_BATTERY_OPTIMIZATIONS"/>
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" />
<uses-permission android:name="android.permission.FOREGROUND_SERVICE" />

<application
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true"
android:theme="@style/Theme.MythAppsServices">
<activity
android:name=".MainActivity"
android:screenOrientation="landscape"
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.MAIN" />

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

<service android:name=".MythAppsService" />

</application>

</manifest>
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
package com.mythtv.mythappsservices;

import androidx.appcompat.app.AppCompatActivity;
import android.app.PendingIntent;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.net.Uri;
import android.os.Build;
import android.os.Bundle;
import android.os.Handler;
import android.provider.Settings;
import android.util.Log;
import android.widget.Toast;

public class MainActivity extends AppCompatActivity {
MythAppsWebSocketServer s = null;
Context context;
boolean restart = false;
int app = 0;

int ACTION_MANAGE_OVERLAY_PERMISSION_REQUEST_CODE = 24;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
context = this;

checkPermission();

startForegroundService(new Intent(this, MythAppsService.class));
Log.d("MythAppServices","oncreate() ");
}

public void openMyth() {
new Handler().postDelayed(new Runnable() {
@Override
public void run() {
Intent intent = new Intent(context, MainActivity.class);
intent.setAction(Long.toString(System.currentTimeMillis())); //intent.FLAG_CANCEL_CURRENT
intent.setComponent(ComponentName.unflattenFromString("org.xbmc.kodi/org.xbmc.kodi.Splash"));
intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_SINGLE_TOP | Intent.FLAG_ACTIVITY_NEW_TASK);
PendingIntent pendingIntent = PendingIntent.getActivity(context, 0, intent, PendingIntent.FLAG_UPDATE_CURRENT);
startActivity(intent);
finish();

try{
Thread.sleep(1500);
}catch(InterruptedException e){
System.out.println(e);
}

intent = new Intent(context, MainActivity.class);
intent.setAction(Long.toString(System.currentTimeMillis())); //intent.FLAG_CANCEL_CURRENT
intent.setComponent(ComponentName.unflattenFromString("org.mythtv.mythfrontend/org.qtproject.qt5.android.bindings.QtActivity"));
intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_SINGLE_TOP | Intent.FLAG_ACTIVITY_NEW_TASK);
pendingIntent = PendingIntent.getActivity(context, 0, intent, PendingIntent.FLAG_UPDATE_CURRENT);
startActivity(intent);
finish();
}
}, 1000 );//time in miliseconds
}

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);

if (requestCode == ACTION_MANAGE_OVERLAY_PERMISSION_REQUEST_CODE) {
if (!Settings.canDrawOverlays(this)) { // No permission
checkPermission();
}

}
}

public void checkPermission() {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
if (!Settings.canDrawOverlays(this)) {
Toast.makeText(this, "Please find MythApps Services and enable 'appear on top.'", Toast.LENGTH_LONG).show();
Intent intent = new Intent(Settings.ACTION_MANAGE_OVERLAY_PERMISSION,
Uri.parse("package:" + getPackageName()));
startActivityForResult(intent, ACTION_MANAGE_OVERLAY_PERMISSION_REQUEST_CODE);
}else { //have permission
Toast.makeText(this, "Remember to disable power optimization for Mythfrontend and Kodi.", Toast.LENGTH_LONG).show();
Toast.makeText(this,"Settings->Apps->:->Special Access->Optimise Battery Usage->All->Mythfrontend ->Off", Toast.LENGTH_LONG).show();
openMyth();
}
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,87 @@
package com.mythtv.mythappsservices;

import android.app.Notification;
import android.app.NotificationChannel;
import android.app.NotificationManager;
import android.app.PendingIntent;
import android.app.Service;
import android.content.Context;
import android.content.Intent;
import android.os.Build;
import android.os.IBinder;
import android.widget.Toast;

import androidx.core.app.NotificationCompat;
import java.net.InetSocketAddress;
import java.net.UnknownHostException;

public class MythAppsService extends Service {
public static boolean isMyServiceRunning;
int startMode; // indicates how to behave if the service is killed
IBinder binder; // interface for clients that bind
boolean allowRebind; // indicates whether onRebind should be used
MythAppsWebSocketServer s = null;
public static boolean IS_ACTIVITY_RUNNING = false;

@Override
public void onCreate() {
super.onCreate();
IS_ACTIVITY_RUNNING = true;
}

private void createNotificationChannel() {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
NotificationChannel serviceChannel = new NotificationChannel(
"ForegroundServiceChannel",
"MythApps Foreground Service",
NotificationManager.IMPORTANCE_DEFAULT
);
NotificationManager manager = getSystemService(NotificationManager.class);
manager.createNotificationChannel(serviceChannel);
}
}

@Override
public int onStartCommand(Intent intent, int flags, int startId) {
createNotificationChannel();
Intent notificationIntent = new Intent(this, MainActivity.class);
PendingIntent pendingIntent = PendingIntent.getActivity(this,
0, notificationIntent, 0);
Notification notification = new NotificationCompat.Builder(this, "ForegroundServiceChannel")
.setContentTitle("MythApps Services")
.setContentIntent(pendingIntent)
.build();
startForeground(1, notification);

//start websocket
Context context = getApplicationContext();
int port = 8088;
InetSocketAddress address = new InetSocketAddress("127.0.0.1", port);

try {
s = new MythAppsWebSocketServer(address, context );
} catch (UnknownHostException e) {
e.printStackTrace();
}

s.start();
return startMode;
}
@Override
public IBinder onBind(Intent intent) {
return binder;
}
@Override
public boolean onUnbind(Intent intent) {
return allowRebind;
}
@Override
public void onRebind(Intent intent) {
}
@Override
public void onDestroy() {
super.onDestroy();
IS_ACTIVITY_RUNNING = false;
Toast.makeText(this, "MythApp Service Stopped", Toast.LENGTH_LONG).show();
}
}
Loading

0 comments on commit b04aa07

Please sign in to comment.