Below is my code. In this by clicking on Add Group, a button is dynamically created and added in fooBar. But when I refresh the page it goes away. I want to create the buttons and save it in the fooBar.
<!DOCTYPE html>
<!--
To change this license header, choose License Headers in Project Properties.
To change this template file, choose Tools | Templates
and open the template in the editor.
-->
<html>
<head>
<title>Content</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<!-- Bootstrap -->
<link href="stylesheets/bootstrap.min.css" rel="stylesheet">
<link href="stylesheets/bootstrap.css" rel="stylesheet">
<link href="stylesheets/bootstrap-theme.min.css" rel="stylesheet">
<link href="stylesheets/bootstrap-theme.css" rel="stylesheet">
<!-- HTML5 Shim and Respond.js IE8 support of HTML5 elements and media queries -->
<!-- WARNING: Respond.js doesn't work if you view the page via file:// -->
<!--[if lt IE 9]>
<script src="https://oss.maxcdn.com/libs/html5shiv/3.7.0/html5shiv.js"></script>
<script src="https://oss.maxcdn.com/libs/respond.js/1.3.0/respond.min.js"></script>
<![endif]-->
<SCRIPT language="javascript">
window.onload = function() {
document.getElementById('btnAdd').onclick = function()
{
myFunction();
};
var person;
var element;
function myFunction()
{
var x;
person = prompt("Please enter Group Name");
if (person != null)
{
add(element);
// x = "Hello " + person + "! How are you today?";
// document.getElementById("demo").innerHTML = x;
}
}
function add(type) {
//Create an input type dynamically.
element = document.createElement("button");
var t = document.createTextNode(person);
element.appendChild(t);
//Assign different attributes to the element.
// element.type = type;
// element.value = type; // Really? You want the default value to be the type string?
// element.name = type; // And the name too?
element.className = "btn btn-default";
span.innerHTML=person;
element.onclick = function() { // Note this is a function
//alert("Do it again!");
$("#btn-group").load("head.html");
};
var foo = document.getElementById("fooBar");
//Append the element in page (in span).
foo.appendChild(element);
// var d = document.getElementById('fooBar');
// d.appendChild(i);
}
};
// function copy()
// {
// var n1 = document.getElementById('addKeyword');
// var n2 = document.getElementById('getKeyword');
// n2.innerText = n1.value;
// }
</SCRIPT>
<script>
$(function(){
$("#btn-group").load("head.html");
});
</script>
</head>
<body>
<div class="btn-group" id="fooBar">
<!-- <button type="button" class="btn btn-default">Marketing</button>
<button type="button" class="btn btn-default">Internet</button>
<button type="button" class="btn btn-default">Politics</button>-->
<button type="button" class="btn btn-default" id="btnAdd">Add Group</button>
</div>
<div class="boxed">
<h4>Group:<span class="label label-default" id="span"></span>
<button type="submit" class="btn btn-default">Edit Name</button>
<button type="submit" class="btn btn-default">Disable</button>
<button type="submit" class="btn btn-default">Delete Group</button></h4>
<div class="row">
<div class="col-lg-6">
<div class="input-group">
<input type="text" class="form-control" placeholder="Enter your keyword" id="addKeyword">
<span class="input-group-btn">
<button class="btn btn-default" type="button" >Add</button>
</span>
</div><!-- /input-group -->
</div><!-- /.col-lg-6 -->
</div>
<h4>Keywords:</h4>
<!-- <div class="keyword" id="getKeyword"></div>-->
</div>
<!-- jQuery (necessary for Bootstrap's JavaScript plugins) -->
<script src="https://code.jquery.com/jquery.js"></script>
<!-- Include all compiled plugins (below), or include individual files as needed -->
<script src="stylesheets/bootstrap.min.js"></script>
<script src="stylesheets/bootstrap.js"></script>
</body>
</html>
Basically, you have two options:
1) Save the information server side: After creating a button, make an AJAX Call to the server, save the configuration there somehow and alter the delivered html accordingly the next time this document is requested
2) Save the button configuration client side: E.g. very simple via localStorage and integrate a check into your page to check the LS for potentially created buttons.
Related
I am new in javascript and currently I am creating an enrolment form where it will validate the cellphone where it only accepts 11 characters and numbers. the only problem is that everytime I click on submit, instead of the message popping up, it completely refreshes my tab. Is there any way to fix this?
Form Code:
<!doctype html>
<html lang="en">
<head>
<nav class="navbar navbar-expand-lg navbar-light">
<a class="navbar-brand" href="Homepage.html"><img src="USTLogo.png" width="30" height="30" alt="">School</a>
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarNav" aria-controls="navbarNav" aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>
<div class="collapse navbar-collapse" id="navbarNav">
<ul class="navbar-nav ml-auto">
<li class="nav-item active">
<a class="nav-link" href="Homepage.html">HOME<span class="sr-only">(current)</span></a>
</li>
</ul>
</div>
</nav>
<title>Enrollment Form</title>
<!-- Required meta tags -->
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
<!-- Bootstrap CSS -->
<link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/css/bootstrap.min.css" integrity="sha384-ggOyR0iXCbMQv3Xipma34MD+dH/1fQ784/j6cY/iJTQUOhcWr7x9JvoRxT2MZw1T" crossorigin="anonymous">
<!-- CSS -->
<link href = "design.css" rel = "stylesheet" type="text/css"/>
<script src="JAVASCRIPT.js" type="text/jsx"></script>
</head>
<body>
<h1 class="display-1">Enrollment Form</h1>
<div class="container">
<div class="row">
<!-- empty space on the left side -->
<div class="col-lg-3"></div>
<!-- Main Content -->
<div class="col-lg-6">
<div id ="ui">
<form id = "form" class="form-group">
<div class="row">
<div class="col-lg-8">
<label >Cellphone Number</label>
<input id = "Cp_Number" type="text" class="form-control" placeholder="Enter Cellphone Number..." required>
</div>
<div class="col-lg-4">
<label >Age</label>
<input id = "Age" type="text" class="form-control" placeholder="Enter your age..." required>
</div>
<br>
<div class="row">
<div class="col-lg-6">
<button type="submit" class="btn btn-primary btn-block">Submit</button>
</div>
<div class="col-lg-6">
Cancel
</div>
</div >
</form>
</div>
</div>
<!-- empty space on the right side -->
<div class="col-lg-3"></div>
</div>
</div>
<script src="https://code.jquery.com/jquery-3.3.1.slim.min.js" integrity="sha384-q8i/X+965DzO0rT7abK41JStQIAqVgRVzpbzo5smXKp4YfRvH+8abtTE1Pi6jizo" crossorigin="anonymous"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.14.7/umd/popper.min.js" integrity="sha384-UO2eT0CpHqdSJQ6hJty5KVphtPhzWj9WO1clHTMGa3JDZwrnQq4sF86dIHNDz0W1" crossorigin="anonymous"></script>
<script src="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/js/bootstrap.min.js" integrity="sha384-JjSmVgyd0p3pXB1rRibZUAYoIIy6OrQ6VrjIEaFf/nJGzIxFDsf4x0xIM+B07jRM" crossorigin="anonymous"></script>
</body>
</html>
Note: I will be removing most of the content in the form and will only include the fields where it needs validation
JS code:
const Cp_num = documet.getElementById('Cp_Number')
const age = document.getElementById('Age')
const form = document.getElementById('form')
form.addEventListener('submit', (e) =>{
var isValid = true;
e.preventDefault();
if(isNaN(Cp_num) || Cp_num.value == null || Cp_num.value == ''){
alert ("Your Cellphone number is invalid!")
isValid == false;
}
if (Cp_num >=12){
alert ("Your Cellphone number is invalid!")
isValid == false;
}
if(isNaN(age) || age.value == null || age.value == ''){
alert ("Your Age is invalid!")
isValid == false;
}
if (isValid == true){
popUp();
}
})
Stop using your custom javascript in the head tag. Because, of this the scripts loads before the contents and doesn't find the form element in the DOM before initialization. So, use any custom javascript inside the body tag and below all the html elements. But remember to include any other dependencies before your custom scripts. Hope it solves the problem.
What's happening here is that your script tag is in your head:
<script src="JAVASCRIPT.js" type="text/jsx"></script>
And for that reason, your HTML hasn't been loaded completely, so a "form" element with the id of "form" does not exist, thus, you get an error (check your console in your browser).
This is why your e.preventDefault() method doesn't work. Because again, your HTML hasn't been loaded yet.
You have two options:
Put the script tag at the bottom of your body:
Very self-explanatory, put the script tag at the end of your body, so your whole HTML loads first, and then your JavaScript file.
Use the "defer" attribute in your script tag:
I won't explain what the defer does in depth here, but if you want some quick answer, it basically waits for your HTML to fully load before using any of the JavaScript code.
So you can try this:
<script src="JAVASCRIPT.js" type="text/jsx" defer></script>
(By the way, this method does not require you to move the script tag out of your HTML head)
You can learn more about defer here: https://developer.mozilla.org/en-US/docs/Web/HTML/Element/script#attr-defer
(EDIT): By further inspection of the code, I found that you were using the "type" parameter in your script tag. You don't need this, and this is causing you the problem of your script tag not being used:
So from:
<script src="JAVASCRIPT.js" type="text/jsx"></script>
do:
<script src="JAVASCRIPT.js" defer></script>
(Another gotcha) You have a typo on the first "document" that you were selecting:
const Cp_num = documet.getElementById('Cp_Number')
"documet" is not defined, you have to change it to:
const Cp_num = document.getElementById('Cp_Number')
I am trying to remove any white space while a user in entering something into the input box. I tried having three separate methods at first: regex to remove spaces when text is pasted, one for when the space bar is pressed, and a simple trim. NOTE: it is required that I use class to call methods. Not sure where to go from here... I appreciate the help!
(function () {
class Digit {
// when user enters keys, do not allow spaces
method2(userInput) {
console.log({userInput});
console.log("formatInput");
const input = userInput.target.value;
console.log(input.length);
if (!input.length) return;
if (userInput.which === 32) { // 32 is space key
console.log("this is a space");
userInput.value = this.method1();
}
}
method1() {
console.log("trimthis input");
return userInput.trim();
}
// when user pastes input remove spaces
method3() {
console.log("formatPaste");
const reg = new RegExp(/\s+/, "");
console.log(this.userInput);
return this.userInput.replace(reg, "");
}
}
const userInput = document.querySelector("#inputNumber");
console.log("User inputs", {userInput});
const digitObject = new Digit();
console.log(digitObject);
userInput.addEventListener("keyup", function() { digitObject.method2(); }, false);
digitObject.method3();
}());
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Numbers App</title>
<!-- Google Fonts -->
<link href="https://fonts.googleapis.com/css?family=Open+Sans|Roboto:400,500" rel="stylesheet">
<!-- CSS -->
<link rel="stylesheet" href="style.css">
</head>
<body>
<!-- ASSIGNMENT: create page where user can type/save numbers only, css grid -->
<div class="wrapper">
<!-- simple form with number input and submit function, auto trim spaces -->
<form>
<div class="form">
<div>
<input class="input--number has-float-label go-bottom Digit" id="inputNumber" placeholder="Enter Number" type="text" required />
<label for="inputNumber">Input</label>
</div>
<div class="btn--group">
<input type="button" value="Post" class="btn post" title="Post">
<input type="button" value="Clear" class="btn clear" title="Clear">
</div>
</div>
</form>
<!-- saved numbers table with date submitted -->
<!---->
</div> <!-- end wrapper -->
<!-- footer -->
<!-- Javascript -->
<script src="script.js"></script>
</body>
</html>
Use the event input to capture every kind of changes and the following regexp / /g
document.getElementById('textfield').addEventListener('input', function() {
this.value = this.value.replace(/ /g, '');
});
<input id='textfield'>
I'm attempting to build a simple address book app using a more OOP approach.
Currently it adds to localStorage without problem; but the next task I wanted to accomplish was a function that displays the Key => value pairs within the HTML. I'm stuck at the first hurdle.
When I call the displayContacts() function on the click event, it is creating another empty object within the LocalStorage. Every time I reload the page and click the 'find' button (and assuming no additional information has been added to the form), a new entry will be added to localStorage such as:
{"first_name":"","last_name":"","email":"","telephone":""}
Thanks in advance
< !-- begin snippet: js hide: false console: true babel: false -->
var addressBook = {
people : JSON.parse(localStorage.getItem('contacts')) || [],
cacheDom : function(){
this.$parent = $('.address_book');
this.$display = $('.find_contacts');
},
bindEvent : function(){
this.$parent.on('submit', this.getFormData.bind(this));
this.$display.on('click', this.displayContacts.bind(this));
},
getStorage : function(param){
return localStorage.getItem();
},
setStorage : function(){
var storage = localStorage.getItem("contacts");
localStorage.setItem("contacts", JSON.stringify(this.people));
},
displayContacts : function(){
var contacts = this.people;
console.log(contacts);
},
getFormData : function(e){
var contacts = {};
var target = e.target.length;
for(var i = 0; i < target; i++){
if(e.target[i].nodeName === "INPUT"){
contacts[e.target[i].name] = e.target[i].value;
/*console.log(contacts);*/
}
}
this.people.push(contacts);
this.setStorage();
return false;
},
render: function(){
},
init : function(){
this.cacheDom();
this.bindEvent();
this.setStorage();
}
}
addressBook.init();
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1">
<!-- The above 3 meta tags *must* come first in the head; any other head content must come *after* these tags -->
<title>Bootstrap 101 Template</title>
<!-- Bootstrap -->
<link href="./bootstrap-3.3.7-dist/css/bootstrap.css" rel="stylesheet">
<link href="./bootstrap-3.3.7-dist/css/custom.css" rel="stylesheet">
<!-- HTML5 shim and Respond.js for IE8 support of HTML5 elements and media queries -->
<!-- WARNING: Respond.js doesn't work if you view the page via file:// -->
<!--[if lt IE 9]>
<script src="https://oss.maxcdn.com/html5shiv/3.7.3/html5shiv.min.js"></script>
<script src="https://oss.maxcdn.com/respond/1.4.2/respond.min.js"></script>
<![endif]-->
</head>
<body>
<div class="row wrapper">
<div class="col-md-4 input_field">
<form class="address_book" method="post">
<div class="form-group">
<label for="exampleInputEmail1">First Name</label>
<input type="text" class="form-control first_name" id="exampleInputEmail1" placeholder="First Name" name="first_name">
</div>
<div class="form-group">
<label for="exampleInputEmail1">Last Name</label>
<input type="text" class="form-control" id="exampleInputEmail1" placeholder="Last Name" name="last_name">
</div>
<div class="form-group">
<label for="exampleInputEmail1">Email address</label>
<input type="email" class="form-control" id="exampleInputEmail1" placeholder="Email" name="email">
</div>
<div class="form-group">
<label for="exampleInputPassword1">Telephone</label>
<input type="number" class="form-control" id="exampleInputPassword1" placeholder="Phone Number" name="telephone">
</div>
<button type="submit" class="btn btn-default submit_to_storage">Submit</button>
<button type="edit" class="btn btn-default submit_to_storage">edit</button>
<button type="delete" class="btn btn-default submit_to_storage">delete</button>
<button type="find" class="btn btn-default find_contacts">find</button>
</form>
</div>
</div>
<div class="row">
<div class="col-sm-push-10 output">
</div>
</div>
<!-- jQuery (necessary for Bootstrap's JavaScript plugins) -->
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.12.4/jquery.min.js"></script>
<!-- Include all compiled plugins (below), or include individual files as needed -->
<script src="./bootstrap-3.3.7-dist/js/bootstrap.js"></script>
<script src="./bootstrap-3.3.7-dist/js/localStorage.class.js"></script>
</body>
</html>
Your button is of type find
<button type="find" class="btn btn-default find_contacts">
This is not a valid type, and instead the button goes back to the default type, which is submit.
A submit button inside a form, submits the form, so not only are you calling the click handler on the button, but the submit handler for the form as well, which inserts into localStorage.
This is why, when you click the button it inserts in to localStorage.
To fix the issue, add a type of button to all the buttons that aren't supposed to submit the form.
<button type="submit" class="btn btn-default submit_to_storage">Submit</button>
<button type="edit" class="btn btn-default submit_to_storage">edit</button>
<button type="delete" class="btn btn-default submit_to_storage">delete</button>
<button type="find" class="btn btn-default find_contacts">find</button>
The only valid types for a button are
submit
reset
button
I have two questions
How to display the initial message and/or upon button click. The current code I have displays the message continuously. I want it to display initially and once users starts pressing other button I want the message "Start guessing" to disappear and only appear after user clicks Start Over button.
How to display the correct answer when user clicks on Give up.
HTML
<!DOCTYPE html>
<html lang="en" data-ng-app="myApp">
<head>
<title>Template that uses Bootstrap</title>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initialscale=1.0"/>
<!-- Bootstrap -->
<link href="css/bootstrap.min.css" rel="stylesheet" />
<!-- Custom CSS -->
<link href="css/custom.css" rel="stylesheet" />
<!-- HTML5 Shim and Respond.js IE8 support of HTML5 elements and media queries -->
<!-- WARNING: Respond.js doesn't work if you view the page via file:// -->
<!--[if lt IE 9]>
<script src="js/html5shiv.js"></script>
<script src="js/respond.min.js"></script>
<![endif]-->
</head>
<body>
<div data-ng-controller="myCtrl">
<div class="container">
<h1>Guessing Game</h1><br>
<label>Enter Guess:</label>
<input type="text" id="guess" name="guess" data-ng-model="guess"/><br>
<span data-ng-bind="Message"></span>
<div class="row">
<div class="col-md-12">
<button class="btn btn-primary btn-md" data-ng-click="checkGuess()">Check</button>
<button class="btn btn-warning btn-md" data-ng-click="showAnswer()">Give Up</button>
<button class="btn btn-info btn-md" data-ng-click="startGame()">Start Over</button>
</div></div>
<div class="row">
<div class="col-xs-7">
<div ng-show="deviation<0" class="alert alert-warning">Guess higher</div>
<div ng-show="deviation>0" class="alert alert-warning">Guess lower</div>
<div ng-show="deviation===0" class="alert alert-success">You got it!</div>
</div></div>
</div>
</div>
<!-- jQuery – required for Bootstrap's JavaScript plugins) -->
<script src="js/jquery.min.js"></script>
<!-- All Bootstrap plug-ins file -->
<script src="js/bootstrap.min.js"></script>
<!-- Basic AngularJS -->
<script src="js/angular.min.js"></script>
<!-- Your Controller -->
<script src="js/app.js"></script>
</body>
</html>
Angular
/*global angular */
var myApp = angular.module("myApp", []);
myApp.controller("myCtrl", function ($scope) {
"use strict";
$scope.checkGuess = function () {
$scope.deviation = $scope.original - $scope.guess;
};
$scope.startGame = function () {
$scope.guess = null;
$scope.original = Math.floor(Math.random() * 1000 + 1);
$scope.deviation = null;
$scope.display = false;
$scope.Message = "Start guessing.";
};
$scope.showAnswer = function () {
$scope.original = Math.floor(Math.random() * 1000 + 1);
$scope.display = true;
};
$scope.startGame();
}
);
1) Use ng-hide to hide your element when needed:
<span data-ng-bind="Message" ng-hide="hideMessage"></span>
In the checkGuess and showAnswer functions set the hideMessage to true:
$scope.hideMessage = true;
In the startGame function, set it to false:
$scope.hideMessage = false;
2) In your HTML add a tag:
<div ng-show="showOriginal">{{previousOriginal}}</div>
And in your showAnser and startGame function, add:
$scope.showOriginal = true;
$scope.previousOriginal = angular.copy($scope.original);
And remove of the showAnswer function:
$scope.original = Math.floor(Math.random() * 1000 + 1)
Finally, in the startGame function, set it to false:
$scope.showOriginal = false;
Hello i'm building an application where i want to dynamically change the source of an image in order to force reload it . The problem is that in order of this i only get a broken image on the browser. Instead , if a run the function manually by a button it runs perfect .
HTML document
<!DOCTYPE html>
<html lang="en" ng-app='cameraApp'>
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>Node JS Camera</title>
<!-- Latest compiled and minified CSS -->
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/css/bootstrap.min.css">
<!-- Optional theme -->
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/css/bootstrap-theme.min.css">
<script src="//code.jquery.com/jquery-1.11.3.min.js"></script>
<!-- Latest compiled and minified JavaScript -->
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/js/bootstrap.min.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.3/angular.min.js"></script>
<script src='https://code.angularjs.org/1.4.4/angular-sanitize.min.js'></script>
<script src="cameraApp.js"></script>
</head>
<body>
<div class="container-fluid">
<div class="jumbotron">
<h1>Welcome to NodeJS Camera v1</h1>
</div>
<div ng-controller="HomeController">
<div class="cameraControl col-md-5">
<p>Here is the camera control</p>
<button class="btn btn-default" ng-click="getSnapshot()">Snapshot</button>
<button class="btn btn-info" ng-click="intervalFunction()">Start Feed</button>
</div>
<div class="lifeFeed col-md-7">
<p>Here is the live feed</p>
<p><button class="btn btn-default" ng-click="readSnapshot()">Snapshot Read</button></p>
<img width='600' height='600' ng-src="{{snapshot}}" alt="SnapShot taken">
</div>
</div>
</div>
</body>
</html>
cameraApp.js
var cameraApp = angular.module('cameraApp',[]);
cameraApp.controller('HomeController', function($scope,$http,$timeout) {
function updateImage() {
var img = 'snapshots/camera.jpg'+ '?decache=' + Math.random();
console.log('Snapshot Loaded');
$scope.snapshot = img;
};
$scope.readSnapshot = updateImage;
$scope.getSnapshot = function() {
$http.get('/api/getSnapshot')
.then(function(response) {
// this callback will be called asynchronously
// when the response is available
console.log('Snapshot captured');
$scope.readSnapshot();
}, function(response) {
console.log('Error in capturing...');
});
}
$scope.intervalFunction = function() {
$timeout(function() {
$scope.getSnapshot();
$scope.intervalFunction();
}, 2000);
};
// Kick off the interval
$scope.intervalFunction();
});
There are two solutions I've used for this in the past.
1) Use an ng-if/ng-show on your img tag. This will prevent the broken image from displaying.
<img ng-if='snapshot'>
2) Set a default image that will load and then be replaced once the other images load.
$scope.snapshot = 'snapshots/default.png';