jQuery上传图片预览与重置默认值

时间:2018-02-02 21:26:49

标签: javascript jquery html upload preview

我正在尝试为用户上传的图片创建上传预览。我已经完成了我想做的大部分工作(感谢stackoverflow ...很多复制粘贴和一些调整)但是由于我不了解JavaScript,我无法让它完全正常工作



function uploadPreview(input) {
  if (input.files && input.files[0]) {
    var reader = new FileReader();

    reader.onload = function(e) {
      if (e.target.result.trim().length == 0) {
        $('#serviceImage').attr('src', 'http://catawbabrewing.com/wp-content/themes/catawba/images/placeholder.png');
      } else {
        $('#serviceImage').attr('src', e.target.result);
      }
    }

    reader.readAsDataURL(input.files[0]);
  }
}

function uploadPreviewExt(input) {
  if (input.trim().length == 0) {
    var previewSrc = '{{CSS_URL}}/images/placeholder.jpg';
  } else {
    var previewSrc = input;
  }

  $('#serviceImage').attr('src', previewSrc);
}

function resetUploadPreview() {
  if (!$('#previousImage').val()) {
    $('#serviceImage').attr('src', 'http://catawbabrewing.com/wp-content/themes/catawba/images/placeholder.png');
  } else {
    $('#serviceImage').attr('src', '{{PROD_IMG}}/'.$('#previousImage').val());
  }
}

$("#mainImage").change(function() {
  uploadPreview(this);
});

$('[name="mainImgExt"]').on('change', function() {
  uploadPreviewExt(this.value);
});

$('#clearUpload').on('click', function() {
  $('#mainImage').val('');

  if ($('#imgExt').val().trim().length == 0) {
    resetUploadPreview();
  } else {
    uploadPreviewExt($('#imgExt').val());
  }
});

$('#clearUploadExt').on('click', function() {
  $('#imgExt').val('');

  if (!$('#mainImage').val()) {
    resetUploadPreview();
  } else {
    uploadPreview($('#mainImage'));
  }
});

pointer {
  cursor: pointer;
}

img.placeholder {
  width: 100px;
  height: 100px;
}

<link rel="stylesheet" href="//maxcdn.bootstrapcdn.com/bootstrap/4.0.0/css/bootstrap.min.css">
<script src="//code.jquery.com/jquery-3.3.1.min.js"></script>
<script src="//unpkg.com/popper.js@1.12.9/dist/umd/popper.min.js"></script>
<script src="//maxcdn.bootstrapcdn.com/bootstrap/4.0.0/js/bootstrap.min.js"></script>

<div class="form-group p-3 border p-2 rounded m-3">
  <div class="row">
    <div class="col-sm-3 text-center pt-2 border-right">
      <label for="mainImage"><img src="http://catawbabrewing.com/wp-content/themes/catawba/images/placeholder.png" alt="Placeholder" id="serviceImage" class="placeholder img-thumbnail" aria-describedby="imagePreviewHelp" /></label>
      <small id="imagePreviewHelp" class="form-text text-muted">Preview could appear stretched</small>
    </div>
    <div class="col">
      <label for="mainImage">Image</label>
      <div class="input-group mb-3">
        <input type="file" class="form-control border p-1" id="mainImage" name="mainImage" />
        <div class="input-group-append">
          <span class="input-group-text bg-warning text-danger pointer" id="clearUpload">X</span>
        </div>
      </div>
      <div class="input-group mb-3">
        <input type="text" class="form-control" id="imgExt" name="mainImgExt" placeholder="Externel Image" aria-describedby="imageHelp" />
        <div class="input-group-append">
          <span class="input-group-text bg-warning text-danger pointer" id="clearUploadExt">X</span>
        </div>
      </div>
      <small id="imageHelp" class="form-text text-muted">Upload a local image <strong>or</strong> link to an external image.</small>
    </div>
  </div>
</div>
&#13;
&#13;
&#13;

View on JSFiddle

涉及到很多JavaScript(因为我根本不知道它,所以我的舒适区域更多)。

JavaScript可能会遇到两种版本的HTML。这取决于用户是添加服务还是编辑服务。表格是在TWIG的帮助下动态生成的。

在JSFiddle中,下面有一个版本的图像上传部分(如果它正在添加服务)是用于编辑服务的版本。 (隐藏的输入字段&#34; previousImage&#34;已添加,预览是当前图像,而不是占位符)

    <div class="form-group p-3 border p-2 rounded">
        <div class="row">
            <div class="col-sm-3 text-center pt-2 border-right">
                <label for="mainImage"><img src="https://logismarketmx.cdnwm.com/ip/eve-maquinaria-mantenimiento-para-gruas-mantenimiento-de-gruas-987423-FGR.jpg" alt="Vinyl" id="serviceImage" class="placeholder img-thumbnail" aria-describedby="imagePreviewHelp" /></label>
                <input type="hidden" name="previousImage" id="previousImage" value="eve-maquinaria-mantenimiento-para-gruas-mantenimiento-de-gruas-987423-FGR.jpg" />
                <small id="imagePreviewHelp" class="form-text text-muted">Preview could appear stretched</small>
            </div>
            <div class="col">
                <label for="mainImage">Image</label>
                <div class="input-group mb-3">
                    <input type="file" class="form-control border p-1" id="mainImage" name="mainImage" />
                    <div class="input-group-append">
                        <span class="input-group-text bg-warning text-danger pointer" id="clearUpload">X</span>
                    </div>
                </div>
                <div class="input-group mb-3">
                    <input type="text" class="form-control" id="imgExt" name="mainImgExt" placeholder="Externel Image" aria-describedby="imageHelp" />
                    <div class="input-group-append">
                        <span class="input-group-text bg-warning text-danger pointer" id="clearUploadExt">X</span>
                    </div>
                </div>
                <small id="imageHelp" class="form-text text-muted">Upload a local image <strong>or</strong> link to an external image.</small>
            </div>
        </div>
    </div>

这是问题的背景故事。这就是我挣扎的。

我希望用户点击红色&#39; X&#39;清除现场直到左边。它会清除该字段,但我还想重置上传预览图像。

表单的第二个版本重要的原因是,如果用户重置并正在添加,则图像将更改为占位符(这是本地上载而不是外部URL);但如果用户正在编辑服务,则上传预览将重置为设置为该服务的上一个图像。

我认为我应该使用javascript,但它没有。

    function resetUploadPreview()
    {
        if(!$('#previousImage').val())
        {
            $('#serviceImage').attr('src', '{{CSS_URL}}/images/placeholder.jpg');
        }
        else
        {
            $('#serviceImage').attr('src', '{{PROD_IMG}}/' . $('#previousImage').val());
        }
    }

背后的逻辑是输入ID&#39; previousImage&#39;是空的(或不存在的)它会显示占位符但是如果它的值是否超过我们使用它的值(文件名)来显示该图像。

但它没有这样做,清除本地文件上传会将图像重置为占位符,无论是否填充了previousImage,外部网址根本不清楚。

我想实现的另一个功能是,如果两个字段都填写(本地和外部),则清除一个将在预览中显示另一个图像。

很抱歉,如果这看起来很简单,那么逻辑对我来说似乎很简单,但我似乎无法让它发挥作用而且我不知道我错过了什么......在我看来,一切都在它应该工作的地方,但它没有。

编辑时,它不会重置为上一张图像......它根本不会重置。控制台给我以下错误

    TypeError: "../design/variant/productImages/".$ is not a function

它导致的代码行是:

    function resetUploadPreview()
    {
        if(!$('#previousImage').val())
        {
            $('#serviceImage').attr('src', '{{CSS_URL}}/images/placeholder.jpg');
        }
        else
        {
            // This is the line that makes that error
            $('#serviceImage').attr('src', '{{PROD_IMG}}/' . $('#previousImage').val());
        }
    }

如果首先添加本地图像然后添加外部图像,则添加新服务时会显示外部图像预览。但是一旦你清除外部图像,它应该显示本地图像(因为它被填写)但它根本不会改变预览。并且控制台没有显示任何警告/错误。

我做错了什么?

1 个答案:

答案 0 :(得分:1)

干得好! 我做了两个调整:

  1. 在JavaScript中,string concatenation使用+符号执行,而不是.符号。 (因此您引用了TypeError消息。)我相应更改了resetUploadPreview()中的代码。

  2. uploadPreview()函数不期望jQuery对象,但是当清除外部图像字段时,传递jQuery对象以恢复主图像。我将其更改为传递DOM元素:$('#mainImage')[0]而不是$('#mainImage')。有关详细信息,请参阅What does $(selector)[0] mean in jQuery?

  3. &#13;
    &#13;
    function uploadPreview(input) {
      if (input.files && input.files[0]) {
        var reader = new FileReader();
    
        reader.onload = function(e) {
          if (e.target.result.trim().length == 0) {
            $('#serviceImage').attr('src', '//catawbabrewing.com/wp-content/themes/catawba/images/placeholder.png');
          } else {
            $('#serviceImage').attr('src', e.target.result);
          }
        }
    
        reader.readAsDataURL(input.files[0]);
      }
    }
    
    function uploadPreviewExt(input) {
      if (input.trim().length == 0) {
        var previewSrc = '{{CSS_URL}}/images/placeholder.jpg';
      } else {
        var previewSrc = input;
      }
    
      $('#serviceImage').attr('src', previewSrc);
    }
    
    function resetUploadPreview() {
      if (!$('#previousImage').val()) {
        $('#serviceImage').attr('src', 'http://catawbabrewing.com/wp-content/themes/catawba/images/placeholder.png');
      } else {
        $('#serviceImage').attr('src', '{{PROD_IMG}}/' + $('#previousImage').val());
      }
    }
    
    $("#mainImage").change(function() {
      uploadPreview(this);
    });
    
    $('[name="mainImgExt"]').on('change', function() {
      uploadPreviewExt(this.value);
    });
    
    $('#clearUpload').on('click', function() {
      $('#mainImage').val('');
    
      if ($('#imgExt').val().trim().length == 0) {
        resetUploadPreview();
      } else {
        uploadPreviewExt($('#imgExt').val());
      }
    });
    
    $('#clearUploadExt').on('click', function() {
      $('#imgExt').val('');
    
      if (!$('#mainImage').val()) {
        resetUploadPreview();
      } else {
        uploadPreview($('#mainImage')[0]);
      }
    });
    &#13;
    pointer {
      cursor: pointer;
    }
    
    img.placeholder {
      width: 100px;
      height: 100px;
    }
    &#13;
    <link rel="stylesheet" href="//maxcdn.bootstrapcdn.com/bootstrap/4.0.0/css/bootstrap.min.css">
    <script src="//code.jquery.com/jquery-3.3.1.min.js"></script>
    <script src="//unpkg.com/popper.js@1.12.9/dist/umd/popper.min.js"></script>
    <script src="//maxcdn.bootstrapcdn.com/bootstrap/4.0.0/js/bootstrap.min.js"></script>
    
    <div class="form-group p-3 border p-2 rounded m-3">
      <div class="row">
        <div class="col-sm-3 text-center pt-2 border-right">
          <label for="mainImage"><img src="http://catawbabrewing.com/wp-content/themes/catawba/images/placeholder.png" alt="Placeholder" id="serviceImage" class="placeholder img-thumbnail" aria-describedby="imagePreviewHelp" /></label>
          <small id="imagePreviewHelp" class="form-text text-muted">Preview could appear stretched</small>
        </div>
        <div class="col">
          <label for="mainImage">Image</label>
          <div class="input-group mb-3">
            <input type="file" class="form-control border p-1" id="mainImage" name="mainImage" />
            <div class="input-group-append">
              <span class="input-group-text bg-warning text-danger pointer" id="clearUpload">X</span>
            </div>
          </div>
          <div class="input-group mb-3">
            <input type="text" class="form-control" id="imgExt" name="mainImgExt" placeholder="Externel Image" aria-describedby="imageHelp" />
            <div class="input-group-append">
              <span class="input-group-text bg-warning text-danger pointer" id="clearUploadExt">X</span>
            </div>
          </div>
          <small id="imageHelp" class="form-text text-muted">Upload a local image <strong>or</strong> link to an external image.</small>
        </div>
      </div>
    </div>
    &#13;
    &#13;
    &#13;