Commit 093421cf authored by Igor Demin's avatar Igor Demin

Screenshot based testing

parent 620547af
<component name="ProjectRunConfigurationManager">
<configuration default="false" name="test" type="GradleRunConfiguration" factoryName="Gradle">
<ExternalSystemSettings>
<option name="executionName" />
<option name="externalProjectPath" value="$PROJECT_DIR$/samples/SkijaInjectSample" />
<option name="externalSystemIdString" value="GRADLE" />
<option name="scriptParameters" value="" />
<option name="taskDescriptions">
<list />
</option>
<option name="taskNames">
<list>
<option value="test" />
</list>
</option>
<option name="vmOptions" value="" />
</ExternalSystemSettings>
<ExternalSystemDebugServerProcess>true</ExternalSystemDebugServerProcess>
<ExternalSystemReattachDebugProcess>true</ExternalSystemReattachDebugProcess>
<DebugAllEnabled>false</DebugAllEnabled>
<method v="2">
<option name="Gradle.BeforeRunTask" enabled="false" tasks="publishToMavenLocal" externalProjectPath="$PROJECT_DIR$/skiko" vmOptions="" scriptParameters="" />
</method>
</configuration>
</component>
\ No newline at end of file
......@@ -56,4 +56,15 @@ application {
run {
systemProperty("skiko.fps.enabled", "true")
}
test {
systemProperty("skiko.test.screenshots.dir", new File(project.projectDir, "src/test/screenshots").absolutePath)
// Tests should be determined, so disable scaling.
// On MacOs we need the actual scale, otherwise we will have aliased screenshots because of scaling.
if (System.getProperty("os.name") != "Mac OS X") {
systemProperty("sun.java2d.dpiaware", "false")
systemProperty("sun.java2d.uiScale", "1")
}
}
\ No newline at end of file
/*
* This Kotlin source file was generated by the Gradle 'init' task.
*/
package SkijaInjectSample
import kotlin.test.Test
import kotlin.test.assertNotNull
class AppTest {
// @Test fun testAppHasAGreeting() {
// val classUnderTest = App()
// assertNotNull(classUnderTest.greeting, "app should have a greeting")
// }
}
package org.jetbrains.skiko
import java.awt.image.BufferedImage
fun isContentSame(img1: BufferedImage, img2: BufferedImage): Boolean {
if (img1.width == img2.width && img1.height == img2.height) {
for (x in 0 until img1.width) {
for (y in 0 until img1.height) {
if (img1.getRGB(x, y) != img2.getRGB(x, y)) {
return false
}
}
}
} else {
return false
}
return true
}
\ No newline at end of file
package org.jetbrains.skiko
import org.junit.rules.TestRule
import org.junit.runner.Description
import org.junit.runners.model.Statement
import java.awt.Rectangle
import java.awt.Robot
import java.io.File
import javax.imageio.ImageIO
// TODO macOs has wrong colors. Only white, black, red and green are correct
class ScreenshotTestRule(private val robot: Robot) : TestRule {
private lateinit var testIdentifier: String
private val screenshotsDir = File(System.getProperty("skiko.test.screenshots.dir")!!)
override fun apply(base: Statement, description: Description): Statement {
return object : Statement() {
override fun evaluate() {
testIdentifier = "${description.className}_${description.methodName}"
.replace(".", "_")
.replace(",", "_")
.replace(" ", "_")
.replace("(", "_")
.replace(")", "_")
.replace("__", "_")
.replace("__", "_")
.removePrefix("_")
.removeSuffix("_")
base.evaluate()
}
}
}
fun assert(rectangle: Rectangle, id: String = "") {
val actual = robot.createScreenCapture(rectangle)
val name = if (id.isNotEmpty()) "${testIdentifier}_$id" else testIdentifier
val actualFile = File(screenshotsDir, "${name}_actual.png")
val expectedFile = File(screenshotsDir, "$name.png")
if (actualFile.exists()) {
actualFile.delete()
}
if (expectedFile.exists()) {
val expected = ImageIO.read(expectedFile)
if (!isContentSame(expected, actual)) {
ImageIO.write(actual, "png", actualFile)
throw AssertionError(
"Image mismatch! Expected image ${expectedFile.absolutePath}, actual: ${actualFile.absolutePath}"
)
}
} else {
ImageIO.write(actual, "png", actualFile)
throw AssertionError(
"Missing screenshot image " +
"${actualFile.absolutePath}. " +
"Did you mean to check in a new image?"
)
}
}
}
\ No newline at end of file
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment