Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 0 additions & 2 deletions CodenameOne/src/com/codename1/ui/Display.java
Original file line number Diff line number Diff line change
Expand Up @@ -2698,8 +2698,6 @@ public int convertToPixels(float value, byte unitType) {
* @since 8.0
*/
public int convertToPixels(float value, byte unitType, boolean horizontal) {


switch (unitType) {
case Style.UNIT_TYPE_REM:
return Math.round(value * Font.getDefaultFont().getHeight());
Expand Down
42 changes: 22 additions & 20 deletions CodenameOne/src/com/codename1/ui/Graphics.java
Original file line number Diff line number Diff line change
Expand Up @@ -636,6 +636,7 @@ public void drawString(String str, int x, int y) {
* @param character - the character to be drawn
* @param x the x coordinate of the baseline of the text
* @param y the y coordinate of the baseline of the text
* @deprecated use drawString instead, this method is inefficient
*/
public void drawChar(char character, int x, int y) {
drawString("" + character, x, y);
Expand All @@ -650,6 +651,7 @@ public void drawChar(char character, int x, int y) {
* @param length the number of characters to be drawn
* @param x the x coordinate of the baseline of the text
* @param y the y coordinate of the baseline of the text
* @deprecated use drawString instead, this method is inefficient
*/
public void drawChars(char[] data, int offset, int length, int x, int y) {
if (!(current instanceof CustomFont)) {
Expand Down Expand Up @@ -1089,9 +1091,9 @@ void drawImageArea(Image img, int x, int y, int imageX, int imageY, int imageWid
* Draws a closed polygon defined by arrays of x and y coordinates.
* Each pair of (x, y) coordinates defines a point.
*
* @param xPoints - a an array of x coordinates.
* @param yPoints - a an array of y coordinates.
* @param nPoints - a the total number of points.
* @param xPoints - an array of x coordinates.
* @param yPoints - an array of y coordinates.
* @param nPoints - the total number of points.
*/
public void drawPolygon(int[] xPoints, int[] yPoints, int nPoints) {
int[] cX = xPoints;
Expand Down Expand Up @@ -1149,7 +1151,7 @@ public int concatenateAlpha(int a) {
}

/**
* Returnes the alpha as a value between 0-255 (0 - 0xff) where 255 is completely opaque
* Returns the alpha as a value between 0-255 (0 - 0xff) where 255 is completely opaque
* and 0 is completely transparent
*
* @return the alpha value
Expand All @@ -1169,59 +1171,59 @@ public void setAlpha(int a) {
}

/**
* Returns true if anti-aliasing for standard rendering operations is supported,
* notice that text anti-aliasing is a separate attribute.
* Returns true if antialiasing for standard rendering operations is supported,
* notice that text antialiasing is a separate attribute.
*
* @return true if anti aliasing is supported
* @return true if antialiasing is supported
*/
public boolean isAntiAliasingSupported() {
return impl.isAntiAliasingSupported(nativeGraphics);
}

/**
* Returns true if anti-aliasing for text is supported,
* notice that text anti-aliasing is a separate attribute from standard anti-alisaing.
* Returns true if antialiasing for text is supported,
* notice that text antialiasing is a separate attribute from standard anti-alisaing.
*
* @return true if text anti aliasing is supported
* @return true if text antialiasing is supported
*/
public boolean isAntiAliasedTextSupported() {
return impl.isAntiAliasedTextSupported(nativeGraphics);
}


/**
* Returns true if anti-aliasing for standard rendering operations is turned on.
* Returns true if antialiasing for standard rendering operations is turned on.
*
* @return true if anti aliasing is active
* @return true if antialiasing is active
*/
public boolean isAntiAliased() {
return impl.isAntiAliased(nativeGraphics);
}

/**
* Set whether anti-aliasing for standard rendering operations is turned on.
* Set whether antialiasing for standard rendering operations is turned on.
*
* @param a true if anti aliasing is active
* @param a true if antialiasing is active
*/
public void setAntiAliased(boolean a) {
impl.setAntiAliased(nativeGraphics, a);
}

/**
* Indicates whether anti-aliasing for text is active,
* notice that text anti-aliasing is a separate attribute from standard anti-alisaing.
* Indicates whether antialiasing for text is active,
* notice that text antialiasing is a separate attribute from standard anti-alisaing.
*
* @return true if text anti aliasing is supported
* @return true if text antialiasing is supported
*/
public boolean isAntiAliasedText() {
return impl.isAntiAliasedText(nativeGraphics);
}

/**
* Set whether anti-aliasing for text is active,
* notice that text anti-aliasing is a separate attribute from standard anti-alisaing.
* Set whether antialiasing for text is active,
* notice that text antialiasing is a separate attribute from standard anti-alisaing.
*
* @param a true if text anti aliasing is supported
* @param a true if text antialiasing is supported
*/
public void setAntiAliasedText(boolean a) {
impl.setAntiAliasedText(nativeGraphics, a);
Expand Down
4 changes: 2 additions & 2 deletions CodenameOne/src/com/codename1/ui/Image.java
Original file line number Diff line number Diff line change
Expand Up @@ -392,7 +392,7 @@ public static Image exifRotation(String capturedImage, String rotatedImage, int
boolean isJpeg = isJPEG(fss.openInputStream(capturedImage));
boolean isPNG = isPNG(fss.openInputStream(capturedImage));
String format;
// IMPORTANT: we cannot relies on the file extension of the capturedImage path,
// IMPORTANT: we cannot rely on the file extension of the capturedImage path,
// because some Android devices return images from the gallery without extension!
if (!isJpeg && !isPNG) {
// Only jpeg and png images are supported, but some devices can return also different formats from the gallery (like gif).
Expand Down Expand Up @@ -472,7 +472,7 @@ public static Image exifRotation(String capturedImage, String rotatedImage, int

/**
* <p>
* Gets the EXIF orientation tag of an image, if it's available.</p>
* Gets the EXIF orientation tag of an image if it's available.</p>
* <p>
* The Exif Orientation Tag is a number from 0 to 8, for the explanation of
* each value see the
Expand Down
2 changes: 1 addition & 1 deletion Ports/JavaSE/src/com/codename1/impl/javase/JavaSEPort.java
Original file line number Diff line number Diff line change
Expand Up @@ -6831,7 +6831,7 @@ public Object createMutableImage(int width, int height, int fillColor) {
BufferedImage b = createTrackableBufferedImage(width, height);
if (a != 0) {
Graphics2D g = b.createGraphics();
g.setColor(new Color(fillColor));
g.setColor(new Color(fillColor, true));
g.fillRect(0, 0, width, height);
g.dispose();
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

import com.codename1.io.ConnectionRequest;
import com.codename1.junit.FormTest;
import com.codename1.junit.TestLogger;
import com.codename1.junit.UITestBase;

import java.util.List;
Expand All @@ -27,6 +28,7 @@ void testVisitQueuesAnalyticsRequest() {

@FormTest
void testCrashReportQueued() {
TestLogger.install();
implementation.clearQueuedRequests();
AnalyticsService.init("UA-2", "app.example.com");
AnalyticsService.setAppsMode(true);
Expand All @@ -35,5 +37,6 @@ void testCrashReportQueued() {
List<ConnectionRequest> requests = implementation.getQueuedRequests();
assertEquals(1, requests.size());
assertTrue(requests.get(0).getUrl().contains("google-analytics"));
TestLogger.remove();
}
}
10 changes: 5 additions & 5 deletions scripts/android/tests/ProcessScreenshots.java
Original file line number Diff line number Diff line change
Expand Up @@ -335,7 +335,7 @@ private static PNGImage loadPng(Path path) throws IOException {
byte[] data = Files.readAllBytes(path);
for (int i = 0; i < PNG_SIGNATURE.length; i++) {
if (data[i] != PNG_SIGNATURE[i]) {
throw new IOException(path + " is not a PNG file (missing signature)");
throw new IOException(path + " is not a PNG file (missing signature) on " + path);
}
}
int offset = PNG_SIGNATURE.length;
Expand All @@ -350,7 +350,7 @@ private static PNGImage loadPng(Path path) throws IOException {
byte[] type = java.util.Arrays.copyOfRange(data, offset + 4, offset + 8);
offset += 8;
if (offset + length + 4 > data.length) {
throw new IOException("PNG chunk truncated before CRC");
throw new IOException("PNG chunk truncated before CRC while processing: " + path);
}
byte[] chunkData = java.util.Arrays.copyOfRange(data, offset, offset + length);
offset += length + 4; // skip data + CRC
Expand All @@ -364,7 +364,7 @@ private static PNGImage loadPng(Path path) throws IOException {
int filter = chunkData[11] & 0xFF;
interlace = chunkData[12] & 0xFF;
if (compression != 0 || filter != 0) {
throw new IOException("Unsupported PNG compression or filter method");
throw new IOException("Unsupported PNG compression or filter method on " + path);
}
} else if ("IDAT".equals(chunkType)) {
idatChunks.add(chunkData);
Expand All @@ -373,10 +373,10 @@ private static PNGImage loadPng(Path path) throws IOException {
}
}
if (width <= 0 || height <= 0) {
throw new IOException("Missing IHDR chunk");
throw new IOException("Missing IHDR chunk on " + path);
}
if (interlace != 0) {
throw new IOException("Interlaced PNGs are not supported");
throw new IOException("Interlaced PNGs are not supported " + path);
}
int bytesPerPixel = bytesPerPixel(bitDepth, colorType);
byte[] combined = concat(idatChunks);
Expand Down
9 changes: 9 additions & 0 deletions scripts/hellocodenameone/common/src/main/css/theme.css
Original file line number Diff line number Diff line change
Expand Up @@ -52,3 +52,12 @@ SideCommand {
font-size: 4mm;
border-bottom: 2px solid #cccccc;
}

GraphicsForm {
background: #cccccc;
}

GraphicsComponent {
padding: 0px;
margin: 1mm;
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package com.codenameone.examples.hellocodenameone;

import com.codename1.system.Lifecycle;
import com.codename1.testing.TestReporting;
import com.codename1.ui.Button;
import com.codename1.ui.BrowserComponent;
Expand All @@ -15,33 +16,15 @@
import com.codenameone.examples.hellocodenameone.tests.Cn1ssDeviceRunner;
import com.codenameone.examples.hellocodenameone.tests.Cn1ssDeviceRunnerReporter;

public class HelloCodenameOne {
private Form current;
private static boolean deviceRunnerExecuted;

public class HelloCodenameOne extends Lifecycle {
@Override
public void init(Object context) {
super.init(context);
TestReporting.setInstance(new Cn1ssDeviceRunnerReporter());
}

public void start() {
if (current != null) {
current.show();
return;
}
Form c = CN.getCurrentForm();
if (!deviceRunnerExecuted || c == null) {
deviceRunnerExecuted = true;
new Thread(() -> new Cn1ssDeviceRunner().runSuite()).start();
return;
}
c.show();
}

public void stop() {
current = Display.getInstance().getCurrent();
}

public void destroy() {
// Nothing to clean up for this sample
@Override
public void runApp() {
new Thread(() -> new Cn1ssDeviceRunner().runSuite()).start();
}
}
Original file line number Diff line number Diff line change
@@ -1,18 +1,118 @@
package com.codenameone.examples.hellocodenameone.tests;

import com.codename1.ui.CN;
import com.codename1.ui.Component;
import com.codename1.ui.Font;
import com.codename1.ui.Form;
import com.codename1.ui.Graphics;
import com.codename1.ui.Image;
import com.codename1.ui.geom.Rectangle;
import com.codename1.ui.layouts.BorderLayout;
import com.codename1.ui.layouts.GridLayout;

abstract class AbstractGraphicsScreenshotTest extends BaseTest {
protected abstract Component createContent();
public abstract class AbstractGraphicsScreenshotTest extends BaseTest {
private final int[] colorSet = {0xff0000, 0xff00, 0xff, 0xffffff};
private int currentColor = -1;
private int factor = 0;

protected void nextColor(Graphics g) {
if(factor == 0) {
factor = CN.getDisplayWidth() < 400 ? 5 : 1;
}
if(currentColor == -1) {
currentColor = 0;
g.setColor(colorSet[0]);
}
g.darkerColor(1);
if(g.getColor() == 0) {
currentColor++;
if (currentColor == colorSet.length) {
currentColor = 0;
}
g.setColor(colorSet[currentColor]);
}
}

protected abstract void drawContent(Graphics g, Rectangle bounds);

protected abstract String screenshotName();

static abstract class CleanPaintComponent extends Component {
CleanPaintComponent() {
setUIID("GraphicsComponent");
}

@Override
public void paint(Graphics g) {
int alpha = g.getAlpha();
int color = g.getColor();
Font font = g.getFont();
g.pushClip();
cleanPaint(g);
g.popClip();
g.setFont(font);
g.setColor(color);
g.setAlpha(alpha);
}

protected abstract void cleanPaint(Graphics g);
}

@Override
public boolean runTest() {
Form form = createForm("Graphics", new BorderLayout(), screenshotName());
form.add(BorderLayout.CENTER, createContent());
Form form = createForm(screenshotName(), new GridLayout(2, 2), screenshotName());
form.setUIID("GraphicsForm");
form.add(new CleanPaintComponent() {
@Override
public void cleanPaint(Graphics g) {
currentColor = -1;
g.setAntiAliased(false);
g.setAntiAliasedText(false);
g.fillRect(getX(), getY(), getWidth(), getHeight());
drawContent(g, getBounds());
Comment on lines +68 to +72

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Avoid double-applying component translation in CleanPaintComponent

The graphics context is already translated to the component origin before paint() runs, but the clearing/drawing logic uses getX()/getY() (and passes getBounds() containing those offsets) when filling and rendering. In the 2×2 grid, the three components whose X/Y are non‑zero end up drawing content offset by their position twice, so their aliased/anti‑aliased panels render off-screen and the resulting screenshots miss those variants. Use component-local coordinates (0,0,width,height) when painting.

Useful? React with 👍 / 👎.

}
});
form.add(new CleanPaintComponent() {
@Override
public void cleanPaint(Graphics g) {
currentColor = -1;
g.setAntiAliased(true);
g.setAntiAliasedText(true);
g.fillRect(getX(), getY(), getWidth(), getHeight());
drawContent(g, getBounds());
}
});
form.add(new CleanPaintComponent() {
private Image img;
@Override
public void cleanPaint(Graphics g) {
if (img == null || img.getWidth() != getWidth() || img.getHeight() != getHeight()) {
currentColor = -1;
img = Image.createImage(getWidth(), getHeight());
Graphics imgGraphics = img.getGraphics();
imgGraphics.setAntiAliased(false);
imgGraphics.setAntiAliasedText(false);
drawContent(imgGraphics, new Rectangle(0, 0, img.getWidth(), img.getHeight()));
}
g.drawImage(img, getX(), getY());
}
});
form.add(new CleanPaintComponent() {
private Image img;
@Override
public void cleanPaint(Graphics g) {
if (img == null || img.getWidth() != getWidth() || img.getHeight() != getHeight()) {
currentColor = -1;
img = Image.createImage(getWidth(), getHeight());
Graphics imgGraphics = img.getGraphics();
imgGraphics.setAntiAliased(true);
imgGraphics.setAntiAliasedText(true);
drawContent(imgGraphics, new Rectangle(0, 0, img.getWidth(), img.getHeight()));
}
g.drawImage(img, getX(), getY());
}
});

form.show();
return true;
}
Expand Down
Loading
Loading