diff --git a/app/src/processing/app/Base.java b/app/src/processing/app/Base.java
index e241ab13a..b0c0a63c1 100644
--- a/app/src/processing/app/Base.java
+++ b/app/src/processing/app/Base.java
@@ -98,6 +98,8 @@ public class Base {
}
}
+ static String nativeArch = System.getProperty("os.arch");
+
static private boolean commandLine;
// A single instance of the preferences window
@@ -1543,6 +1545,30 @@ public class Base {
return nativeBits;
}
+ /**
+ * Return the value of the os.arch propery
+ */
+ static public String getNativeArch() {
+ return nativeArch;
+ }
+
+ /*
+ * Return a string that identifies the variant of a platform
+ * e.g. "32" or "64" on Intel
+ */
+ static public String getVariant() {
+ return getVariant(PApplet.platform, getNativeArch(), getNativeBits());
+ }
+
+ static public String getVariant(int platform, String arch, int bits) {
+ if (platform == PConstants.LINUX && bits == 32 && "arm".equals(Base.getNativeArch())) {
+ // assume armv6hf for now
+ return "armv6hf";
+ } else {
+ // 32 or 64
+ return Integer.toString(bits);
+ }
+ }
/*
static public String getPlatformName() {
diff --git a/app/src/processing/app/Library.java b/app/src/processing/app/Library.java
index 4b9c3f74a..fef59cafd 100644
--- a/app/src/processing/app/Library.java
+++ b/app/src/processing/app/Library.java
@@ -173,6 +173,7 @@ public class Library extends LocalContribution {
String platformName = platformNames[i];
String platformName32 = platformName + "32";
String platformName64 = platformName + "64";
+ String platformNameArmv6hh = platformName + "-armv6hf";
// First check for things like 'application.macosx=' or 'application.windows32' in the export.txt file.
// These will override anything in the platform-specific subfolders.
@@ -182,6 +183,8 @@ public class Library extends LocalContribution {
String[] platformList32 = platform32 == null ? null : PApplet.splitTokens(platform32, ", ");
String platform64 = exportTable.get("application." + platformName + "64");
String[] platformList64 = platform64 == null ? null : PApplet.splitTokens(platform64, ", ");
+ String platformArmv6hf = exportTable.get("application." + platformName + "-armv6hf");
+ String[] platformListArmv6hf = platformArmv6hf == null ? null : PApplet.splitTokens(platformArmv6hf, ", ");
// If nothing specified in the export.txt entries, look for the platform-specific folders.
if (platformAll == null) {
@@ -193,14 +196,17 @@ public class Library extends LocalContribution {
if (platform64 == null) {
platformList64 = listPlatformEntries(libraryFolder, platformName64, baseList);
}
+ if (platformListArmv6hf == null) {
+ platformListArmv6hf = listPlatformEntries(libraryFolder, platformNameArmv6hh, baseList);
+ }
- if (platformList32 != null || platformList64 != null) {
+ if (platformList32 != null || platformList64 != null || platformListArmv6hf != null) {
multipleArch[i] = true;
}
// if there aren't any relevant imports specified or in their own folders,
// then use the baseList (root of the library folder) as the default.
- if (platformList == null && platformList32 == null && platformList64 == null) {
+ if (platformList == null && platformList32 == null && platformList64 == null && platformListArmv6hf == null) {
exportList.put(platformName, baseList);
} else {
@@ -215,6 +221,9 @@ public class Library extends LocalContribution {
if (platformList64 != null) {
exportList.put(platformName64, platformList64);
}
+ if (platformListArmv6hf != null) {
+ exportList.put(platformNameArmv6hh, platformListArmv6hf);
+ }
}
}
// for (String p : exportList.keySet()) {
@@ -369,8 +378,8 @@ public class Library extends LocalContribution {
}
- public File[] getApplicationExports(int platform, int bits) {
- String[] list = getApplicationExportList(platform, bits);
+ public File[] getApplicationExports(int platform, String variant) {
+ String[] list = getApplicationExportList(platform, variant);
return wrapFiles(list);
}
@@ -380,14 +389,17 @@ public class Library extends LocalContribution {
* If no 32 or 64-bit version of the exports exists, it returns the version
* that doesn't specify bit depth.
*/
- public String[] getApplicationExportList(int platform, int bits) {
+ public String[] getApplicationExportList(int platform, String variant) {
String platformName = PConstants.platformNames[platform];
- if (bits == 32) {
+ if (variant.equals("32")) {
String[] pieces = exportList.get(platformName + "32");
if (pieces != null) return pieces;
- } else if (bits == 64) {
+ } else if (variant.equals("64")) {
String[] pieces = exportList.get(platformName + "64");
if (pieces != null) return pieces;
+ } else if (variant.equals("armv6hf")) {
+ String[] pieces = exportList.get(platformName + "-armv6hf");
+ if (pieces != null) return pieces;
}
return exportList.get(platformName);
}
@@ -408,12 +420,12 @@ public class Library extends LocalContribution {
}
- public boolean supportsArch(int platform, int bits) {
+ public boolean supportsArch(int platform, String variant) {
// If this is a universal library, or has no natives, then we're good.
if (multipleArch[platform] == false) {
return true;
}
- return getApplicationExportList(platform, bits) != null;
+ return getApplicationExportList(platform, variant) != null;
}
diff --git a/build/build.xml b/build/build.xml
index 2efcf03e3..b684a5b06 100644
--- a/build/build.xml
+++ b/build/build.xml
@@ -37,6 +37,7 @@
+
diff --git a/core/build.xml b/core/build.xml
index 5d31d4673..6e5781730 100644
--- a/core/build.xml
+++ b/core/build.xml
@@ -63,8 +63,8 @@
-
-
+
+
diff --git a/core/library/export.txt b/core/library/export.txt
index 308d1a35a..88d0bc274 100644
--- a/core/library/export.txt
+++ b/core/library/export.txt
@@ -8,3 +8,4 @@ application.windows32=core.jar,jogl-all.jar,gluegen-rt.jar,jogl-all-natives-wind
application.windows64=core.jar,jogl-all.jar,gluegen-rt.jar,jogl-all-natives-windows-amd64.jar,gluegen-rt-natives-windows-amd64.jar
application.linux32=core.jar,jogl-all.jar,gluegen-rt.jar,jogl-all-natives-linux-i586.jar,gluegen-rt-natives-linux-i586.jar
application.linux64=core.jar,jogl-all.jar,gluegen-rt.jar,jogl-all-natives-linux-amd64.jar,gluegen-rt-natives-linux-amd64.jar
+application.linux-armv6hf=core.jar,jogl-all.jar,gluegen-rt.jar,jogl-all-natives-linux-armv6hf.jar,gluegen-rt-natives-linux-armv6hf.jar
\ No newline at end of file
diff --git a/core/src/processing/opengl/PGraphicsOpenGL.java b/core/src/processing/opengl/PGraphicsOpenGL.java
index de8a1e796..b0c61414d 100644
--- a/core/src/processing/opengl/PGraphicsOpenGL.java
+++ b/core/src/processing/opengl/PGraphicsOpenGL.java
@@ -7042,9 +7042,15 @@ public class PGraphicsOpenGL extends PGraphics {
if (smooth < 1) {
pgl.disable(PGL.MULTISAMPLE);
} else {
- pgl.enable(PGL.MULTISAMPLE);
+ // work around runtime exceptions in Broadcom's VC IV driver
+ if (false == OPENGL_RENDERER.equals("VideoCore IV HW")) {
+ pgl.enable(PGL.MULTISAMPLE);
+ }
+ }
+ // work around runtime exceptions in Broadcom's VC IV driver
+ if (false == OPENGL_RENDERER.equals("VideoCore IV HW")) {
+ pgl.disable(PGL.POLYGON_SMOOTH);
}
- pgl.disable(PGL.POLYGON_SMOOTH);
if (sized) {
// reapplySettings();
@@ -7154,14 +7160,27 @@ public class PGraphicsOpenGL extends PGraphics {
pgl.getIntegerv(PGL.MAX_TEXTURE_SIZE, intBuffer);
maxTextureSize = intBuffer.get(0);
- pgl.getIntegerv(PGL.MAX_SAMPLES, intBuffer);
- maxSamples = intBuffer.get(0);
+ // work around runtime exceptions in Broadcom's VC IV driver
+ if (false == OPENGL_RENDERER.equals("VideoCore IV HW")) {
+ pgl.getIntegerv(PGL.MAX_SAMPLES, intBuffer);
+ maxSamples = intBuffer.get(0);
+ }
if (anisoSamplingSupported) {
pgl.getFloatv(PGL.MAX_TEXTURE_MAX_ANISOTROPY, floatBuffer);
maxAnisoAmount = floatBuffer.get(0);
}
+ // overwrite the default shaders with vendor specific versions
+ // if needed
+ if (OPENGL_RENDERER.equals("VideoCore IV HW") || // Broadcom's binary driver for Raspberry Pi
+ OPENGL_RENDERER.equals("Gallium 0.4 on VC4")) { // Mesa driver for same hardware
+ defLightShaderVertURL =
+ PGraphicsOpenGL.class.getResource("/processing/opengl/shaders/LightVert-vc4.glsl");
+ defTexlightShaderVertURL =
+ PGraphicsOpenGL.class.getResource("/processing/opengl/shaders/TexLightVert-vc4.glsl");
+ }
+
glParamsRead = true;
}
diff --git a/core/src/processing/opengl/PSurfaceJOGL.java b/core/src/processing/opengl/PSurfaceJOGL.java
index 1cf3a6383..0764d2ff2 100644
--- a/core/src/processing/opengl/PSurfaceJOGL.java
+++ b/core/src/processing/opengl/PSurfaceJOGL.java
@@ -195,7 +195,13 @@ public class PSurfaceJOGL implements PSurface {
if (profile == null) {
if (PJOGL.profile == 2) {
try {
- profile = GLProfile.getGL2ES1();
+ if ("arm".equals(System.getProperty("os.arch"))) {
+ // request at least GL2 or GLES2
+ profile = GLProfile.getGL2ES2();
+ } else {
+ // stay compatible with previous versions for now
+ profile = GLProfile.getGL2ES1();
+ }
} catch (GLException ex) {
profile = GLProfile.getMaxFixedFunc(true);
}
diff --git a/core/src/processing/opengl/shaders/LightVert-vc4.glsl b/core/src/processing/opengl/shaders/LightVert-vc4.glsl
new file mode 100644
index 000000000..d008c529c
--- /dev/null
+++ b/core/src/processing/opengl/shaders/LightVert-vc4.glsl
@@ -0,0 +1,153 @@
+/*
+ Part of the Processing project - http://processing.org
+
+ Copyright (c) 2011-13 Ben Fry and Casey Reas
+
+ This library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Lesser General Public
+ License version 2.1 as published by the Free Software Foundation.
+
+ This library is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General
+ Public License along with this library; if not, write to the
+ Free Software Foundation, Inc., 59 Temple Place, Suite 330,
+ Boston, MA 02111-1307 USA
+ */
+
+#define PROCESSING_LIGHT_SHADER
+
+uniform mat4 modelviewMatrix;
+uniform mat4 transformMatrix;
+uniform mat3 normalMatrix;
+
+uniform int lightCount;
+uniform vec4 lightPosition[8];
+uniform vec3 lightNormal[8];
+uniform vec3 lightAmbient[8];
+uniform vec3 lightDiffuse[8];
+uniform vec3 lightSpecular[8];
+uniform vec3 lightFalloff[8];
+uniform vec2 lightSpot[8];
+
+attribute vec4 position;
+attribute vec4 color;
+attribute vec3 normal;
+
+attribute vec4 ambient;
+attribute vec4 specular;
+attribute vec4 emissive;
+attribute float shininess;
+
+varying vec4 vertColor;
+varying vec4 backVertColor;
+
+const float zero_float = 0.0;
+const float one_float = 1.0;
+const vec3 zero_vec3 = vec3(0);
+
+float falloffFactor(vec3 lightPos, vec3 vertPos, vec3 coeff) {
+ vec3 lpv = lightPos - vertPos;
+ vec3 dist = vec3(one_float);
+ dist.z = dot(lpv, lpv);
+ dist.y = sqrt(dist.z);
+ return one_float / dot(dist, coeff);
+}
+
+float spotFactor(vec3 lightPos, vec3 vertPos, vec3 lightNorm, float minCos, float spotExp) {
+ vec3 lpv = normalize(lightPos - vertPos);
+ vec3 nln = -one_float * lightNorm;
+ float spotCos = dot(nln, lpv);
+ return spotCos <= minCos ? zero_float : pow(spotCos, spotExp);
+}
+
+float lambertFactor(vec3 lightDir, vec3 vecNormal) {
+ return max(zero_float, dot(lightDir, vecNormal));
+}
+
+float blinnPhongFactor(vec3 lightDir, vec3 vertPos, vec3 vecNormal, float shine) {
+ vec3 np = normalize(vertPos);
+ vec3 ldp = normalize(lightDir - np);
+ return pow(max(zero_float, dot(ldp, vecNormal)), shine);
+}
+
+void main() {
+ // Vertex in clip coordinates
+ gl_Position = transformMatrix * position;
+
+ // Vertex in eye coordinates
+ vec3 ecVertex = vec3(modelviewMatrix * position);
+
+ // Normal vector in eye coordinates
+ vec3 ecNormal = normalize(normalMatrix * normal);
+ vec3 ecNormalInv = ecNormal * -one_float;
+
+ // Light calculations
+ vec3 totalAmbient = vec3(0, 0, 0);
+
+ vec3 totalFrontDiffuse = vec3(0, 0, 0);
+ vec3 totalFrontSpecular = vec3(0, 0, 0);
+
+ vec3 totalBackDiffuse = vec3(0, 0, 0);
+ vec3 totalBackSpecular = vec3(0, 0, 0);
+
+ // prevent register allocation failure by limiting ourselves to
+ // two lights for now
+ for (int i = 0; i < 2; i++) {
+ if (lightCount == i) break;
+
+ vec3 lightPos = lightPosition[i].xyz;
+ bool isDir = zero_float < lightPosition[i].w;
+ float spotCos = lightSpot[i].x;
+ float spotExp = lightSpot[i].y;
+
+ vec3 lightDir;
+ float falloff;
+ float spotf;
+
+ if (isDir) {
+ falloff = one_float;
+ lightDir = -one_float * lightNormal[i];
+ } else {
+ falloff = falloffFactor(lightPos, ecVertex, lightFalloff[i]);
+ lightDir = normalize(lightPos - ecVertex);
+ }
+
+ spotf = spotExp > zero_float ? spotFactor(lightPos, ecVertex, lightNormal[i],
+ spotCos, spotExp)
+ : one_float;
+
+ if (any(greaterThan(lightAmbient[i], zero_vec3))) {
+ totalAmbient += lightAmbient[i] * falloff;
+ }
+
+ if (any(greaterThan(lightDiffuse[i], zero_vec3))) {
+ totalFrontDiffuse += lightDiffuse[i] * falloff * spotf *
+ lambertFactor(lightDir, ecNormal);
+ totalBackDiffuse += lightDiffuse[i] * falloff * spotf *
+ lambertFactor(lightDir, ecNormalInv);
+ }
+
+ if (any(greaterThan(lightSpecular[i], zero_vec3))) {
+ totalFrontSpecular += lightSpecular[i] * falloff * spotf *
+ blinnPhongFactor(lightDir, ecVertex, ecNormal, shininess);
+ totalBackSpecular += lightSpecular[i] * falloff * spotf *
+ blinnPhongFactor(lightDir, ecVertex, ecNormalInv, shininess);
+ }
+ }
+
+ // Calculating final color as result of all lights (plus emissive term).
+ // Transparency is determined exclusively by the diffuse component.
+ vertColor = vec4(totalAmbient, 0) * ambient +
+ vec4(totalFrontDiffuse, 1) * color +
+ vec4(totalFrontSpecular, 0) * specular +
+ vec4(emissive.rgb, 0);
+
+ backVertColor = vec4(totalAmbient, 0) * ambient +
+ vec4(totalBackDiffuse, 1) * color +
+ vec4(totalBackSpecular, 0) * specular +
+ vec4(emissive.rgb, 0);
+}
\ No newline at end of file
diff --git a/core/src/processing/opengl/shaders/LightVert.glsl b/core/src/processing/opengl/shaders/LightVert.glsl
index 8d75f970a..747e0295d 100644
--- a/core/src/processing/opengl/shaders/LightVert.glsl
+++ b/core/src/processing/opengl/shaders/LightVert.glsl
@@ -29,7 +29,7 @@ uniform vec4 lightPosition[8];
uniform vec3 lightNormal[8];
uniform vec3 lightAmbient[8];
uniform vec3 lightDiffuse[8];
-uniform vec3 lightSpecular[8];
+uniform vec3 lightSpecular[8];
uniform vec3 lightFalloff[8];
uniform vec2 lightSpot[8];
diff --git a/core/src/processing/opengl/shaders/TexLightVert-vc4.glsl b/core/src/processing/opengl/shaders/TexLightVert-vc4.glsl
new file mode 100644
index 000000000..ef5ed5a61
--- /dev/null
+++ b/core/src/processing/opengl/shaders/TexLightVert-vc4.glsl
@@ -0,0 +1,159 @@
+/*
+ Part of the Processing project - http://processing.org
+
+ Copyright (c) 2011-13 Ben Fry and Casey Reas
+
+ This library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Lesser General Public
+ License version 2.1 as published by the Free Software Foundation.
+
+ This library is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General
+ Public License along with this library; if not, write to the
+ Free Software Foundation, Inc., 59 Temple Place, Suite 330,
+ Boston, MA 02111-1307 USA
+ */
+
+#define PROCESSING_TEXLIGHT_SHADER
+
+uniform mat4 modelviewMatrix;
+uniform mat4 transformMatrix;
+uniform mat3 normalMatrix;
+uniform mat4 texMatrix;
+
+uniform int lightCount;
+uniform vec4 lightPosition[8];
+uniform vec3 lightNormal[8];
+uniform vec3 lightAmbient[8];
+uniform vec3 lightDiffuse[8];
+uniform vec3 lightSpecular[8];
+uniform vec3 lightFalloff[8];
+uniform vec2 lightSpot[8];
+
+attribute vec4 position;
+attribute vec4 color;
+attribute vec3 normal;
+attribute vec2 texCoord;
+
+attribute vec4 ambient;
+attribute vec4 specular;
+attribute vec4 emissive;
+attribute float shininess;
+
+varying vec4 vertColor;
+varying vec4 backVertColor;
+varying vec4 vertTexCoord;
+
+const float zero_float = 0.0;
+const float one_float = 1.0;
+const vec3 zero_vec3 = vec3(0);
+
+float falloffFactor(vec3 lightPos, vec3 vertPos, vec3 coeff) {
+ vec3 lpv = lightPos - vertPos;
+ vec3 dist = vec3(one_float);
+ dist.z = dot(lpv, lpv);
+ dist.y = sqrt(dist.z);
+ return one_float / dot(dist, coeff);
+}
+
+float spotFactor(vec3 lightPos, vec3 vertPos, vec3 lightNorm, float minCos, float spotExp) {
+ vec3 lpv = normalize(lightPos - vertPos);
+ vec3 nln = -one_float * lightNorm;
+ float spotCos = dot(nln, lpv);
+ return spotCos <= minCos ? zero_float : pow(spotCos, spotExp);
+}
+
+float lambertFactor(vec3 lightDir, vec3 vecNormal) {
+ return max(zero_float, dot(lightDir, vecNormal));
+}
+
+float blinnPhongFactor(vec3 lightDir, vec3 vertPos, vec3 vecNormal, float shine) {
+ vec3 np = normalize(vertPos);
+ vec3 ldp = normalize(lightDir - np);
+ return pow(max(zero_float, dot(ldp, vecNormal)), shine);
+}
+
+void main() {
+ // Vertex in clip coordinates
+ gl_Position = transformMatrix * position;
+
+ // Vertex in eye coordinates
+ vec3 ecVertex = vec3(modelviewMatrix * position);
+
+ // Normal vector in eye coordinates
+ vec3 ecNormal = normalize(normalMatrix * normal);
+ vec3 ecNormalInv = ecNormal * -one_float;
+
+ // Light calculations
+ vec3 totalAmbient = vec3(0, 0, 0);
+
+ vec3 totalFrontDiffuse = vec3(0, 0, 0);
+ vec3 totalFrontSpecular = vec3(0, 0, 0);
+
+ vec3 totalBackDiffuse = vec3(0, 0, 0);
+ vec3 totalBackSpecular = vec3(0, 0, 0);
+
+ // prevent register allocation failure by limiting ourselves to
+ // two lights for now
+ for (int i = 0; i < 2; i++) {
+ if (lightCount == i) break;
+
+ vec3 lightPos = lightPosition[i].xyz;
+ bool isDir = zero_float < lightPosition[i].w;
+ float spotCos = lightSpot[i].x;
+ float spotExp = lightSpot[i].y;
+
+ vec3 lightDir;
+ float falloff;
+ float spotf;
+
+ if (isDir) {
+ falloff = one_float;
+ lightDir = -one_float * lightNormal[i];
+ } else {
+ falloff = falloffFactor(lightPos, ecVertex, lightFalloff[i]);
+ lightDir = normalize(lightPos - ecVertex);
+ }
+
+ spotf = spotExp > zero_float ? spotFactor(lightPos, ecVertex, lightNormal[i],
+ spotCos, spotExp)
+ : one_float;
+
+ if (any(greaterThan(lightAmbient[i], zero_vec3))) {
+ totalAmbient += lightAmbient[i] * falloff;
+ }
+
+ if (any(greaterThan(lightDiffuse[i], zero_vec3))) {
+ totalFrontDiffuse += lightDiffuse[i] * falloff * spotf *
+ lambertFactor(lightDir, ecNormal);
+ totalBackDiffuse += lightDiffuse[i] * falloff * spotf *
+ lambertFactor(lightDir, ecNormalInv);
+ }
+
+ if (any(greaterThan(lightSpecular[i], zero_vec3))) {
+ totalFrontSpecular += lightSpecular[i] * falloff * spotf *
+ blinnPhongFactor(lightDir, ecVertex, ecNormal, shininess);
+ totalBackSpecular += lightSpecular[i] * falloff * spotf *
+ blinnPhongFactor(lightDir, ecVertex, ecNormalInv, shininess);
+ }
+ }
+
+ // Calculating final color as result of all lights (plus emissive term).
+ // Transparency is determined exclusively by the diffuse component.
+ vertColor = vec4(totalAmbient, 0) * ambient +
+ vec4(totalFrontDiffuse, 1) * color +
+ vec4(totalFrontSpecular, 0) * specular +
+ vec4(emissive.rgb, 0);
+
+ backVertColor = vec4(totalAmbient, 0) * ambient +
+ vec4(totalBackDiffuse, 1) * color +
+ vec4(totalBackSpecular, 0) * specular +
+ vec4(emissive.rgb, 0);
+
+ // Calculating texture coordinates, with r and q set both to one
+ vertTexCoord = texMatrix * vec4(texCoord, 1.0, 1.0);
+}
diff --git a/core/src/processing/opengl/shaders/TexLightVert.glsl b/core/src/processing/opengl/shaders/TexLightVert.glsl
index d9f2cde3a..a69c66dc0 100644
--- a/core/src/processing/opengl/shaders/TexLightVert.glsl
+++ b/core/src/processing/opengl/shaders/TexLightVert.glsl
@@ -30,7 +30,7 @@ uniform vec4 lightPosition[8];
uniform vec3 lightNormal[8];
uniform vec3 lightAmbient[8];
uniform vec3 lightDiffuse[8];
-uniform vec3 lightSpecular[8];
+uniform vec3 lightSpecular[8];
uniform vec3 lightFalloff[8];
uniform vec2 lightSpot[8];
diff --git a/java/src/processing/mode/java/Commander.java b/java/src/processing/mode/java/Commander.java
index 4d3ecf0e4..fc46ba66d 100644
--- a/java/src/processing/mode/java/Commander.java
+++ b/java/src/processing/mode/java/Commander.java
@@ -35,6 +35,7 @@ import processing.app.SketchException;
import processing.app.Util;
import processing.app.contrib.ModeContribution;
import processing.core.PApplet;
+import processing.core.PConstants;
import processing.mode.java.runner.Runner;
@@ -280,14 +281,9 @@ public class Commander implements RunnerListener {
JavaBuild build = new JavaBuild(sketch);
build.build(true);
if (build != null) {
-// if (platformBits == 0) {
-// platformBits = Base.getNativeBits();
-// }
-// if (platformBits == 0 &&
-// Library.hasMultipleArch(platform, build.getImportedLibraries())) {
-// complainAndQuit("This sketch can be exported for 32- or 64-bit, please specify one.", true);
-// }
- success = build.exportApplication(outputFolder, platform, platformBits, embedJava);
+
+ String variant = Base.getVariant();
+ success = build.exportApplication(outputFolder, platform, variant, embedJava);
}
}
}
diff --git a/java/src/processing/mode/java/JavaBuild.java b/java/src/processing/mode/java/JavaBuild.java
index deda39941..3950a6831 100644
--- a/java/src/processing/mode/java/JavaBuild.java
+++ b/java/src/processing/mode/java/JavaBuild.java
@@ -796,17 +796,24 @@ public class JavaBuild {
if (Library.hasMultipleArch(platform, importedLibraries)) {
// export the 32-bit version
folder = new File(sketch.getFolder(), "application." + platformName + "32");
- if (!exportApplication(folder, platform, 32, embedJava && Base.getNativeBits() == 32)) {
+ if (!exportApplication(folder, platform, "32", embedJava && Base.getNativeBits() == 32 && "x86".equals(Base.getNativeArch()))) {
return false;
}
// export the 64-bit version
folder = new File(sketch.getFolder(), "application." + platformName + "64");
- if (!exportApplication(folder, platform, 64, embedJava && Base.getNativeBits() == 64)) {
+ if (!exportApplication(folder, platform, "64", embedJava && Base.getNativeBits() == 64 && "x86".equals(Base.getNativeArch()))) {
return false;
}
+ if (platform == PConstants.LINUX) {
+ // export the armv6hf version as well
+ folder = new File(sketch.getFolder(), "application.linux-armv6hf");
+ if (!exportApplication(folder, platform, "armv6hf", embedJava && Base.getNativeBits() == 32 && "arm".equals(Base.getNativeArch()))) {
+ return false;
+ }
+ }
} else { // just make a single one for this platform
folder = new File(sketch.getFolder(), "application." + platformName);
- if (!exportApplication(folder, platform, 0, embedJava)) {
+ if (!exportApplication(folder, platform, "", embedJava)) {
return false;
}
}
@@ -847,18 +854,18 @@ public class JavaBuild {
*/
protected boolean exportApplication(File destFolder,
int exportPlatform,
- int exportBits,
+ String exportVariant,
boolean embedJava) throws IOException, SketchException {
// TODO this should probably be a dialog box instead of a warning
// on the terminal. And the message should be written better than this.
// http://code.google.com/p/processing/issues/detail?id=884
for (Library library : importedLibraries) {
- if (!library.supportsArch(exportPlatform, exportBits)) {
+ if (!library.supportsArch(exportPlatform, exportVariant)) {
String pn = PConstants.platformNames[exportPlatform];
Base.showWarning("Quibbles 'n Bits",
- "The application." + pn + exportBits +
+ "The application." + pn + exportVariant +
" folder will not be created\n" +
- "because no " + exportBits + "-bit version of " +
+ "because no " + exportVariant + " version of " +
library.getName() + " is available for " + pn, null);
return true; // don't cancel all exports for this, just move along
}
@@ -1062,7 +1069,7 @@ public class JavaBuild {
/// add contents of 'library' folders to the export
for (Library library : importedLibraries) {
// add each item from the library folder / export list to the output
- for (File exportFile : library.getApplicationExports(exportPlatform, exportBits)) {
+ for (File exportFile : library.getApplicationExports(exportPlatform, exportVariant)) {
// System.out.println("export: " + exportFile);
String exportName = exportFile.getName();
if (!exportFile.exists()) {
diff --git a/java/src/processing/mode/java/runner/Runner.java b/java/src/processing/mode/java/runner/Runner.java
index efb17f00d..2e910b93a 100644
--- a/java/src/processing/mode/java/runner/Runner.java
+++ b/java/src/processing/mode/java/runner/Runner.java
@@ -90,9 +90,11 @@ public class Runner implements MessageConsumer {
// Make sure all the imported libraries will actually run with this setup.
int bits = Base.getNativeBits();
+ String variant = Base.getVariant();
+
for (Library library : build.getImportedLibraries()) {
- if (!library.supportsArch(PApplet.platform, bits)) {
- sketchErr.println(library.getName() + " does not run in " + bits + "-bit mode.");
+ if (!library.supportsArch(PApplet.platform, variant)) {
+ sketchErr.println(library.getName() + " does not run on this architecture: " + variant);
int opposite = (bits == 32) ? 64 : 32;
if (Base.isMacOS()) {
//if (library.supportsArch(PConstants.MACOSX, opposite)) { // should always be true
@@ -668,7 +670,7 @@ public class Runner implements MessageConsumer {
listener.statusError("A library used by this sketch is not installed properly.");
err.println("A library relies on native code that's not available.");
err.println("Or only works properly when the sketch is run as a " +
- ((Base.getNativeBits() == 32) ? "64-bit " : "32-bit ") + " application.");
+ ((Base.getNativeBits() == 32) ? "64-bit" : "32-bit") + " application.");
} else if (exceptionClass.equals("java.lang.StackOverflowError")) {
listener.statusError("StackOverflowError: This sketch is attempting too much recursion.");