Hi guys, i need to handle base64 pdf to pdf file in one of my app, so i’m building a uno module to do it.
the code below will describe my integration on both iOS and android.
AndroidImpl.uno file.
using Uno;
using Uno.UX;
using Uno.Collections;
using Uno.Compiler.ExportTargetInterop;
using Fuse;
using Fuse.Triggers;
using Fuse.Controls;
using Fuse.Controls.Native;
using Fuse.Controls.Native.Android;
using Uno.Threading;
namespace PDF
{
[ForeignInclude(Language.Java, "android.util.Base64", "java.io.FileOutputStream", "java.io.File", "android.content.Context")]
[Require("AndroidManifest.Permission", "android.permission.WRITE_EXTERNAL_STORAGE")]
[Require("AndroidManifest.Permission", "android.permission.WRITE_INTERNAL_STORAGE")]
extern(android)
class Transform: Promise<string>
{
public Transform(string base64String, string filePath)
{
Init(base64String, filePath);
}
[Foreign(Language.Java)]
public void Init(string base64String, string filePath)
@{
try{
FileOutputStream fos = new FileOutputStream(filePath);
fos.write(Base64.decode(base64String, Base64.NO_WRAP));
fos.close();
}catch(Exception e)
{
@{Transform:Of(_this).Reject(string):Call(e.toString())};
} finally {
@{Transform:Of(_this).Resolve(string):Call("yess file added")};
}
@}
void Resolve(string message)
{
base.Resolve(message);
}
void Reject(string reason)
{
Reject(new Exception(reason));
}
}
[ForeignInclude(Language.Java, "com.fuse.Activity", "android.content.Context", "android.content.Intent", "android.net.Uri", "java.io.File")]
extern(android)
class LaunchScan: Promise<string>
{
public LaunchScan(string path)
{
Init(path);
}
[Foreign(Language.Java)]
public void Init(string path)
@{
try {
Uri uri = Uri.parse(path);
Intent intent = new Intent(Intent.ACTION_VIEW);
intent.setDataAndType(uri, "application/pdf");
intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
if(intent!=null){
Activity.getRootActivity().startActivity(intent);
}
} catch (Exception e) {
@{LaunchScan:Of(_this).Reject(string):Call(e.toString())};
e.printStackTrace();
}
@}
void Resolve(string message)
{
base.Resolve(message);
}
void Reject(string reason)
{
Reject(new Exception(reason));
}
}
}
PDFJS.uno
using Uno;
using Uno.UX;
using Uno.Threading;
using Uno.Text;
using Uno.Platform;
using Uno.Compiler.ExportTargetInterop;
using Uno.Collections;
using Fuse;
using Fuse.Scripting;
using Fuse.Reactive;
namespace PDF
{
[UXGlobalModule]
public sealed class PDFmodule: NativeModule
{
static readonly PDFmodule _instance;
public PDFmodule()
{
if(_instance != null) return;
Uno.UX.Resource.SetGlobalKey(_instance = this, "PDF");
AddMember(new NativePromise<string, string>("Transform", Transform));
AddMember(new NativePromise<string, string>("LaunchScan", LaunchScan));
}
Future<string> Transform(object[] args)
{
var base64 = (string)args[0];
var filepath = (string)args[1];
return new PDF.Transform(base64, filepath);
}
Future<string> LaunchScan(object[] args)
{
var path = (string)args[0];
return new PDF.LaunchScan(path);
}
}
}
The transform method take a base64 pdf and transform it into a real pdf file before saving it locally. for specifying path i’m using FileSystem.dataDirectory + "/file.pdf"
all seems to work perfectly, but when i try the launch the same file save with my LaunchScan method, the pdf file doesn’t launch and i have this kind of method android.content.ActivityNotFoundException: No Activity found to handle Intent { act=android.intent.action.VIEW dat=/data/user/0/com.apps.pdf/files/file.pdf typ=application/pdf flg=0x4000000 }
anyone can help me on this ?
i’m doin the same with my iOS implementation.
using Uno;
using Uno.UX;
using Uno.Collections;
using Uno.Compiler.ExportTargetInterop;
using Fuse;
using Fuse.Triggers;
using Fuse.Controls;
using Fuse.Controls.Native;
using Fuse.Controls.Native.iOS;
using Uno.Threading;
namespace PDF
{
extern(iOS)
class Transform: Promise<string>
{
[Foreign(Language.ObjC)]
public Transform(string base64, string directory)
@{
@try {
NSString *base64Encoded = base64;
NSData *data = [[NSData alloc] initWithBase64EncodedString:base64Encoded options:0];
NSString *path = directory;
[data writeToFile:path atomically:YES];
}
@catch (NSException *exception) {
NSLog(@"%@", exception.reason);
@{Transform:Of(_this).Reject(string):Call(@"Vous devez etre connecter")};
}
@finally {
@{Transform:Of(_this).Resolve(string):Call(@"ahhh sccesss")};
}
@}
void Resolve(string message)
{
base.Resolve(message);
}
void Reject(string reason)
{
Reject(new Exception(reason));
}
}
[Require("Source.Include", "WebKit/WebKit.h")]
extern(iOS)
class LaunchScan: Promise<string>
{
[Foreign(Language.ObjC)]
public LaunchScan(string path)
@{
@try {
UIWebView *webView = [[UIWebView alloc] init];
webView.scalesPageToFit = YES;
NSURL *targetURL = [NSURL fileURLWithPath:path];
NSURLRequest *request = [NSURLRequest requestWithURL:targetURL];
[webView loadRequest:request];
}
@catch (NSException *exception) {
NSLog(@"%@", exception.reason);
@{LaunchScan:Of(_this).Reject(string):Call(@"La lecture du fichier a echoué")};
}
@finally {
@{LaunchScan:Of(_this).Resolve(string):Call(@"file open")};
}
@}
void Resolve(string message)
{
base.Resolve(message);
}
void Reject(string reason)
{
Reject(new Exception(reason));
}
}
}
Transform method works but i’m not able to launch the webview, for showing the pdf , anyone can show me how to successfully launch the webview here and show the pdf ?