mirror of
https://github.com/revanced/Apktool.git
synced 2025-01-07 10:35:52 +01:00
Merge branch 'master' into fix-optical-inset
This commit is contained in:
commit
2a35125441
19
INTERNAL.md
19
INTERNAL.md
@ -239,3 +239,22 @@ we lose the ability to quickly build just the aapt binary. So the Windows proced
|
|||||||
1. `source build/envsetup.sh`
|
1. `source build/envsetup.sh`
|
||||||
2. `lunch sdk-eng`
|
2. `lunch sdk-eng`
|
||||||
3. `make OUT_DIR=out-x64 LOCAL_MULTILIB=64 USE_NINJA=false aapt`
|
3. `make OUT_DIR=out-x64 LOCAL_MULTILIB=64 USE_NINJA=false aapt`
|
||||||
|
|
||||||
|
# Gradle Tips n Tricks
|
||||||
|
|
||||||
|
./gradlew build shadowJar proguard -x test
|
||||||
|
|
||||||
|
This skips the testing suite (which currently takes 2-4 minutes). Use this when making quick builds and save the testing
|
||||||
|
suite before pushing to GitHub.
|
||||||
|
|
||||||
|
./gradlew build shadowJar proguard -Dtest.debug
|
||||||
|
|
||||||
|
This enables debugging on the test suite. This starts the debugger on port 5005 which you can connect with IntelliJ.
|
||||||
|
|
||||||
|
./gradlew :brut.apktool:apktool-lib:test ---tests "*BuildAndDecodeTest"
|
||||||
|
|
||||||
|
This runs the library project of Apktool, selecting a specific test to run. Comes in handy when writing a new test and
|
||||||
|
only wanting to run that one. The asterisk is used to the full path to the test can be ignored. You can additionally
|
||||||
|
match this with the debugging parameter to debug a specific test. This command can be found below.
|
||||||
|
|
||||||
|
./gradlew :brut.apktool:apktool-lib:test --tests "*BuildAndDecodeTest" -Dtest.debug
|
||||||
|
@ -19,6 +19,7 @@ package brut.androlib;
|
|||||||
import brut.androlib.meta.MetaInfo;
|
import brut.androlib.meta.MetaInfo;
|
||||||
import brut.androlib.meta.UsesFramework;
|
import brut.androlib.meta.UsesFramework;
|
||||||
import brut.androlib.res.AndrolibResources;
|
import brut.androlib.res.AndrolibResources;
|
||||||
|
import brut.androlib.res.data.ResConfigFlags;
|
||||||
import brut.androlib.res.data.ResPackage;
|
import brut.androlib.res.data.ResPackage;
|
||||||
import brut.androlib.res.data.ResTable;
|
import brut.androlib.res.data.ResTable;
|
||||||
import brut.androlib.res.data.ResUnknownFiles;
|
import brut.androlib.res.data.ResUnknownFiles;
|
||||||
@ -279,7 +280,22 @@ public class Androlib {
|
|||||||
mAndRes.setSharedLibrary(meta.sharedLibrary);
|
mAndRes.setSharedLibrary(meta.sharedLibrary);
|
||||||
|
|
||||||
if (meta.sdkInfo != null && meta.sdkInfo.get("minSdkVersion") != null) {
|
if (meta.sdkInfo != null && meta.sdkInfo.get("minSdkVersion") != null) {
|
||||||
mMinSdkVersion = Integer.parseInt(meta.sdkInfo.get("minSdkVersion"));
|
String minSdkVersion = meta.sdkInfo.get("minSdkVersion");
|
||||||
|
|
||||||
|
// Preview builds use short letter for API versions
|
||||||
|
switch (minSdkVersion) {
|
||||||
|
case "M":
|
||||||
|
mMinSdkVersion = ResConfigFlags.SDK_MNC;
|
||||||
|
break;
|
||||||
|
case "N":
|
||||||
|
mMinSdkVersion = ResConfigFlags.SDK_NOUGAT;
|
||||||
|
break;
|
||||||
|
case "O":
|
||||||
|
mMinSdkVersion = ResConfigFlags.SDK_O;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
mMinSdkVersion = Integer.parseInt(meta.sdkInfo.get("minSdkVersion"));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (outFile == null) {
|
if (outFile == null) {
|
||||||
|
@ -507,6 +507,9 @@ public class ResConfigFlags {
|
|||||||
public final static byte SDK_LOLLIPOP = 21;
|
public final static byte SDK_LOLLIPOP = 21;
|
||||||
public final static byte SDK_LOLLIPOP_MR1 = 22;
|
public final static byte SDK_LOLLIPOP_MR1 = 22;
|
||||||
public final static byte SDK_MNC = 23;
|
public final static byte SDK_MNC = 23;
|
||||||
|
public final static byte SDK_NOUGAT = 24;
|
||||||
|
public final static byte SDK_NOUGAT_MR1 = 25;
|
||||||
|
public final static byte SDK_O = 26;
|
||||||
|
|
||||||
public final static byte ORIENTATION_ANY = 0;
|
public final static byte ORIENTATION_ANY = 0;
|
||||||
public final static byte ORIENTATION_PORT = 1;
|
public final static byte ORIENTATION_PORT = 1;
|
||||||
|
@ -90,7 +90,8 @@ public class ResValueFactory {
|
|||||||
if (key == ResAttr.BAG_KEY_ATTR_TYPE) {
|
if (key == ResAttr.BAG_KEY_ATTR_TYPE) {
|
||||||
return ResAttr.factory(parentVal, items, this, mPackage);
|
return ResAttr.factory(parentVal, items, this, mPackage);
|
||||||
}
|
}
|
||||||
if (key == ResArrayValue.BAG_KEY_ARRAY_START) {
|
// Android O Preview added an unknown enum for ResTable_map. This is hardcoded as 0 for now.
|
||||||
|
if (key == ResArrayValue.BAG_KEY_ARRAY_START || key == 0) {
|
||||||
return new ResArrayValue(parentVal, items);
|
return new ResArrayValue(parentVal, items);
|
||||||
}
|
}
|
||||||
if (key >= ResPluralsValue.BAG_KEY_PLURALS_START && key <= ResPluralsValue.BAG_KEY_PLURALS_END) {
|
if (key >= ResPluralsValue.BAG_KEY_PLURALS_START && key <= ResPluralsValue.BAG_KEY_PLURALS_END) {
|
||||||
|
@ -20,6 +20,8 @@ import brut.androlib.AndrolibException;
|
|||||||
import brut.androlib.err.CantFind9PatchChunk;
|
import brut.androlib.err.CantFind9PatchChunk;
|
||||||
import brut.util.ExtDataInput;
|
import brut.util.ExtDataInput;
|
||||||
import java.awt.image.BufferedImage;
|
import java.awt.image.BufferedImage;
|
||||||
|
import java.awt.image.Raster;
|
||||||
|
import java.awt.image.WritableRaster;
|
||||||
import java.io.*;
|
import java.io.*;
|
||||||
import javax.imageio.ImageIO;
|
import javax.imageio.ImageIO;
|
||||||
import javax.imageio.ImageTypeSpecifier;
|
import javax.imageio.ImageTypeSpecifier;
|
||||||
@ -39,8 +41,24 @@ public class Res9patchStreamDecoder implements ResStreamDecoder {
|
|||||||
BufferedImage im = ImageIO.read(new ByteArrayInputStream(data));
|
BufferedImage im = ImageIO.read(new ByteArrayInputStream(data));
|
||||||
int w = im.getWidth(), h = im.getHeight();
|
int w = im.getWidth(), h = im.getHeight();
|
||||||
|
|
||||||
BufferedImage im2 = new BufferedImage(w+2, h+2, BufferedImage.TYPE_INT_ARGB);
|
BufferedImage im2 = new BufferedImage(w + 2, h + 2, BufferedImage.TYPE_INT_ARGB);
|
||||||
im2.createGraphics().drawImage(im, 1, 1, w, h, null);
|
if (im.getType() == BufferedImage.TYPE_CUSTOM) {
|
||||||
|
//TODO: Ensure this is gray + alpha case?
|
||||||
|
Raster srcRaster = im.getRaster();
|
||||||
|
WritableRaster dstRaster = im2.getRaster();
|
||||||
|
int[] gray = null, alpha = null;
|
||||||
|
for (int y = 0; y < im.getHeight(); y++) {
|
||||||
|
gray = srcRaster.getSamples(0, y, w, 1, 0, gray);
|
||||||
|
alpha = srcRaster.getSamples(0, y, w, 1, 1, alpha);
|
||||||
|
|
||||||
|
dstRaster.setSamples(1, y + 1, w, 1, 0, gray);
|
||||||
|
dstRaster.setSamples(1, y + 1, w, 1, 1, gray);
|
||||||
|
dstRaster.setSamples(1, y + 1, w, 1, 2, gray);
|
||||||
|
dstRaster.setSamples(1, y + 1, w, 1, 3, alpha);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
im2.createGraphics().drawImage(im, 1, 1, w, h, null);
|
||||||
|
}
|
||||||
|
|
||||||
NinePatch np = getNinePatch(data);
|
NinePatch np = getNinePatch(data);
|
||||||
drawHLine(im2, h + 1, np.padLeft + 1, w - np.padRight);
|
drawHLine(im2, h + 1, np.padLeft + 1, w - np.padRight);
|
||||||
|
@ -131,8 +131,14 @@ public class StringBlock {
|
|||||||
if (style == null) {
|
if (style == null) {
|
||||||
return ResXmlEncoders.escapeXmlChars(raw);
|
return ResXmlEncoders.escapeXmlChars(raw);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// If the returned style is further in string, than string length. Lets skip it.
|
||||||
|
if (style[1] > raw.length()) {
|
||||||
|
return ResXmlEncoders.escapeXmlChars(raw);
|
||||||
|
}
|
||||||
StringBuilder html = new StringBuilder(raw.length() + 32);
|
StringBuilder html = new StringBuilder(raw.length() + 32);
|
||||||
int[] opened = new int[style.length / 3];
|
int[] opened = new int[style.length / 3];
|
||||||
|
boolean[] unclosed = new boolean[style.length / 3];
|
||||||
int offset = 0, depth = 0;
|
int offset = 0, depth = 0;
|
||||||
while (true) {
|
while (true) {
|
||||||
int i = -1, j;
|
int i = -1, j;
|
||||||
@ -149,6 +155,9 @@ public class StringBlock {
|
|||||||
int last = opened[j];
|
int last = opened[j];
|
||||||
int end = style[last + 2];
|
int end = style[last + 2];
|
||||||
if (end >= start) {
|
if (end >= start) {
|
||||||
|
if (style[last + 1] == -1 && end != -1) {
|
||||||
|
unclosed[j] = true;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
if (offset <= end) {
|
if (offset <= end) {
|
||||||
@ -160,6 +169,11 @@ public class StringBlock {
|
|||||||
depth = j + 1;
|
depth = j + 1;
|
||||||
if (offset < start) {
|
if (offset < start) {
|
||||||
html.append(ResXmlEncoders.escapeXmlChars(raw.substring(offset, start)));
|
html.append(ResXmlEncoders.escapeXmlChars(raw.substring(offset, start)));
|
||||||
|
if (j >= 0 && unclosed.length >= j && unclosed[j]) {
|
||||||
|
if (unclosed.length > (j + 1) && unclosed[j + 1] || unclosed.length == 1) {
|
||||||
|
outputStyleTag(getString(style[opened[j]]), html, true);
|
||||||
|
}
|
||||||
|
}
|
||||||
offset = start;
|
offset = start;
|
||||||
}
|
}
|
||||||
if (i == -1) {
|
if (i == -1) {
|
||||||
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@ -253,6 +253,11 @@ public class BuildAndDecodeTest {
|
|||||||
compareValuesFiles("values-ast/strings.xml");
|
compareValuesFiles("values-ast/strings.xml");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void androidOStringTest() throws BrutException, IOException {
|
||||||
|
compareValuesFiles("values-ast/strings.xml");
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void twoLetterNotHandledAsBcpTest() throws BrutException, IOException {
|
public void twoLetterNotHandledAsBcpTest() throws BrutException, IOException {
|
||||||
checkFolderExists("res/values-fr");
|
checkFolderExists("res/values-fr");
|
||||||
@ -345,6 +350,27 @@ public class BuildAndDecodeTest {
|
|||||||
assertEquals(controlImage.getRGB(30, 30), testImage.getRGB(30, 30));
|
assertEquals(controlImage.getRGB(30, 30), testImage.getRGB(30, 30));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void issue1508Test() throws BrutException, IOException {
|
||||||
|
char slash = File.separatorChar;
|
||||||
|
String location = slash + "res" + slash + "drawable-xhdpi" + slash;
|
||||||
|
|
||||||
|
File control = new File((sTestOrigDir + location), "btn_zoom_up_normal.9.png");
|
||||||
|
File test = new File((sTestNewDir + location), "btn_zoom_up_normal.9.png");
|
||||||
|
|
||||||
|
BufferedImage controlImage = ImageIO.read(control);
|
||||||
|
BufferedImage testImage = ImageIO.read(test);
|
||||||
|
|
||||||
|
// 0, 0 = clear
|
||||||
|
assertEquals(controlImage.getRGB(0, 0), testImage.getRGB(0, 0));
|
||||||
|
|
||||||
|
// 30, 0 = black line
|
||||||
|
assertEquals(controlImage.getRGB(0, 30), testImage.getRGB(0, 30));
|
||||||
|
|
||||||
|
// 30, 30 = greyish button
|
||||||
|
assertEquals(controlImage.getRGB(30, 30), testImage.getRGB(30, 30));
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void drawableXxhdpiTest() throws BrutException, IOException {
|
public void drawableXxhdpiTest() throws BrutException, IOException {
|
||||||
compareResFolder("drawable-xxhdpi");
|
compareResFolder("drawable-xxhdpi");
|
||||||
|
Binary file not shown.
After Width: | Height: | Size: 1.9 KiB |
@ -0,0 +1,9 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<resources>
|
||||||
|
<string name="test1">"Forgot your username or password?\nVisit google.com/accounts/recovery."</string>
|
||||||
|
<string name="test2">Forgot your username or password?\n.Visit google.com/accounts/recovery</string>
|
||||||
|
<string name="test3"> (string8) "Forgot your username or password?\nVisit google.com/accounts/recovery."</string>
|
||||||
|
<string name="test4">Forgot your username or password?\nVisit google.com/accounts/recovery.</string>
|
||||||
|
<string name="test5">Forgot your username or password?
|
||||||
|
Visit google.com/accounts/recovery.</string>
|
||||||
|
</resources>
|
@ -31,4 +31,14 @@ bar"</string>
|
|||||||
<string name="test_string29" formatted="false">category=temp%temp%foo</string>
|
<string name="test_string29" formatted="false">category=temp%temp%foo</string>
|
||||||
<string name="test_string30">res/foo/</string>
|
<string name="test_string30">res/foo/</string>
|
||||||
<string name="test_string31">res/foo</string>
|
<string name="test_string31">res/foo</string>
|
||||||
|
<string name="test_string32">[<font size="17">TEST STRING</font>]</string>
|
||||||
|
<string name="test_string33"><font size="17">[TEST STRING]</font></string>
|
||||||
|
<string name="test_string34">[<font size="17">TEST STRING]</font></string>
|
||||||
|
<string name="test_string35"><font size="17">[TEST STRING</font>]</string>
|
||||||
|
<string name="test_string36"><font size="17">TEST STRING</font></string>
|
||||||
|
<string name="test_string37">[<font size="17">Ţåþ ţö ţýþé þåššŵöŕð one two three]</font></string>
|
||||||
|
<string name="test_string38">[<font size="17">Ţåþ ţö ţýþé þåššŵöŕð one two three</font>]</string>
|
||||||
|
<string name="test_string39"><font size="17">[Ţåþ ţö ţýþé þåššŵöŕð one two three</font>]</string>
|
||||||
|
<string name="test_string40">[<font size="17">]Ţåþ ţö ţýþé þåššŵöŕð one two three</font></string>
|
||||||
|
<string name="test_string41"><font size="17">[Ţåþ ţö ţýþé þåššŵöŕð one two three]</font></string>
|
||||||
</resources>
|
</resources>
|
||||||
|
@ -82,7 +82,7 @@ subprojects {
|
|||||||
|
|
||||||
ext {
|
ext {
|
||||||
depends = [
|
depends = [
|
||||||
baksmali: 'org.smali:baksmali:2.2.0',
|
baksmali: 'org.smali:baksmali:2.2.1',
|
||||||
commons_cli: 'commons-cli:commons-cli:1.4',
|
commons_cli: 'commons-cli:commons-cli:1.4',
|
||||||
commons_io: 'commons-io:commons-io:2.4',
|
commons_io: 'commons-io:commons-io:2.4',
|
||||||
commons_lang: 'org.apache.commons:commons-lang3:3.1',
|
commons_lang: 'org.apache.commons:commons-lang3:3.1',
|
||||||
@ -91,7 +91,7 @@ subprojects {
|
|||||||
junit: 'junit:junit:4.12',
|
junit: 'junit:junit:4.12',
|
||||||
proguard_gradle: 'net.sf.proguard:proguard-gradle:5.2.1',
|
proguard_gradle: 'net.sf.proguard:proguard-gradle:5.2.1',
|
||||||
snakeyaml: 'org.yaml:snakeyaml:1.17',
|
snakeyaml: 'org.yaml:snakeyaml:1.17',
|
||||||
smali: 'org.smali:smali:2.2.0',
|
smali: 'org.smali:smali:2.2.1',
|
||||||
xmlpull: 'xpp3:xpp3:1.1.4c',
|
xmlpull: 'xpp3:xpp3:1.1.4c',
|
||||||
xmlunit: 'xmlunit:xmlunit:1.3',
|
xmlunit: 'xmlunit:xmlunit:1.3',
|
||||||
]
|
]
|
||||||
|
Loading…
Reference in New Issue
Block a user