Merge remote-tracking branch 'origin/main' into feat/v9-prerelease

This commit is contained in:
Nathan Walker
2025-11-02 08:54:59 -08:00
42 changed files with 729 additions and 417 deletions

View File

@@ -7,9 +7,9 @@ buildscript {
}
dependencies {
classpath 'com.android.tools.build:gradle:8.11.1'
classpath 'org.jetbrains.kotlin:kotlin-gradle-plugin:2.0.21'
classpath 'org.jetbrains.kotlin:kotlin-gradle-plugin:2.0.21'
// NOTE: Do not place your application dependencies here; they belong
// NOTE: Do not place your application dependencies here; they belong
// in the individual module build.gradle files
}
}

View File

@@ -4,20 +4,13 @@ def isWinOs = System.properties['os.name'].toLowerCase().contains('windows')
apply plugin: 'com.android.library'
def computeCompileSdkVersion() {
if (project.hasProperty("compileSdk")) {
return compileSdk
} else {
return 35
}
}
def computeBuildToolsVersion() {
if (project.hasProperty("buildToolsVersion")) {
return buildToolsVersion
} else {
return "35.0.0"
}
def computeCompileSdkValue () {
if(project.hasProperty("compileSdk")) {
return compileSdk
}
else {
return 35
}
}
def computeTargetSdkVersion() {
@@ -29,20 +22,22 @@ def computeTargetSdkVersion() {
}
android {
namespace "org.nativescript.widgets"
compileSdkVersion computeCompileSdkVersion()
buildToolsVersion computeBuildToolsVersion()
// AGP 8 DSL: use 'compileSdk' and specify namespace
compileSdk computeCompileSdkValue()
namespace "org.nativescript.widgets"
defaultConfig {
minSdkVersion 21
targetSdkVersion computeTargetSdkVersion()
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
}
defaultConfig {
minSdk 21
targetSdk computeTargetSdkVersion()
versionCode 1
versionName "1.0"
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
}
}
dependencies {

View File

@@ -364,6 +364,17 @@ public class ImageView extends androidx.appcompat.widget.AppCompatImageView impl
float uniformScale;
float pivotX, pivotY;
switch (this.getScaleType()) {
case CENTER:
uniformScale = 1;
matrix.postTranslate((innerWidth - bitmapWidth) / 2, (innerHeight - bitmapHeight) / 2);
matrix.postScale(uniformScale, uniformScale, innerWidth / 2, innerHeight / 2);
canvas.clipRect(
borderLeftWidth + (innerWidth - bitmapWidth * uniformScale) / 2,
borderTopWidth + (innerHeight - bitmapHeight * uniformScale) / 2,
borderLeftWidth + (innerWidth + bitmapWidth * uniformScale) / 2,
borderTopWidth + (innerHeight + bitmapHeight * uniformScale) / 2
);
break;
case FIT_CENTER: // aspectFit
uniformScale = Math.min(fittingScaleX, fittingScaleY);
matrix.postTranslate((innerWidth - bitmapWidth) / 2, (innerHeight - bitmapHeight) / 2);

View File

@@ -219,6 +219,36 @@ public class Utils {
boolean autoScaleFactor;
}
private static int parsePositiveInt(JSONObject object, String key) {
if (object == null || key == null) {
return 0;
}
try {
if (!object.has(key) || object.isNull(key)) {
return 0;
}
Object value = object.get(key);
if (value instanceof Number) {
int parsed = (int) Math.floor(((Number) value).doubleValue());
return parsed > 0 ? parsed : 0;
}
if (value instanceof String) {
String s = ((String) value).trim();
if (s.length() == 0) {
return 0;
}
try {
int parsed = Integer.parseInt(s);
return parsed > 0 ? parsed : 0;
} catch (NumberFormatException ignored) {
return 0;
}
}
} catch (JSONException ignored) {
}
return 0;
}
private static final Executor executors = Executors.newCachedThreadPool();
@@ -346,8 +376,9 @@ public class Utils {
try {
JSONObject object = new JSONObject(options);
opts.width = object.optInt("width", 0);
opts.height = object.optInt("height", 0);
// Coerce numeric strings or numbers; fallback to 0 for invalid values
opts.width = parsePositiveInt(object, "width");
opts.height = parsePositiveInt(object, "height");
opts.keepAspectRatio = object.optBoolean("keepAspectRatio", true);
opts.autoScaleFactor = object.optBoolean("autoScaleFactor", true);
} catch (JSONException ignored) {

View File

@@ -6,6 +6,33 @@ set -e
echo "Use dumb gradle terminal"
export TERM=dumb
# Prefer running with JDK 21 for Gradle 8.4+/AGP 8.3+
if [ "$(uname)" = "Darwin" ]; then
# On macOS, prefer JDK 21, fall back to JDK 17
if /usr/libexec/java_home -v 21 >/dev/null 2>&1; then
export JAVA_HOME=$(/usr/libexec/java_home -v 21)
export PATH="$JAVA_HOME/bin:$PATH"
echo "Using Java (21) at $JAVA_HOME"
java -version 2>&1 | head -n 1
elif /usr/libexec/java_home -v 17 >/dev/null 2>&1; then
export JAVA_HOME=$(/usr/libexec/java_home -v 17)
export PATH="$JAVA_HOME/bin:$PATH"
echo "Using Java (17) at $JAVA_HOME"
java -version 2>&1 | head -n 1
else
echo "Warning: JDK 21 or 17 not found via /usr/libexec/java_home. Using current JAVA_HOME: ${JAVA_HOME:-unset}"
java -version 2>&1 || true
echo "Install JDK 21 (preferred) or JDK 17."
fi
else
# Non-macOS: print Java version for visibility
if command -v java >/dev/null 2>&1; then
echo "Detected Java runtime: $(java -version 2>&1 | head -n 1)"
else
echo "Warning: 'java' not found on PATH. Build will likely fail."
fi
fi
rm -rf dist/package/platforms/android || true
mkdir -p dist/package/platforms/android