Onedrive api how to attach files rather than downloading? - javascript

I followed the interactive live sdk and added it into my HTML page.
Also, I have successfully added the callback.html page where I am successfully getting the file picker dialog box. Once I select file from the file dialog box it's getting downloaded which I understand because of WL.download function.
But all I want is to attach the files rather than downloading it. how to change the javascript in interactive live sdk
Any suggestions?

Sorry about that. You can either use the "source" or the "link" to accomplish this. On the ISDK for "Using the open from OneDrive picker", change the code following code snippet (I used "file.link" below). The Output box should give you some idea on what the link would be if you include it in your app. You'll, of course, will want to remove the "WL.download" function so that it doesn't download the file and add the file.link or file.source somewhere into your code instead of logging it like the ISDK does.
function openFromSkyDrive() {
WL.fileDialog({
mode: 'open',
select: 'single'
}).then(
function(response) {
log("The following file is being downloaded:");
log("");
var files = response.data.files;
for (var i = 0; i < files.length; i++) {
var file = files[i];
log(file.link);
WL.download({ "path": file.id + "/content" });
}
},
function(errorResponse) {
log("WL.fileDialog errorResponse = " + JSON.stringify(errorResponse));
}
);
}

In the ISDK (http://isdk.dev.live.com), you'll want to try using the "Using the save to OneDrive picker". You'll notice that WL.fileDialog is set to ({ mode: 'save' }) and the WL.upload function is called. I hope that helps.

Related

Trying to use pdf-lib to fill pdf form fields. Trouble Flattening and Saving Form

I'm looking into using the pdf-lib library form manipulating pdf forms. The package is located here: https://github.com/Hopding/pdf-lib
Edited the question yet again (it has been here for months and no takers on 2 bounties for 100) to just include a code snippet that is at least partially working after getting the right script tag libraries.
The issue I am having is that I want to be able to Flatten and Save the form after any online editing after the pre-populated form is edited and completed.
Here is a bit of a sample from what I have posted as an issue on Github in the pdf-lib repo here https://github.com/Hopding/pdf-lib/issues/965
$("#flatten").on("click", function(e) {
async function Flatten() {
pdfDoc = await PDFLib.PDFDocument.load(document.getElementById('pdf').src)
form = pdfDoc.getForm()
form.updateFieldAppearances();
checkboxes.forEach(function (item, index) {
checkBox = form.getCheckBox(item);
checkBox.defaultUpdateAppearances()
});
form.flatten()
pdfBytes = await pdfDoc.saveAsBase64({ dataUri: true })
document.getElementById('pdf').src = pdfBytes
}
Flatten();
});
$("#pdf").on("load", function(e) {
autoResize($(this));
});
function autoResize(iframe) {
// iframe.height($(iframe).contents().find('html').height());
iframe.height("1650px");
iframe.width("1275px");
iframe.show();
}
$("#saveform").on("click", function(e) {
download(document.getElementById('pdf').src, SaveAs+'.pdf', "application/pdf");
});
$("#sendform").on("click", function(e) {
alert(document.getElementById('pdf').src);
//download(document.getElementById('pdf').src, SaveAs+'.pdf', "application/pdf");
});
There is an archive.zip attached to the GitHub issue post. If you are interested, I suggest you put the two files there on a server to see what the issue is. It is setup to just work if you put the test.html file and the PDF on a webserver in the same directory (root of server) and then just open it up in a browser. If you type something into a field and then try to Flatten you'll be asked to stay on page or leave. That is what I want to try to fix.

How do I use a downloaded svg file within my application using Tizen Web studio?

I can get an SVG file downloaded, additionally, I can display svg files as you would normally within an image tag. I do not know how to access the folder location for downloads or the wgt-private folder so I may download images to a client's watch and then use the downloaded version.
I'm sure my file is downloading as I've console logged on successful download and when I list the items in the directory the file shows up.
Placing downloads/[filename] or wgt-private/[filename] does not appear to work as these are virtual file locations however I've no idea how to access these files within the application without using the filesystem methods.
Download:
var download_obj = new tizen.DownloadRequest('someFile.svg', 'wgt-private');//Hidden the actual location however this file does display when enterting the whole file location
tizen.download.start(download_obj, {
onprogress: function(id, receivedSize, totalSize) {
console.log(id);
console.log(receivedSize);
console.log(totalSize);
},
onpaused: function(id) {
console.log(id);
},
oncanceled: function(id) {
console.log(id);
},
oncompleted: function(id, fullPath) {
console.log(id);
console.log(fullPath);
},
onfailed: function(id, error) {
console.log(id);
console.log(JSON.stringify(error));
}
});
Full path comes out as: wgt-private/someFile.svg
Doesn't display as displays a file error in the console on all attempts.
I understand that your questions relates to how to show the image downloaded with tizen.download API in html img tag.
I can see two workarounds that could help you with it:
You can use filesystem API (which you would like to avoid), BUT since 5.0 there is a method which needs no additional privileges and I hope it will match your needs - FileSystemManager.toURI(). It just gets the path to file (returned by download API) and returns the full URI, able to be used in img.
I noticed that download to non-public directories on the device, download API returns the 'hidden' path which uses virtual root, but when downloading to public directory as 'downloads', the full path is returned and it works for img as well.
If both of above is not acceptable for you, I am afraid that the only alternative is to use regular tizen.filesystem API and resolve the path from download API and then use File.toURI() function to get the path.
var link = "http://techslides.com/demos/samples/sample.jpg"
var download_obj = new tizen.DownloadRequest(link, 'wgt-private');//Hidden the actual location however this file does display when enterting the whole file location
tizen.download.start(download_obj, {
oncompleted: function(id, fullPath) {
console.log("completed " + id + " : " + fullPath);
tizen.filesystem.resolve(fullPath, (s)=>{console.log("Resovled full path: " + s.toURI())}, (e) => {console.log(e)})
},
onfailed: function(id, error) {
console.log("failed " + id);
console.log(JSON.stringify(error));
}
});
You can find the proper web sample app: new Tizen project - Sample - Mobile 4.0 - Web application - Content - Download Manager
Open index.html and replace https://www.sample-videos.com/video/mkv/720/big_buck_bunny_720p_10mb.mkv with your file address.

Issue with Electron ipcRenderer.send

I have an Electron app. It sends via a ipcRenderer.send in renderer.js a download event to an ipcMain.on listener in index.js:
renderer.js:
for (var i=0; i < data3.projects.length; i++) {
var project = data3.projects[i];
for (var j=0; j < project.files.length; j++) {
var file = project.files[j];
async function downloadFunction(file) {
await ipcRenderer.send("download", {
url: file.url,
location: "/Users/Marc/GreenPool/" + project.projectId + "/files/"
})
console.log("downloaded " + file.url);
}
await downloadFunction(file);
}
}
index.js:
ipcMain.on("download", function (event, info) {
console.log(info.location);
download(mb.window.webContents, info.url, {directory:info.location});
});
So it is supposed to download (thanks to electron-dl npm package) all the files under project.files, and save them under info.location.
When there is only one project under data3.projects array, it works, the files get downloaded and stored under "/Users/Marc/GreenPool/" + project.projectId + "/files/".
But when there is more than one value in data3.projects array, it only saves the downloaded files of one of the data3.project, not of the others:
One has the files:
One doesn't:
We can see on the first picture that one of the files is duplicated. I think it shows that the issue has to do with the fact that after writing the first files in the first folder, it somehow still thinks that it is in this one when starting to write the second files (we can see it with file compute2Numbers(1).js being a duplicate because it is in the wrong folder).
And the log of console are logic:
index.js:
/Users/Marc/GreenPool/qjggnatri/files/
/Users/Marc/GreenPool/qjggnatri/files/
/Users/Marc/GreenPool/qjggnatri/files/
/Users/Marc/GreenPool/qjggnatri/files/
/Users/Marc/GreenPool/z9g7_a1qa/files/
/Users/Marc/GreenPool/z9g7_a1qa/files/
/Users/Marc/GreenPool/z9g7_a1qa/files/
/Users/Marc/GreenPool/z9g7_a1qa/files/
renderer.js:
It seems like it is an asynchronous issue. But I have wrapped the queries in an async await function to prevent the two download events from overlapping each other. And the logs of the console show it: first the files of the first value in data3.projects array are downloaded, then the files of the second value in data3.projects array are downloaded.
So how can I make it happen that the files get saved in the proper folder?

Why doesn't Microsoft Skydrive download multiple files even though MS example shows it? (wl.download)

Summary
I am attempting to find out why the wl.download function will not download more than one file even though the Microsoft examples seem to indicate that they can.
And, the code seems to be called for each file you attempt to download, but only the one file is actually downloaded.
Details
Here are the details of how you can see this problem which I've tried in IE 11.x and Chrome 30.x
If you will kindly go to :
http://isdk.dev.live.com/dev/isdk/ISDK.aspx?category=scenarioGroup_skyDrive&index=0
You will be able to run an example app which allows you to download files from your skydrive.
Note: the app does require you to allow the app to access your skydrive.
Once you get there you'll see code that looks like this on the right side of the page:
Alter One Value: select:
You need to alter one value: Change the
select: 'single'
to
select: 'multi'
which will allow you to select numerous files to download to your computer. If you do not make that one change then you won't be able to choose more than one file in the File dialog.
Click the Run Button to Start
Next, you'll see a [Run] button to start the app (above the code sample).
Go ahead and click that button.
Pick Files For Download
After that just traverse through your skydrive files and choose more than one in a folder and click the [Open] button. At that point, you will see one of the files actually downloads, and a number of file names are displayed in the bottom (output) section of the example web page.
My Questions
Why is it that the others do not download, even though wl.download is called in the loop, just as the console.log is called in the loop?
Is this a known limitation of the browser?
Is this a known bug in skydrive API?
Is this just a bug in the example code?
The problem here is that the call to wl.download({ "path": file.id + "/content" }) stores some internal state (among other things, the file being downloaded and the current status thereof). By looping over the list of files, that state is in fact overwritten with each call. When I tried downloading three text files at once, it was always the last one that was actually downloaded and never the first two.
The difficulty here is that the downloads are executed in the traditional fashion, whereby the server adds Content-Disposition: attachment to the response headers to force the browser to download the file. Because of this, it is not possible to receive notification of any kind when the download has actually completed, meaning that you can't perform the downloads serially to get around the state problem.
One approach that I thought might work is inspired by this question. According to the documentation, we can get a download link to a file if we append /content?suppress_redirects=true to its id. Using this approach, we can set the src property of an IFrame and download the file that way. This works OK, but it will only force a download for file types that the browser can't natively display (zip files, Exe files, etc.) due to the lack of the Content-Disposition: attachment response header.
The following is what I used in the Interactive Live SDK.
WL.init({ client_id: clientId, redirect_uri: redirectUri });
WL.login({ "scope": "wl.skydrive wl.signin" }).then(
function(response) {
openFromSkyDrive();
},
function(response) {
log("Failed to authenticate.");
}
);
function openFromSkyDrive() {
WL.fileDialog({
mode: 'open',
select: 'multi'
}).then(
function(response) {
log("The following file is being downloaded:");
log("");
var files = response.data.files;
for (var i = 0; i < files.length; i++) {
var file = files[i];
log(file.name);
WL.api({
path: file.id + "/content?suppress_redirects=true",
method: "GET"
}).then(
function (response) {
var iframe = document.createElement("iframe");
iframe.src = response.location;
iframe.style.display = "none";
document.body.appendChild(iframe);
},
function (responseFailed) {
log("Error calling API: " + responseFailed.error.message);
}
);
}
},
function(errorResponse) {
log("WL.fileDialog errorResponse = " + JSON.stringify(errorResponse));
}
);
}
function log(message) {
var child = document.createTextNode(message);
var parent = document.getElementById('JsOutputDiv') || document.body;
parent.appendChild(child);
parent.appendChild(document.createElement("br"));
}
Did you try to bind some events to the WL.download() method? According to the documentation:
The WL.download method accepts only one parameter:
The required path parameter specifies the unique SkyDrive file ID of the file to download.
If the WL.download method call is unsuccessful, you can use its then method's onError parameter to report the error. In this case, the WL.download doesn't support the onSuccess and onProgress parameters. If the WL.download method call is successful, the user experience for actually downloading the files will differ based on the type of web browser in use.
Perhaps you are getting some errors in your log to identify the problem.
For me, one suggestion without having checked the documentation, I can think of the fact that you are not waiting for each download to end. Why not change your loop in such a manner that you call WL.download() only if you know no other download is currently running ( like calling the next WL.download only in the success/complete event ):
WL.download({ "path": file.id + "/content" }).then(
function (response) {
window.console && console.log("File downloaded.");
//call the next WL.download() here <!-----------------
},
function (responseFailed) {
window.console && console.log( "Error downloading file: " + responseFailed.error.message);
}
);

Getting notified when the user clicks a link in an embedded PDF

I got a PDF embedded in my page, and I'd like to set something like a Javascript-callback to be called whenever the user clicks a link within the PDF.
Is there a way to accomplish this?
If you check out the Acrobat JS Reference for the minimum version you want to support, you'll see documentation on the HostContainer object.
In the PDF:
this.hostContainer.messageHandler =
{
onMessage: function(messageArray)
{
for(var i = 0; i < messageArray.length; i++)
console.println("Message " + i + ": " + messageArray[i]);
},
onError: function(error, messageArray){ },
onDisclose: function() {return true;}
};
In your HTML, assuming your PDF is inside an <object id="thePdf"> tag:
function messageFunc(messageArray) {
for(var i = 0; i < messageArray.length; i++)
alert("Message " + i + ": " + messageArray[i]);
}
document.getElementById("thePdf").messageHandler = { onMessage: messageFunc };
In your PDF, you'd also need to modify the links so they have a JS action that would post a message to the containing web page. This could be done programmatically (varying wildly depending on the language/library you use), or manually in Acrobat Pro.
this.hostContainer.postMessage(["urlClicked", "http://blah.blah.blah..."]);
Not terribly hard, but no one's ever heard of it. I'd be stunned if this worked anywhere outside an Adobe viewer (Reader/Acrobat) for the next several years.
If you want to send a message from your HTML to the PDF for some reason, it goes something like this:
var thePDF = document.getElementById("thePdf");
thePDF.postMessage(["This", "is", "an", "array", "too."]);
You could even yank out all the existing links and have the PDF request the links be opened by the wrapping HTML page... that way you can give the new windows names, close them from JS, etc. You can get down right snazzy.
But you have to be able to change the PDFs.
Your link is probably represented as a "Link annotation" inside your PDF file. Annotations in PDF can contain "Additional Actions", you could use a pdf processing software like iText (free for non commercial use) or Amyuni PDF Creator(commercial, usual disclaimer applis) to add a Javascript action to the "Additional Actions" collection of your link(s). You can invoke a page or method in your server using this Javascript code.
Client side:
PDF
$("#pdf-link").click(function(){
$.post('yoursite.com/phpfunctionpage/notifyPdf',
{event:'pdf'},
function(response){
alert(response['message']);
}, 'json'
);
});
Your server side:
function notifyPdf(){
$event = $_POST['event'];
if ($event == 'pdf'){
// handle notification here
echo json_encode(array('result'=>1, 'message'=>'notifiation successful'));
}
}
<a href="file.pdf" onclick:'javascriptFunction();'>Open the pdf file</a>
<script>
function javascriptFunction(){
}
</script>

Categories

Resources