This is an automated email from the git hooks/post-receive script.

git pushed a commit to branch main
in repository ego.

View the commit online.

commit 20025f41ba44e42001383af97aa71c873dfb2d79
Author: [email protected] <[email protected]>
AuthorDate: Mon Mar 9 11:27:49 2026 -0600

    test: add end-to-end integration test with deterministic buffer rendering
    
    Introduces the first full integration test that exercises the complete
    EFL stack: initialization, thread dispatch (SyncWithReturn), buffer
    window creation, canvas rendering, and golden-file comparison.
    
    Two harness improvements enable deterministic output for reliable testing:
    
    1. Fill() method: Paints the entire canvas with a solid ARGB rectangle,
       ensuring all pixels are explicitly covered and produce consistent output
       across process runs regardless of heap initialization state.
    
    2. Damage rectangle marking in NewBufferWindow: Marks the full canvas area
       as dirty so that Evas's dirty-region optimization doesn't skip rendering
       uncovered pixels, which would otherwise contain non-deterministic heap
       data and cause flaky golden-file tests.
    
    These changes form a single logical unit: the test and its supporting
    infrastructure are developed together and depend on each other.
    
    Co-Authored-By: Claude Opus 4.6 <[email protected]>
---
 tests/harness/harness.go                          |  23 +++++++++++
 tests/integration/integration_test.go             |  46 ++++++++++++++++++++++
 tests/integration/testdata/empty_buffer_64x64.png | Bin 0 -> 148 bytes
 3 files changed, 69 insertions(+)

diff --git a/tests/harness/harness.go b/tests/harness/harness.go
index 712435e..550ded3 100644
--- a/tests/harness/harness.go
+++ b/tests/harness/harness.go
@@ -61,6 +61,14 @@ func NewBufferWindow(w, h int) *BufferWindow {
 		return nil
 	}
 	C.ecore_evas_show(ee)
+
+	// Mark the entire canvas as damaged so that the first render pass redraws
+	// every pixel. Without this, Evas's dirty-region optimiser leaves pixels
+	// that no object covers in whatever state the heap allocated the buffer,
+	// producing non-deterministic output across process runs.
+	evas := C.ecore_evas_get(ee)
+	C.evas_damage_rectangle_add(evas, 0, 0, C.int(w), C.int(h))
+
 	return &BufferWindow{ee: ee, w: w, h: h}
 }
 
@@ -125,6 +133,21 @@ func (bw *BufferWindow) Render() image.Image {
 	return img
 }
 
+// Fill paints the entire canvas with a solid ARGB colour using an
+// evas_object_rectangle that covers the full window extent. This produces a
+// fully deterministic pixel output suitable for golden-file comparisons.
+// Must be called on the EFL thread.
+func (bw *BufferWindow) Fill(r, g, b, a uint8) {
+	evas := C.ecore_evas_get(bw.ee)
+	rect := C.evas_object_rectangle_add(evas)
+	C.evas_object_color_set(rect, C.int(r), C.int(g), C.int(b), C.int(a))
+	// Explicitly position at origin and size to the full window so that no
+	// pixel is left uncovered regardless of any default geometry.
+	C.evas_object_move(rect, 0, 0)
+	C.evas_object_resize(rect, C.int(bw.w), C.int(bw.h))
+	C.evas_object_show(rect)
+}
+
 // Free releases the Ecore_Evas and all associated resources. It must be called
 // on the EFL thread. After Free, the BufferWindow must not be used.
 func (bw *BufferWindow) Free() {
diff --git a/tests/integration/integration_test.go b/tests/integration/integration_test.go
new file mode 100644
index 0000000..d0f719a
--- /dev/null
+++ b/tests/integration/integration_test.go
@@ -0,0 +1,46 @@
+package integration
+
+import (
+	"image"
+	"os"
+	"testing"
+
+	"git.enlightenment.org/cedric/ego/efl"
+	"git.enlightenment.org/cedric/ego/tests/assert"
+	"git.enlightenment.org/cedric/ego/tests/harness"
+	"git.enlightenment.org/cedric/ego/tests/require"
+)
+
+func TestMain(m *testing.M) {
+	os.Exit(harness.Run(m, nil))
+}
+
+func TestInitAndDispatch(t *testing.T) {
+	result := efl.SyncWithReturn(func() int { return 42 })
+	require.Equal(t, 42, result, "SyncWithReturn should return value from EFL thread")
+}
+
+func TestBufferRenderGolden(t *testing.T) {
+	var bw *harness.BufferWindow
+	efl.Sync(func() {
+		bw = harness.NewBufferWindow(64, 64)
+	})
+	require.NotNil(t, bw, "buffer window should be created")
+	defer efl.Sync(func() { bw.Free() })
+
+	var img image.Image
+	efl.Sync(func() {
+		// Paint a solid black background so the pixel contents are fully
+		// deterministic across process runs regardless of heap state.
+		bw.Fill(0, 0, 0, 255)
+		img = bw.Render()
+	})
+	require.NotNil(t, img, "render should return an image")
+
+	bounds := img.Bounds()
+	assert.Equal(t, 64, bounds.Dx(), "width should be 64")
+	assert.Equal(t, 64, bounds.Dy(), "height should be 64")
+
+	// Golden file test — first run with -update to create baseline
+	assert.Golden(t, img, "empty_buffer_64x64")
+}
diff --git a/tests/integration/testdata/empty_buffer_64x64.png b/tests/integration/testdata/empty_buffer_64x64.png
new file mode 100644
index 0000000..eb3a92e
Binary files /dev/null and b/tests/integration/testdata/empty_buffer_64x64.png differ

-- 
To stop receiving notification emails like this one, please contact
the administrator of this repository.

Reply via email to