0

i am trying to achieve a file upload with JavaScript and pass the uploaded image to a backing bean value to store it. The page is a mobile webpage with Primefaces Mobile.

The following is my jsf-Page:

<f:view xmlns="http://www.w3.org/1999/xhtml"
    xmlns:f="http://java.sun.com/jsf/core"
    xmlns:h="http://java.sun.com/jsf/html"
    xmlns:ui="http://java.sun.com/jsf/facelets"
    xmlns:p="http://primefaces.org/ui"
    xmlns:fn="http://java.sun.com/jsp/jstl/functions"
    xmlns:pm="http://primefaces.org/mobile"
    contentType="text/html"
    renderKitId="PRIMEFACES_MOBILE">

<style type="text/css">
.invisible *{
    display:none;
}
</style>
<pm:page title="" swatch="a">
    <pm:view id="main">
        <pm:content>
            <h:form id="imageForm">
                <p:commandLink immediate="true" value="Select image" onclick="onClickTakeCam();"/>
                <h:panelGroup styleClass="invisible">
                    <input type="file" id="files" name="files[]" multiple="multiple" />
                </h:panelGroup>
                 <input value="#{testBean.imageData}" type="text" id="inputId" />
            </h:form>
            <script>
                function onClickTakeCam() { 
                    $("#files").click();
                }
                function handleFileSelect(evt) {
                    var files = evt.target.files; // FileList object

                    // Loop through the FileList and render image files as thumbnails.
                    for (var i = 0, f; f = files[i]; i++) {

                          // Only process image files.
                          if (!f.type.match('image.*')) {
                            continue;
                          }
                         var reader = new FileReader();
                      // Closure to capture the file information.
                        reader.onload = (function(theFile) {
                            return function(e) {
                              var result = e.target.result;
                              var input = document.getElementById('inputId');
                              input.value = result;
                            };
                          })(f);
                          // Read in the image file as a data URL.
                       reader.readAsDataURL(f);
                    }
                }
                document.getElementById('files').addEventListener('change', handleFileSelect, false);
            </script>
     </pm:content>
    </pm:view>
</pm:page>

The bean looks as following:

@ManagedBean
@SessionScoped
public class TestBean{
    private String imageData;
    public TestBean() { }

    public String getImageData() {
        return imageData;
    }

    public void setImageData(String imageData) {
        this.imageData = imageData;
    }
}

After image selection the input field shows the value, but "setImageData" is never called and so I can't work with the data from here. So how can I get the setter to be called?

Tutorial from HTML5Rocks

Pass variables from client side to server side from BalusC

mabi
  • 5,279
  • 2
  • 43
  • 78

2 Answers2

0

Your problem is caused by JSF not knowing it should do anything. HTML is just what it outputs, it doesn't understand that you want the value of TestBean#imageData to change when you modify the input field.

Try changing your input field to a JSF component:

<h:inputText id="testId" value="#{testBean.imageData}" />

You will need to adjust your Javascript to accommodate the changed id.

mabi
  • 5,279
  • 2
  • 43
  • 78
0

I finally found the mistake. The form submit was missing.

So in the "handleFileSelect"-Method I had to add:

document.getElementById('imageForm').submit();