I have activated proguard in my project since I am trying to release this on Google Play. Even though proguard-android.txt has
-keepclassmembers class **.R$* {
public static <fields>;
}
which means it should not obfuscate the R.raw class that I need, I find that when running this code
import headwayEnt.Blackhole_Darksun.R;
private static final String RES_PATH = "headwayEnt.Blackhole_Darksun.R";
public static int getFileHandle(String fileName, String path) {
String fullPath = RES_PATH + '$' + path;
if (subClass == null) {
Class<headwayEnt.Blackhole_Darksun.R> c = null;
try {
c = (Class<R>)Class.forName(RES_PATH);
} catch(ClassNotFoundException e) {
e.printStackTrace();
} catch(ClassCastException e) {
e.printStackTrace();
}
subClass = c.getDeclaredClasses();
}
int fileHandle = 0;
try {
int i = 0;
System.out.println("fullPath: " + fullPath + " subclass len: " +
subClass.length);
for (; i < subClass.length; ++i) {
String name = subClass[i].getName();
if (subClass[i].getName().equals(fullPath)) {
break;
}
}
System.out.println("found i: " + i);
Field[] f = subClass[i].getDeclaredFields();
for (i = 0; i < f.length; ++i) {
if (f[i].getName().equals(fileName)) {
break;
}
}
try {
fileHandle = f[i].getInt(null);
} catch(IllegalAccessException e) {
}
} catch (RuntimeException e) {
System.out.println("Could not find filename: " + fileName +
" with path: " + path);
throw e;
}
return fileHandle;
}
with path raw for example and a filename from there I get an ArrayIndexOutOfBoundsException at line
Field[] f = subClass[i].getDeclaredFields();
since subClass.length is 0.
This thing works just fine if not obfuscating so I figured that the problem is with proguard.
I tried playing with different ways to make it not obfuscate the R classes like this:
-keep public class headwayEnt.HotshotEngine.Resource.ENG_Resource { *; }
-keep class headwayEnt.HotshotEngine.** { *; }
-keep class **.R$*
-keep public class headwayEnt.Blackhole_Darksun.R { *; }
-keep public class headwayEnt.Blackhole_Darksun_Full.R { *; }
-repackageclasses ''
-keep public class **.R {
public *;
}
-keep public class **.R$* {
public *;
}
and still doesn't work.
I must mention that all of my code is in a library (headwayEnt.Blackhole_Darksun) and that I reference that library in headwayEnt.Blackhole_Darksun_Full. Basically I am building two versions from the same code, one for full version and one for the free demo. All this obfuscation happens in the application, not in the referenced library (just to be clear).
To enable R8, open build. gradle module app file and add this piece of code inside the buildTypes . The code inside the release{} block means that this will be applied to the release build version of your application. If you launch the app in the emulator, this code is not executed.
-keepclassmembernames. This is the most permissive keep directive; it lets ProGuard do almost all of its work. Unused classes are removed, the remaining classes are renamed, unused members of those classes are removed, but then the remaining members keep their original names.
ProGuard is a tool to help minify, obfuscate, and optimize your code. It is not only especially useful for reducing the overall size of your Android application as well as removing unused classes and methods that contribute towards the intrinsic 64k method limit of Android applications.
This should work:
-keepattributes InnerClasses
-keep class **.R
-keep class **.R$* {
<fields>;
}
The InnerClasses
attribute is necessary to get anything from Class$getDeclaredClasses()
. The -keep options are necessary to keep the relevant classes and fields, with their original names.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With