Home>

I am making an app to post images with rails.
Currently, I am trying to create a function to post dropped images via Ajax communication, but it does not work as expected and I am in trouble.
Would you please give me some wisdom if there is any good way?


When I drag and drop an image, I get an error (422).
It seems to indicate that the server can understand the content type of the request body and the syntax of the request body is correct, but the instructions contained therein could not be processed.

Corresponding source code
= form_with model: [@scrap_folder, @scrap], local: true do | f |
  = f.label: image, class:'overlay-area', id:'js-overlay-area' do
    = f.file_field: image, style: "display: none"
    .overlay-text # js-overlay-text
      % p Drag and drop here
$(function () {
  document.addEventListener ("turbolinks: load", function () {
    function buildPost (scrap) {
      return `
              
                
                  
                
              
             ``
    }
    $('# js-overlay-area'). on ('drop', function (e) {
      e.preventDefault ();
      e.stopPropagation ();
      // get file
      let file = e.originalEvent.dataTransfer.files [0];
      let formData = new FormData ();
      formData.append ("file", file);
      let url = $(this) .parent (). attr ('action')
      $.ajax ({{
        url: url,
        type: "POST",
        data: formData,
        dataType:'json',
        cache: false,
        processData: false,
        contentType: false
      })
        .done (function (data) {
          let html = buildPost (data)
          $(". Scrap"). append (html) .animate ({scrollTop: $(". Scrap") [0] .scrollHeight})
        })
        .fail (function () {
          alert ("Failed to send image")
        })
    })
  })
})
What I tried

Check what value is in the variable.

I did binding.pry with create on the controller, but there was no response in the log.
I think I'm probably getting an error when sending a JavaScript file to my controller via Ajax.

  • Answer # 1

    Drag and drop into the area of ​​input type = file
    Activate ajax in the change event

  • Answer # 2

    Share the resolved code.

    = form_with model: [@scrap_folder, @scrap], class: "ScrapForm", local: true do | f |
          = f.label: image, class:'overlay-area', id:'js-overlay-area' do
            = f.file_field: image, style: "display: none"
            .overlay-text # js-overlay-text
              % p Drag and drop here
    .overlay-area {
      width: 100%;
      height: 100%;
      position: absolute;
      top: 50%;
      left: 50%;
      transform: translate (-50%, -50%);
      background: rgba (0, 0, 0, 0.5);
      z-index: 100;
      display: none;
      .overlay-text {
        position: absolute;
        top: 50%;
        left: 50%;
        transform: translate (-50%, -50%);
        background-color: #FFFFFF;
        color: # 16a5bc;
        border-radius: 5px;
        z-index: 10;
        box-shadow: 0 0 12px # d8d8d8;
        pointer-events: none;
        p {
          padding: 20px;
          line-height: 1.5em;
          }
        }
      }
    $(function () {
      document.addEventListener ("turbolinks: load", function () {
        function buildPost (scrap) {
          return `
                  
                    
                      
                    
                  
                 ``
        }
        $('.ScrapForm'). on ('submit', function (e) {
          e.preventDefault ();
          let formData = new FormData (this)
          let url = $(this) .attr ('action')
          $.ajax ({{
            url: url,
            type: "POST",
            data: formData,
            dataType:'json',
            processData: false,
            contentType: false
          })
            .done (function (data) {
              let html = buildPost (data)
              $(". Scrap"). append (html) .animate ({scrollTop: $(". Scrap") [0] .scrollHeight})
              $("form") [0] .reset ()
            })
            .fail (function () {
              alert ("Failed to send image")
            })
        })
      })
    })
    $(function () {
      $(document) .on ('dragenter', function (e) {
        e.stopPropagation ();
        e.preventDefault ();
      });
      $(document) .on ('dragover', function (e) {
        e.stopPropagation ();
        e.preventDefault ();
      });
      $(document) .on ('drop', function (e) {
        e.stopPropagation ();
        e.preventDefault ();
      });
      // When entering the droppable area
      $('# js-dropzone'). on ('dragenter', function (e) {
        e.preventDefault ();
        e.stopPropagation ();
        $('# js-overlay-area'). show ()
      })
      $('# js-overlay-area'). on ('dragleave', function (e) {
        // When you leave the droppable area
        e.preventDefault ();
        e.stopPropagation ();
        $('# js-overlay-area'). hide ()
      }) .on ('dragover', function (e) {
        // When the cursor is in the droppable area
        e.preventDefault ();
        e.stopPropagation ();
      }) .on ('drop', function (e) {
        // When dropped
        e.preventDefault ();
        e.stopPropagation ();
        $('# js-overlay-area'). hide ()
        $(e.target) .find ('[type = "file"]'). get () [0] .files = e.originalEvent.dataTransfer.files;
        $(this) .closest ('form'). Trigger ('submit');
      })
    })

Related articles