How to reset/clear file Input - file

I am stuck with this problem from resetting an image file from input type=file. This is the scenario,
I set an image and then I clicked the 'Cancel' button (which means it was reset), and then I will set again the same image, it will not set. I do not know why but I think it is a bug.
Here is my code for resetting the image/form.
resetImage() {
this.$refs.addImageForm.reset()
this.dialog = ''
this.imgSrc = ''
this.fileName = ''
this.imgUrl = ''
this.file = ''
}
I am using Vue.js and Vuetify if that helps. I hope you can help me. I am stuck with this problem
HERE IS THE HTML
<template>
<v-dialog
persistent
v-model="dialog"
width="600"
>
<template v-slot:activator="{ on }">
<v-btn depressed color="primary" v-on="on">
<v-icon class="pr-2">check</v-icon>Approve
</v-btn>
</template>
<v-card>
<div class="px-4 pt-3">
<span class="subheading font-weight-bold">Approve Details</span>
<input
ref="image"
type="file"
name="image"
accept="image/*"
style="display: none;"
#change="setImage"
/>
<v-layout row wrap align-center>
<v-flex xs12 class="pa-0">
<div class="text-xs-center">
<v-img :src="imgUrl" contain/>
</div>
<VueCropper
:dragMode="'none'"
:viewMode="1"
:autoCrop="false"
:zoomOnWheel="false"
:background="false"
:src="imgSrc"
v-show="false"
ref="cropper"
/>
<v-form ref="addImageForm" lazy-validation>
<v-layout row wrap class="pt-2">
<v-flex xs12>
<v-text-field
outline
readonly
:label="imgSrc ? 'Click here to change the image' : 'Click here to upload image'"
append-icon='attach_file'
:rules="imageRule"
v-model='fileName'
#click='launchFilePicker'
></v-text-field>
</v-flex>
</v-layout>
</v-form>
</v-flex>
</v-layout>
</div>
<v-divider></v-divider>
<v-card-actions class="px-4">
<v-btn
large
flat
#click="resetImage()"
>Cancel</v-btn>
<v-spacer></v-spacer>
<v-btn
large
depressed
color="primary"
#click="approveCashout"
:loading="isUploading"
>Approve</v-btn>
</v-card-actions>
</v-card>
</v-dialog>
</template>

You can use ref to reset the file uploader value.
this.$refs.fileupload.value = null;
codepen - https://codepen.io/Pratik__007/pen/MWYVjqP?editors=1010

To reset the input, I let vue rerender it. Just add a key to the input and change the value of the key whenever you want the file input to be cleared.
Like so:
window.app = new Vue({
el: '#app',
data: {
fileInputKey: 0
},
methods:{
inputChange() {
console.log('files chosen');
},
clear() {
this.fileInputKey++;
}
}
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.5.17/vue.js"></script>
<div id="app">
<input type="file" #change="inputChange($event)" :key="fileInputKey"/>
<button #click="clear">Clear</button>
</div>

I tried several suggestions I found on Stackoverflow, but in my project there were several errors.
What solved my problem was:
<input type="file" ref="inputFile"/>
this.$refs.inputFile.reset();
This code above resets the field values.

I also came to this problem and could not reset the value. after going through the code of all previous projects and modifying them I got a lot of methods through which a file input could be reset.
one of the way is do is to capture the event object if you want to perform it after handling some code. another way is to change the type of the input element and change it back again.
<div id="app">
<input type="file" #change="onFilePicked" ref="file">
<button #click="clear()">Cancel</button>
</div>
var v = new Vue({
el:'#app',
data:{},
methods:{
clear() {
this.$refs.file.type='text';
this.$refs.file.type='file';
},
onFilePicked(event){
//if you directly want to clear the file input after handling
//some code........
event.target.value=null;
//OR
event.target.value='';
}
},
});

For Composition api
<input type="file"
class="custom-file-input"
id="customFileLang"
lang="en"
accept="image/*"
:class="{ 'is-invalid': errors && errors.images }"
#change="previewImg" multiple
>
Inside setup function:
const imgInput = ref(null) // for input type file
const previewImg = (event) => {
imgInput.value = event
// rest of code to preview img
}
const uploadImage = () => {
//on success
imgInput.value.target.value = null //reset input type file
}

I try mutilpe ways on vue, the best way is:
define this method:
removePic(inp) {
if (this.$refs[inp].files.length === 0) return
this.$refs[inp].files = []
delete this.body[inp]
this.$refs[`${inp}_preview`].src = ''
},
in the template use as this:
<b-form-file
ref="pic"
name="pic"
accept="image/jpeg, image/png, image/gif"
/>
<feather-icon
icon="XIcon"
size="18"
class="text-primary stroke-current"
#click="removePic('pic')"
/>
<div>
<img ref="pic_preview" src="#" alt="select" />
</div>

Related

Add and remove clicked html elements from array in vue

Here’s my code
<form>
<div v-for="(inputAvion, index) in inputsAvion" :key="inputAvion.id" :id="`avion-${index}`">
<input placeholder="origin" name="data" />
<input placeholder="destination" />
<div class="ui button small green" #click="addAvion">+</div>
<div
class="ui button small red"
#click="removeAvion(inputAvion)"
v-show="inputsAvion.length > 1"
>
-
</div>
{{ index }}
</div>
</form>
And the script part :
<script>
export default {
mounted() {
this.inputsAvion.push(this.inputsAvion.length + 1);
//this.inputsAvion.push(this.inputsAvion);
},
data() {
return {
inputsAvion: [],
};
},
methods: {
addAvion() {
this.inputsAvion.push(this.inputsAvion.length + 1);
},
removeAvion(index) {
this.inputsAvion.splice(index, 1);
console.log(this.inputsAvion)
console.log(index)
}
},
};
I would like to add the div element each time the button “+” is clicked and assign a unique id to the div (I willl then add autocomplete google map places to calculate distance between 2 locations)
I think I did it correctly … hope so ^^
But I’d like to use also a remove button to delete the selected line. I’ve tried a lot of things but only managed to remove the last “div” added not the one I clicked.
If someone could help me I’d be grateful a lot ! :)
Thanks
You should pass the index instead of inputAvion
#click="removeAvion(index)"
then
removeAvion(index) {
this.inputsAvion.splice(index, 1);
...

Angular NG-Model not setting

I am trying to set the NG-Model on an input box (within a form if that matters) but it doesn't seem like it ever gets set on $scope. Everytime I set a breakpoint on the if statement in the controller 'lpScan' is always blank. I've tried to display the {{lpScan}} on screen and it also never seems like it sets there. Anybody have any ideas on why that might be?
Here is the small piece of controller code:
$scope.submitLP = function () {
$scope.lpScan = "";
if (!$scope.checkInForm.$valid) {
$scope.formValidate = 1;
return;
}
if ($scope.scanRequired && $scope.lpScan !== $scope.lp.LPNumber) {
FoundationApi.publish('load-notification',
{
title: 'Invalid LP',
content: 'Must scan current LP to receive it.',
autoclose: '4000'
});
}
and here is the html
<div class="full-block">
<form name="checkInForm">
<div class="center data-item">
<div class="button" ng-click="reprintLP()">Reprint LP</div>
</div>
<div class="data-item" ng-if="scanRequired && !lp.CheckedIn"
</div>
<div class="data-label-narrow">Scan LP:</div>
<div class="data-wide"><input id="assignLP" autocomplete="off" type="tel"
ng-keypress="processKeystroke(event)"
ng-model="lpScan" placeholder="Scan LP" name="LPNumber"
required ng-pattern="/^\d+$/" ng-minlength="20" ng-maxlength="20"
ng-trim="true"/>
<div class="data-error"
ng-if="(checkInForm.LPNumber.$dirty || formValidate === 1) && checkInForm.LPNumber.$invalid">
LPNumber must be 20 digits
</div>
</div>
</div>
</form>
First of all you have a broken div in your example code HTML.
<div class="data-item" ng-if="scanRequired && !lp.CheckedIn"
Try adding ng-change on your input something like ng-change="watchInput()" then in your controller add
$scope.watchInput = function() {
console.log($scope.lpScan);
}
Check your console log and see if you are getting a logging at all. If it is then just place your actionable code inside that function.
Looks like you are resetting your $scope.lpScan variable to blank everytime your submitLP function is fired, so declare it outside your submit function:
$scope.lpScan = "";
$scope.submitLP = function () {...
Here is an example:
https://plnkr.co/edit/jcLsGoVFCXkmv1SnUdHl?p=preview

Firebase makes me stop typing after one keystroke in my AngularFire/AngularJS project

I started using Firebase (AngularFire) for synchronizing my data for my application. It's a Card tool for Scrum that adds cards to an array. You can manipulate the input fields.
In the first place I used localStorage, which worked really well. Now that I basically implemented Firebase, I got the following problem: After typing a single key into one field, the application stops and the only way of resuming typing is to click in the input field again.
Do you know why this is? Thank you very much in advance!
That's my basic implementation in my Controller:
Card = (#color, #customer, #points, #number, #projectName, #story) ->
$scope.cards = []
reference = new Firebase("https://MYACCOUNT.firebaseio.com/list")
angularFire(reference, $scope, "cards")
$scope.reset = ->
$scope.cards = []
$scope.addCardRed = (customer) ->
$scope.cards.push new Card("red", customer)
That's my Markup:
<div class="card card-{{ card.color }}">
<header>
<input class="points" contenteditable ng-model="card.points"></input>
<input class="number" placeholder="#" contenteditable ng-model="card.number"></input>
<input class="customerName" contenteditable ng-model="card.customer.name"></input>
<input class="projectName" placeholder="Projekt" contenteditable ng-model="card.projectName"></input>
</header>
<article>
<input class="task" placeholder="Titel" contenteditable ng-model="card.task"></input>
<textarea class="story" placeholder="Story" contenteditable ng-model="card.story"></textarea>
</article>
<footer>
<div class="divisions">
<p class="division"></p>
<button ng-click="deleteCard()" class="delete">X</button>
</div>
</footer>
</div>
<div class="card card-{{ card.color }} backside">
<article>
<h2 class="requirement">Requirements</h2>
<textarea class="requirements" placeholder="Aspects" contenteditable ng-model="card.requirements"></textarea>
</article>
</div>
I ran into this as well. This is because it's recalculating the entire array. Here's how I fixed it:
Bind your input to an ng-model and also add this focus directive
<input class="list-group-item" type="text" ng-model="device.name" ng-change="update(device, $index)" ng-click="update(device, $index)" ng-repeat='device in devices' focus="{{$index == selectedDevice.index}}" />
I set the selectedDevice like this
$scope.update = function(device, index) {
$scope.selectedDevice = device
$scope.selectedDevice.index = index
}
Now create this directive.
angular.module('eio').directive("focus", function() {
return function(scope, element, attrs) {
return attrs.$observe("focus", function(newValue) {
return newValue === "true" && element[0].focus();
});
};
});
Update Sorry for the delay, had a few things to tend to.
The reason why this works is because it is constantly saving the index value of the item in the array you are currently selecting. Once focus is lost, focus is returned immediately by going to that index.
If we're talking about multiple arrays, however, you'll need to refactor the setSelected code to say which array it is.
So you'd want to change
focus="{{$index == selectedDevice.index}}"
to something like
focus="{{$index == selectedDevice.index && selectedDevice.kind == 'points'}}"
Where points is the category of the array where the code appears.
I sorted this one by downloading the most recent version of angularFire.js, seems like bower installed the on that didn't have this fix. now my contentEditable is!

Making a switch statement on my partials angularjs

I'm having a problem, i'm unable to get my ng-switch to work on my partials. What I'm trying to do is upload an image but before I upload it I must first check if the included image size doesn't reach 25kb.
Here is my controller code:
$scope.validateAvatar = function(files) {
var fd = new FormData();
$scope.filesize = files[0].size;
$scope.filemaxsize = 25;
//Take the first selected file
fd.append("file", files[0]);
$scope.uploadAvatar = function() {
Api.uploadAvatar($scope.main.user.email, fd)
.then(function(result) {
console.log(result.data);
}, function(result) {
console.log(result);
})
};
};
and my partials code:
<form data-ng-submit="uploadAvatar()">
<input type="file" name="file" onchange="angular.element(this).scope().validateAvatar(this.files)"/>
<div ng-switch on="filesize / 1024 < filemaxsize">
<div ng-switch-when="true">
<input type="submit" value="Upload Avatar">
</div>
<div ng-switch-default>
Please choose you avatar.
</div>
</div>
</form>
Also do you think my validation is enough when checking for the image file size, say what if the image included is size:20MB, will my validation still catch it? Sorry in the first place I haven't been able to make it work the switch statements first . :(
You need to call $scope.$apply() after you changed $scope.filesize manually.
BTW, why not just let $scope.filemaxsize = 25 * 1024;

angular.js view doesn't update

I am updating an object within a resource.save callback like so:
$scope.addProfile = function () {
User.save( { "id": user_id }, $scope.createdProfile, function( savedUser, getResponseHeaders ) {
//$scope.$apply(function () {
$scope.user = savedUser;
console.debug($scope.user); // I doublechecked that this contains the correct data
//});
});
};
Unfortunately the view isn't updating correctly. As you can see I have already tried to wrap the thing in an apply, which results in an error "Error: $digest already in progress". Therefore i commented that bit out again.
The view bit which doesn't update looks like this:
<h1>{{user.name}}</h1>
{{user.location}}
...
The function addProfile is called from a button inside a form like so:
<form name='profileForm' >
<div class="section">
<label class="title">Name <span class="help">(required)</span>
<textarea ng-model="createdProfile.name" ></textarea>
</label>
</div>
<div class="section">
<button class="btn btn-large highlight" ng-disabled="!profileForm.$valid" ng-click="addProfile()">Save</button>
</div>
</form>
Thanks in advance for any help!
You aren't defining your controller in the html.
<ANY ng-controller="{expression}">
...
</ANY>

Resources