Pdf Creator on Capacitor Project

I did this quickly so anyone can feel free to correct it in a more professional manner.
After the code that Patrick provided, I added a variable to save the uri generated after creating the pdf.

image


Then I added the Capawesome file opener plugin in the same way explained in this tutorial for plugins that are not in Wappler (yet).

  1. Install the plugin
  • npm install @capawesome-team/capacitor-file-opener
  • npx cap sync
  1. Copy the plugin.js file from node_modules/@capawesome-team/capacitor-file-opener/dist to your folder, in my case I place it in js/plugins and renamed to fileopener.js.
    Don’t forget to call the js on your page:
    <script src="js/plugins/fileopener.js"></script>

Then we insert the code with a function that executes the plugin.
Inside it has the variable as path.

<script>
        function openPdf() {
  return new Promise(function(resolve, reject) {
    Capacitor.Plugins.FileOpener.openFile
({
      path: dmx.parse('var1.value')
    })
.then
(function()
 {
      resolve();
    })
.catch(function(error) 
{
      console.error('Error opening file:', error);
      reject(error);
    });
  });
}

    </script>

After doing this, all we have to do is call the function via the same flow:

This is the result:

Here is the entire code in case you need it:

<!doctype html>
<html>

<head>
	<script src="dmxAppConnect/dmxAppConnect.js"></script>
	<meta charset="UTF-8">
	<title>Untitled Document</title>

	<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
	<script src="js/routes.js" defer></script>
	<link rel="stylesheet" href="bootstrap/5/css/bootstrap.min.css" />
	<script src="https://cdn.jsdelivr.net/npm/pdfmake@0.2.9/build/pdfmake.min.js" defer></script>
	<script src="https://cdn.jsdelivr.net/npm/pdfmake@0.2.9/build/vfs_fonts.min.js" defer></script>
	<script src="https://cdn.jsdelivr.net/npm/html-to-pdfmake@2.5.2/browser.min.js" defer></script>
	<script src="dmxAppConnect/dmxPdfCreator/dmxPdfCreator.js" defer></script>
	<script src="dmxAppConnect/dmxRouting/dmxRouting.js" defer></script>
	<script src="capacitor.js"></script>
	<script src="js/plugins/filesystem/plugin.js" defer></script>
	<script src="js/plugins/fileopener.js"></script>
	<script src="dmxAppConnect/dmxCapacitorFilesystem/dmxCapacitorFilesystem.js" defer></script>
</head>

<body is="dmx-app" id="index">
	<dmx-value id="var1"></dmx-value>
	<dmx-pdf-creator id="pdfcreator1" content="#pdfcontent1"></dmx-pdf-creator>
	<script is="dmx-flow" id="flow1" type="text/dmx-flow">
[
  {
    run: {name: "pdf", outputType: "text", action: "{{pdfcreator1.getBase64()}}"}
  },
  {
    Capacitor.Filesystem.writeFile: {
      name: "writeFile",
      output: true,
      outputType: "object",
      path: "myFile.pdf",
      data: "{{pdf}}",
      directory: "DOCUMENTS"
    }
  },
  {
    run: {
      name: "seturi",
      outputType: "text",
      action: "{{var1.setValue(writeFile.uri)}}"
    }
  },
  {
    runJS: {name: "openpdf", outputType: "text", function: "openPdf"}
  }
]</script>

	<div is="dmx-view" id="view1"></div>
	<div class="container">
		<div class="row">
			<div class="col" is="dmx-pdf-content" id="pdfcontent1">
				<button id="btn1" class="btn btn-danger" dmx-on:click="flow1.run()">Download pdf</button>
				<h1>Pdf title</h1>
			</div>
		</div>
	</div>
<script>
        function openPdf() {
  return new Promise(function(resolve, reject) {
    Capacitor.Plugins.FileOpener.openFile
({
      path: dmx.parse('var1.value')
    })
.then
(function()
 {
      resolve();
    })
.catch(function(error) 
{
      console.error('Error:', error);
      reject(error);
    });
  });
}

    </script>
	<script src="bootstrap/5/js/bootstrap.bundle.min.js"></script>
</body>

</html>
1 Like

Wow… You save my life… I will sure try myself tonight. As now i have no access to PC… Again million thanks

Actually it’s @patrick you have to thank.
As I mentioned in the linked topic, the implementation of capacitor plugins is possible due to its explanation from some time ago.
I definitely owe him (and several others) a few beers :beers:

I can’t to test and tested immediately. It works well as below

I copy the apk and try on real phone. PDF when click no response. Any clue?

Mmm.
Can you debug the apk via usb?
https://developer.android.com/studio/debug/dev-options?hl=en-419#enable

Then check the console and see if you got some error there

Also verify if the permissions have been granted.


Error Found with Android Phone via UBS Debug

Do you manage to run it on Android Phone?

Does the error indicate that is due to CORS issue? Seems like only affect the fileopener.js

I think I found the problem of the file not created:

If you target SDK 30, then android:requestLegacyExternalStorage=“true” will not work on Android 11+ devices.
Google doesn’t allow to programmatically access external shared files anymore. (Documents and ExternalStorage)

https://developer.android.com/training/data-storage/use-cases#opt-out-in-production-app
We can modify the manifiest.xml, let me see, but first:
Can you use another directory?

Is actually js/fileopener.js in the project?
Have you done this?:

1 Like

After adding android:requestLegacyExternalStorage=“true” and it work on Both Emulator and Phone.

Thanks a lot… :muscle: :muscle:

Great news, just being curious, what android version is it?

I am using Huawei Pro 30 EMUI 12.0.0… Per google is based on Android 10

Hi Patrick, will the above be added into the future release?

The new getBase64 method will be available with the next update.

1 Like

Thanks