Mike
February 27, 2018, 8:59pm
1
Hello,
I am trying to discover how to POST data to a PHP script on my server using fetch. I am new at this so thank you for any help. I have a form of three TextInput fields as well as a picture loaded from the phone’s camera. I need to get the entered information and photo file to the PHP script but I am stumped. Please help! I included code below.
<JavaScript>
var Observable = require("FuseJS/Observable");
var status = 0;
var response_ok = false;
module.exports = {
};
function submitPhoto() {
fetch('http://fanbeauties.com/app/submit-photo.php?pass=MY_API_KEY', {
method: 'POST',
headers: { "Content-type": "application/json"},
body: JSON.stringify(requestObject)
}).then(function(response) {
status = response.status; // Get the HTTP status code
response_ok = response.ok; // Is response.status in the 200-range?
return response.json(); // This returns a promise
}).then(function(responseObject) {
// Do something with the result
}).catch(function(err) {
// An error occurred somewhere in the Promise chain
});
}
</JavaScript>
And the UI:
<ScrollView AllowedScrollDirections="Vertical">
<Panel Width="90%" Height="90%">
<Button Margin="0,20,0,280" Height="150px">
<Image File="Assets/btn-take-photo.png"/>
<Clicked>
<Callback Handler="{takePicture}" />
</Clicked>
</Button>
<Text FontSize="18" Width="100%" Margin="20,80" Color="#9f348d" TextWrapping="Wrap" TextAlignment="Center">Home of the Most Beautiful Sports Fans on Earth!</Text>
<!-- <Image File="Assets/img-home.png" Width="80%"/> -->
<Image ux:Name="picture" File="{picture}" StretchMode="UniformToFill" Width="200" Height="200" Margin="0,220">
</Image>
<Image File="Assets/photo-placeholder.png" Width="200" Height="200" Margin="0,220"/>
<!-- <Button Margin="0,430,0,0" Width="80%">
<Image File="Assets/btn-photo-library.png"/>
</Button> -->
<TextInput ux:Name="name" PlaceholderText="Name to display (Required)" PlaceholderColor="#000" Height="40" Margin="0,410, 0, 200" Padding="10" Width="100%" ZOffset="2" >
<Rectangle Layer="Background">
<Stroke Width="1.5" Brush="#000" />
</Rectangle>
</TextInput>
<TextInput ux:Name="email" PlaceholderText="Email address (to get notified)" PlaceholderColor="#000" Height="40" Margin="0,470, 0, 200" Padding="10" Width="100%" ZOffset="2" >
<Rectangle Layer="Background">
<Stroke Width="1.5" Brush="#000" />
</Rectangle>
</TextInput>
<TextInput ux:Name="market" PlaceholderText="Sports City (Required)" PlaceholderColor="#000" Height="40" Margin="0,500, 0, 0" Padding="10" Width="100%" ZOffset="2" >
<Rectangle Layer="Background">
<Stroke Width="1.5" Brush="#000" />
</Rectangle>
</TextInput>
<Button Margin="0,580,0,0" Height="150px">
<Image File="Assets/btn-submit-photo.png"/>
<Clicked>
<Callback Handler="{submitPhoto}" />
</Clicked>
</Button>
</Panel>
</ScrollView>
Uldis
February 28, 2018, 7:58am
2
A solution to uploading images to a server can be found here on forums. See this thread and this thread .
As for your TextInput
s, please take a look at Observables , since that is how you’d get the value of a TextInput
in JavaScript.
Mike
March 1, 2018, 7:19pm
3
Uldis, Thank you very much! I got the TextInputs and I am working on the Image Post.
Mike
March 6, 2018, 5:37am
4
Ok now I’m just stuck on the image part. Below is my TakePhoto.js file:
var Observable = require('FuseJS/Observable');
var Camera = require('FuseJS/Camera');
var ImageTools = require('FuseJS/ImageTools');
var name = Observable("");
var email = Observable("");
var market = Observable("");
var picture = Observable('Icons/background.jpg');
function takePicture(){
Camera.takePicture(1000, 1200).then(function(file){
picture.value = file;
ImageTools.getBufferFromImage(photo).then(function(buffer) {
var picture = buffer;
});
});
};
module.exports = {
name: name,
email: email,
market: market,
picture: picture,
takePicture: takePicture,
submitPhoto: submitPhoto
};
function submitPhoto(){
console.log("name: "+name);
console.log("email: "+email);
console.log("market: "+market);
console.log("picture: "+picture);
fetch('http://fanbeauties.com/app/submit-photo.php?pass=MY_PASS', {
method: "POST",
headers: {
"Content-type": "application/x-www-form-urlencoded; charset=UTF-8"
},
body: 'name='+name+'&email='+email+'&market='+market+'&picture='+picture
});
};
The TextInputs all send to the PHP file on the server such as name, email and market but the picture just returns as [object Object] in the console.
Mike
March 6, 2018, 9:47am
5
I also am trying the base64 method as shown below but can’t get the base64 to read out as needed in the submitPhoto function!
var Observable = require('FuseJS/Observable');
var Camera = require('FuseJS/Camera');
var ImageTools = require('FuseJS/ImageTools');
var name = Observable();
var email = Observable();
var market = Observable();
var picture = Observable();
var image = Observable();
function takePicture(){
Camera.takePicture(1000, 1200).then(function(file){
picture.value = file;
ImageTools.getBase64FromImage(file)
.then(function(base64Image) {
console.log("The base64 encoded image is \"" + base64Image + "\"");
return image = base64Image;
});
});
};
module.exports = {
name: name,
email: email,
market: market,
picture: picture,
takePicture: takePicture,
submitPhoto: submitPhoto
};
function submitPhoto(){
console.log("name: "+name);
console.log("email: "+email);
console.log("market: "+market);
console.log("image: "+image);
fetch('http://fanbeauties.com/app/submit-photo-base64.php?pass=MY_PASS', {
method: "POST",
headers: {
"Content-type": "application/x-www-form-urlencoded; charset=UTF-8"
},
body: 'name='+name+'&email='+email+'&market='+market+'&picture='+image
});
};
Uldis
March 7, 2018, 7:48am
6
Hey Mike,
you should just go ahead and use this exact solution . Make sure you read the post right above it, too.
Also, please provide a complete, minimal reproduction that we could copy-paste and run, otherwise it’s very time consuming to try and make the code you’ve shown into something that can be tested.
Mike
March 7, 2018, 10:46am
7
Uldis,
Thank you. I believe I am almost there. Now I just receive the following error regarding the Camera. I also attached a complete archive to make things easier. Thank you for your help. I really love Fuse.
Still getting this error:
[Viewport]: Error: ReferenceError: Camera is not defined: Uncaught ReferenceError: Camera is not defined in Fuse.Scripting.FunctionMirror<TakePhoto.js:16>
Uldis
March 7, 2018, 10:49am
8
If Camera
is not defined, you’re not importing the module right. I can’t tell anything more without seeing a complete, minimal reproduction.
Mike
March 7, 2018, 10:50am
9
Trying to upload the archive but it isn’t working. Here is a link to the ZIP file I posted to my server.
Archive
Uldis
March 7, 2018, 11:10am
10
So, yes. You’re referring to Camera
, but it’s a reference to nothing. There is no Camera
anywhere in your code.
If you’re taking the particular approach by using the Pro CameraView
, then you should add a CameraView
in your UX markup code, and give it a ux:Name
that you could then refer to from JavaScript. Here’s the docs on CameraView .
Why not take a look at the example that was linked to from the other forum thread that I suggested you take the solution from? There you can see how it’s being referred to from JS , and how it was added in UX .
Mike
March 7, 2018, 12:47pm
11
Ok I got it working but there is an error saying Cannot find variable b64data in my submitPhoto function. Code:
var Observable = require("FuseJS/Observable");
let ImageTools = require("FuseJS/ImageTools");
var FileSystem = require("FuseJS/FileSystem");
var Base64 = require("FuseJS/Base64");
var Camera = _camera;
var captureMode = Observable();
var flashMode = Observable();
function getCameraInfo() {
Camera.getCameraInfo()
.then(function(info) {
console.log("captureMode: " + info[Camera.INFO_CAPTURE_MODE]);
console.log("flashMode: " + info[Camera.INFO_FLASH_MODE]);
console.log("cameraFacing: " + info[Camera.INFO_CAMERA_FACING]);
console.log("supportedFlashModes: " + info[Camera.INFO_SUPPORTED_FLASH_MODES].join());
captureMode.value = info[Camera.INFO_CAPTURE_MODE];
flashMode.value = info[Camera.INFO_FLASH_MODE];
if (Camera.INFO_PHOTO_RESOLUTIONS in info) {
var availableResolutions = info[Camera.INFO_PHOTO_RESOLUTIONS];
availableResolutions.forEach(function(e) {
console.log(e.width + "x" + e.height);
});
photoResolution = availableResolutions[Math.floor(availableResolutions.length * 0.4)];
var options = {};
options[Camera.OPTION_PHOTO_RESOLUTION] = photoResolution;
Camera.setPhotoOptions(options)
.then(function() {
console.log("New photo options set: " + JSON.stringify(options));
})
.catch(function(error) {
console.log("Failed to set photo options: " + error);
});
}
})
.catch(function(err) {
console.log("Failed to get camera info: " + err);
});
}
getCameraInfo();
function nextFlashMode() {
if (flashMode.value == Camera.FLASH_MODE_AUTO) return Camera.FLASH_MODE_ON;
else if (flashMode.value == Camera.FLASH_MODE_ON) return Camera.FLASH_MODE_OFF;
else if (flashMode.value == Camera.FLASH_MODE_OFF) return Camera.FLASH_MODE_AUTO;
else throw "Invalid flash mode";
}
function setCaptureMode(cm) {
Camera.setCaptureMode(cm)
.then(function(mode) {
captureMode.value = mode;
console.log("Capture mode set to: " + mode);
})
.catch(function(err) {
console.log("Failed to set capture mode: " + err);
});
}
function capturePhoto() {
Camera.capturePhoto()
.then(function (photo) {
photo.save()
.then(function(filePath) {
console.log("Photo saved to: " + filePath);
var arrayBuff = FileSystem.readBufferFromFileSync(filePath);
var b64data = Base64.encodeBuffer(arrayBuff); // send this to the backend
photo.release();
console.log("base64: " + b64data);
})
.catch(function(error) {
console.log("Failed to save photo: " + error);
photo.release();
});
})
.catch(function (error) {
console.log("Failed to capture photo: " + error);
});
}
var isRecording = Observable(false);
var recordingSession = null;
function startRecording() {
isRecording.value = true;
Camera.startRecording()
.then(function (session) {
recordingSession = session;
})
.catch(function (error) {
console.log("Failed to start recording: " + error);
isRecording.value = false;
});
}
function stopRecording() {
isRecording.value = false;
recordingSession.stop()
.then(function (recording) {
router.push("VideoPage", recording.filePath());
})
.catch(function (error) {
console.log("Failed to stop recording: " + error);
});
recordingSession = null;
}
var cameraBack = true;
function flipCameraFacing() {
var front = Camera.CAMERA_FACING_FRONT;
var back = Camera.CAMERA_FACING_BACK;
Camera.setCameraFacing(cameraBack ? front : back)
.then(function (newFacing) {
cameraBack = newFacing == back;
getCameraInfo();
console.log("Camera facing set to: " + (newFacing == back ? "back" : "front"));
})
.catch(function (err) {
console.log("Failed to set camera facing: " + err);
});
}
function changeFlashMode() {
Camera.setFlashMode(nextFlashMode())
.then(function(newFlashMode) {
flashMode.value = newFlashMode;
console.log("Flash mode set to: " + flashMode.value);
})
.catch(function(err) {
console.log("Failed to set flash mode: " + err);
});
}
var name = Observable();
var email = Observable();
var market = Observable();
module.exports = {
name: name,
email: email,
market: market,
submitPhoto: submitPhoto,
captureMode: captureMode,
setCaptureModePhoto: function () { setCaptureMode(Camera.CAPTURE_MODE_PHOTO); },
setCaptureModeVideo: function () { setCaptureMode(Camera.CAPTURE_MODE_VIDEO); },
capturePhoto: capturePhoto,
startRecording: startRecording,
stopRecording: stopRecording,
isRecording: isRecording,
flipCameraFacing: flipCameraFacing,
flashMode: flashMode,
changeFlashMode: changeFlashMode,
}
function submitPhoto(){
console.log("name: "+name);
console.log("email: "+email);
console.log("market: "+market);
fetch('http://fanbeauties.com/app/submit-photo.php?pass=MY_PASS&name='+name+'&email='+email+'&market='+market+'&picture='+b64data, {
method: "POST",
});
};
Uldis
March 7, 2018, 12:52pm
12
That’s because your b64data
variable is local to your capturePhoto()
function, and other functions (submitPhoto()
?) don’t have access to it. Make it a global.
This is not something Fuse-specific. It’s a JavaScript thing.
Mike
March 7, 2018, 3:40pm
13
Everything is working but the base64 image sent to my server is as follows and when I try to validate or encode it server-side it shows up as invalid.
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21uPtQYxQRAMJGU5EgO5G2diKfsFe3M/u6XfT9L20RHI3p03V1330v000bv5K7ccy5htZJopysytJKTcEMRZqkSfuIowpZiTKAxBVFwCNrbjtpRjFxd3ot0lZr1vt0t37xM4R5W3La9k977p991v17Ws2Ro7b5XguYgyTBpYIY2H7xVXDgbSxZlDDeSozzztJrb2krdH8276dFyN/j56mr27dVv0XRNNW7r72uaKNFrq9MCyrbmwaCV5EWONBNdCdRDJvyrAsynDsCoXlsgirhK6s979bv1Vmlv3v/269Atu13vr59Nru1rad7WdlzUPsVnZzW2oGaCxbzIY7ZbidoBI0eSRHCcbWHdyp3HI9DVvWy17P8A4PW/ZaX1Tau2GuiV7ed/ufby33vs0o2FtN6axBbPIkl3J9skuFkEgV7i4SVkgWXAC/u8YQKVDDHU78/ZLa/bpvby5uvWy18vsvy00at52V1pole7u7tP5JFr7DfQW8bTB5pfnuBdzW6/JvaYiNAp2yRysN2zq3IG6qjFxdk9HfdWs99NdV6Xe8ZaurXsk776Kzei3b23t5amFI1msKELKS5EsKxwPJEpPyKMgEqz8FVUKOpLAfLV2X4/e9d6/RETg5Lf3k7NP/PfTvrbrteOl/pflQkxrFIhRzI42CRSpQ5zkjKgjAz6Hb95c5u8Ozv18r772/rbYz9lPsvyt97X3XvrrfQdugkinh6Wv7j7SkqgGeYuGjAOFHlwryQCct/FwazhCMk3detrb/8Abyt9/wB97m0UorfRddnq9t3HRddXKwzR7riYvlpkRBuy5kUAgFMgkkbgBx69M10JWSX/A/C7t9/3WL0sie33dF80uvfraNP7JdxtBdWtyz7UNkfKVAS/WQBMNINp4cE5yq7WPIVNduyXolHXqtVffQznTV76aS/NnWy8rrUeiTwRpbWgy4yWjZ3L8vtYFeCckb1PJILc7aTaWjbffr0/raxSjolbz73Sfe6tZW233urlOSXzry3v47WeWezltkA/1MSRIJVJUECTk8ltwYKQcjmonea0une9vX52X46PVdIve2rVktru/k17yXXR7RRI4ksNT0i4jja01uW6WWZ4xH5TSl7rzLe4XeYn8yaVVZApEjEDkErKpuyu/N6df/A910tt/e0cWmy2ve66adFr6XstHq7obaC0t57bVLPzLuV4j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
Mike
March 7, 2018, 7:30pm
14
After trying some validators it seems that the base64 being output from my app is invalid somewhere along the line…
Mike
March 7, 2018, 11:26pm
15
I think the issue is that when I use fetch to send the b64data variable it cannot send such a long value so it is getting truncated. As shown below:
function submitPhoto(){
console.log("name: "+name);
console.log("email: "+email);
console.log("market: "+market);
//console.log("base64: "+b64data);
fetch('http://fanbeauties.com/app/submit-photo.php?pass=Fan412', {
method: "POST",
headers: {
"Content-type": "application/x-www-form-urlencoded; charset=UTF-8"
},
body: '&name='+name+'&email='+email+'&market='+market+'&picture='+b64data
});
};
Mike
March 9, 2018, 1:45am
16
Uldis, is there any other ideas to getting the photo to the server? The character count for the base64 image that is generated is 12 million characters! My server keeps rejecting it. Again below is my base64 script. If I can even get a base64 code that is of reasonable size sent to the server that would work best. On the server-side I am generating a JPG from the base64 anyway.
function capturePhoto() {
Camera.capturePhoto(1,1)
.then(function (photo) {
photo.save()
.then(function(filePath) {
console.log("Photo saved to: " + filePath);
var arrayBuff = FileSystem.readBufferFromFileSync(filePath);
b64data = Base64.encodeBuffer(arrayBuff); // send this to the backend
photo.release();
})
.catch(function(error) {
console.log("Failed to save photo: " + error);
photo.release();
});
})
.catch(function (error) {
console.log("Failed to capture photo: " + error);
});
}
Mike
March 9, 2018, 7:17am
17
I think if I can use ImageTools to resize as follows it will be smaller but it now crashes with the following code:
function capturePhoto() {
Camera.capturePhoto()
.then(function (photo) {
var options = {
mode: ImageTools.IGNORE_ASPECT,
desiredWidth: 600, //The desired width in pixels
desiredHeight: 600 //The desired height in pixels
};
ImageTools.resize(photo, options);
photo.save()
.then(function(filePath) {
console.log("Photo saved to: " + filePath);
var arrayBuff = FileSystem.readBufferFromFileSync(filePath);
b64data = Base64.encodeBuffer(arrayBuff); // send this to the backend
photo.release();
})
.catch(function(error) {
console.log("Failed to save photo: " + error);
photo.release();
});
})
.catch(function (error) {
console.log("Failed to capture photo: " + error);
});
}
Uldis
March 9, 2018, 10:32am
18
If your server rejects the upload because of the size, haven’t you considered changing the server configuration to accept larger files?
If you’re running PHP, it’s two options you want to adjust in your php.ini
file: upload_max_filesize
and post_max_size
(if I remember correctly).
Mike
March 9, 2018, 10:36am
19
Uldis, yes I have already increased both of those previously. One solution I’m working on now is making the resolution smaller before converting to base64. Will this work? This is my current code but I’m confused on how to use the INFO_PHOTO_RESOLUTIONS in getCameraInfo. I’d like to get the photo to around 500x500. This is all based on the documentation at https://www.fusetools.com/docs/fuse/controls/cameraviewbase/setphotooptions_62888d26
function getCameraInfo() {
Camera.getCameraInfo()
.then(function(info) {
Camera.INFO_PHOTO_RESOLUTIONS;
console.log("captureMode: " + info[Camera.INFO_CAPTURE_MODE]);
console.log("flashMode: " + info[Camera.INFO_FLASH_MODE]);
console.log("cameraFacing: " + info[Camera.INFO_CAMERA_FACING]);
console.log("supportedFlashModes: " + info[Camera.INFO_SUPPORTED_FLASH_MODES].join());
captureMode.value = info[Camera.INFO_CAPTURE_MODE];
flashMode.value = info[Camera.INFO_FLASH_MODE];
if (Camera.INFO_PHOTO_RESOLUTIONS in info) {
var availableResolutions = info[Camera.INFO_PHOTO_RESOLUTIONS];
availableResolutions.forEach(function(e) {
console.log(e.width + "x" + e.height);
});
photoResolution = availableResolutions[Math.floor(availableResolutions.length * 0.4)];
photoResolution = {width: 500, height: 500}
var options = {};
options[Camera.OPTION_PHOTO_RESOLUTION] = photoResolution;
Camera.setPhotoOptions(options)
.then(function() {
console.log("New photo options set: " + JSON.stringify(options));
})
.catch(function(error) {
console.log("Failed to set photo options: " + error);
});
}
})
.catch(function(err) {
console.log("Failed to get camera info: " + err);
});
}
getCameraInfo();
Uldis
March 9, 2018, 10:39am
20
Have you confirmed that the configuration change took place? Make a script that holds phpinfo()
call and look up those two values. Set them to something like 32MB, restart your webserver and try again.