summaryrefslogtreecommitdiffstats
path: root/mobile/android/geckoview/src/androidTest/java/org/mozilla/geckoview/test/PdfCreationTest.kt
blob: 9693139d9c6750cbe245db023fc233744cce035e (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
/* -*- Mode: Java; c-basic-offset: 4; tab-width: 4; indent-tabs-mode: nil; -*-
 * Any copyright is dedicated to the Public Domain.
   http://creativecommons.org/publicdomain/zero/1.0/ */

package org.mozilla.geckoview.test

import android.graphics.Bitmap
import android.graphics.Color
import android.graphics.Color.rgb
import android.graphics.pdf.PdfRenderer
import android.os.ParcelFileDescriptor
import androidx.test.ext.junit.rules.ActivityScenarioRule
import androidx.test.ext.junit.runners.AndroidJUnit4
import androidx.test.filters.LargeTest
import org.hamcrest.Matchers.equalTo
import org.junit.After
import org.junit.Assert.assertTrue
import org.junit.Before
import org.junit.Rule
import org.junit.Test
import org.junit.rules.RuleChain
import org.junit.runner.RunWith
import org.mozilla.geckoview.Autofill
import org.mozilla.geckoview.GeckoViewPrintDocumentAdapter
import org.mozilla.geckoview.test.rule.GeckoSessionTestRule.NullDelegate
import java.io.File
import java.io.InputStream
import kotlin.math.roundToInt

@RunWith(AndroidJUnit4::class)
@LargeTest
class PdfCreationTest : BaseSessionTest() {
    private val activityRule = ActivityScenarioRule(GeckoViewTestActivity::class.java)
    var deviceHeight = 0
    var deviceWidth = 0
    var scaledHeight = 0
    var scaledWidth = 12

    @get:Rule
    override val rules: RuleChain = RuleChain.outerRule(activityRule).around(sessionRule)

    @Before
    fun setup() {
        activityRule.scenario.onActivity {
            it.view.setSession(mainSession)
            deviceHeight = it.resources.displayMetrics.heightPixels
            deviceWidth = it.resources.displayMetrics.widthPixels
            scaledHeight = (scaledWidth * (deviceHeight / deviceWidth.toDouble())).roundToInt()
        }
    }

    @After
    fun cleanup() {
        activityRule.scenario.onActivity {
            it.view.releaseSession()
        }
    }

    private fun createFileDescriptor(pdfInputStream: InputStream): ParcelFileDescriptor {
        val file = File.createTempFile("temp", null)
        pdfInputStream.use { input ->
            file.outputStream().use { output ->
                input.copyTo(output)
            }
        }
        return ParcelFileDescriptor.open(file, ParcelFileDescriptor.MODE_READ_ONLY)
    }

    private fun pdfToBitmap(pdfInputStream: InputStream): ArrayList<Bitmap>? {
        val bitmaps: ArrayList<Bitmap> = ArrayList()
        try {
            val pdfRenderer = PdfRenderer(createFileDescriptor(pdfInputStream))
            for (pageNo in 0 until pdfRenderer.pageCount) {
                val page = pdfRenderer.openPage(pageNo)
                var bitmap = Bitmap.createBitmap(deviceWidth, deviceHeight, Bitmap.Config.ARGB_8888)
                page.render(bitmap, null, null, PdfRenderer.Page.RENDER_MODE_FOR_DISPLAY)
                bitmaps.add(bitmap)
                page.close()
            }
            pdfRenderer.close()
        } catch (e: Exception) {
            e.printStackTrace()
        }
        return bitmaps
    }

    @NullDelegate(Autofill.Delegate::class)
    @Test
    fun singleColorPdf() {
        activityRule.scenario.onActivity {
            mainSession.loadTestPath(COLOR_ORANGE_BACKGROUND_HTML_PATH)
            mainSession.waitForPageStop()
            val pdfInputStream = mainSession.saveAsPdf()
            sessionRule.waitForResult(pdfInputStream).let {
                val bitmap = pdfToBitmap(it)!![0]
                val scaled = Bitmap.createScaledBitmap(bitmap, scaledWidth, scaledHeight, false)
                val centerPixel = scaled.getPixel(scaledWidth / 2, scaledHeight / 2)
                val orange = rgb(255, 113, 57)
                assertTrue("The PDF orange color matches.", centerPixel == orange)
            }
        }
    }

    @NullDelegate(Autofill.Delegate::class)
    @Test
    fun rgbColorsPdf() {
        activityRule.scenario.onActivity {
            mainSession.loadTestPath(COLOR_GRID_HTML_PATH)
            mainSession.waitForPageStop()
            val pdfInputStream = mainSession.saveAsPdf()
            sessionRule.waitForResult(pdfInputStream).let {
                val bitmap = pdfToBitmap(it)!![0]
                val scaled = Bitmap.createScaledBitmap(bitmap, scaledWidth, scaledHeight, false)
                val redPixel = scaled.getPixel(2, scaledHeight / 2)
                assertTrue("The PDF red color matches.", redPixel == Color.RED)
                val greenPixel = scaled.getPixel(scaledWidth / 2, scaledHeight / 2)
                assertTrue("The PDF green color matches.", greenPixel == Color.GREEN)
                val bluePixel = scaled.getPixel(scaledWidth - 2, scaledHeight / 2)
                assertTrue("The PDF blue color matches.", bluePixel == Color.BLUE)
                val doPixelsMatch = (
                    redPixel == Color.RED &&
                        greenPixel == Color.GREEN &&
                        bluePixel == Color.BLUE
                    )
                assertTrue("The PDF generated RGB colors.", doPixelsMatch)
            }
        }
    }

    @NullDelegate(Autofill.Delegate::class)
    @Test
    fun makeTempPdfFileTest() {
        activityRule.scenario.onActivity { activity ->
            mainSession.loadTestPath(COLOR_ORANGE_BACKGROUND_HTML_PATH)
            mainSession.waitForPageStop()
            val pdfInputStream = mainSession.saveAsPdf()
            sessionRule.waitForResult(pdfInputStream).let { stream ->
                val file = GeckoViewPrintDocumentAdapter.makeTempPdfFile(stream, activity)!!
                assertTrue("PDF File exists.", file.exists())
                assertTrue("PDF File is not empty.", file.length() > 0L)
                file.delete()
            }
        }
    }

    @NullDelegate(Autofill.Delegate::class)
    @Test
    fun saveAPdfDocument() {
        activityRule.scenario.onActivity {
            mainSession.loadTestPath(HELLO_PDF_WORLD_PDF_PATH)
            mainSession.waitForPageStop()
            val pdfInputStream = mainSession.saveAsPdf()
            val originalBytes = getTestBytes(HELLO_PDF_WORLD_PDF_PATH)
            sessionRule.waitForResult(pdfInputStream).let {
                assertThat("The PDF File must the same as the original one.", it!!.readBytes(), equalTo(originalBytes))
            }
        }
    }
}