I am trying to make a blog type of website. I got to a point where you can enter text into a textarea box and then click submit to have it appear below. However, I have come to a problem where it does not save the format of the input (notably for me, transforms paragraphs into spaces). I have read that this would require a rich-text editor, and I have tried TinyMCE but it gives a lot more options than needed or which would be able to be used in my case. Is there a simple way to fix this problem? If not, what is the best way to go about this?
I am mainly after the paragraph, tab, and multiple spaces formatting, everything else is currently not needed.
Here is what I currently have that is related:
HTML
<!-- Blog Section -->
<div class="itemBlog">
<h2 id="itemBlogTitle">My Blog</h2>
<textarea type="text" rows="10" cols="100" class="blogTextArea" id="blogInput"></textarea>
<div onclick="newBlog()" class="addBtn">Add</div>
<ul id="blogList"></ul>
</div>
<script src="itemblog.js"></script>
JavaScript
// Create a new blog item when clicking on the "Add" button
function newBlog() {
var li = document.createElement("li");
var inputValue = document.getElementById("blogInput").value;
var t = document.createTextNode(inputValue);
li.appendChild(t);
if (inputValue != '') {
document.getElementById("blogList").appendChild(li);
}
document.getElementById("blogInput").value = "";
var textarea = document.createElement("TEXTAREA");
var txt = document.createTextNode("\u00D7");
textarea.className = "close";
textarea.appendChild(txt);
li.appendChild(textarea);
for (i = 0; i < close.length; i++) {
close[i].onclick = function () {
var div = this.parentElement;
div.style.display = "none";
}
}
}
EDIT: white-space: pre-wrap; fixed it, thank you
If you want something simple, just save into your database the input content with id description, after that it will respect the paragraph and spaces.
JQUERY
$('#test').keyup(function() {
var text = $(this).val();
var description = text.replace(/ /g, ' ').replace(/[\n]/g, '<br>');
$('#text').html(description)
$('#description').val(description)
});
<textarea id="test" cols="30" rows="10"></textarea>
<input id="description" name="description" hidden>
<div id="text"></div>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
js
function formatString(el) {
var str = el.value;
str = str.replace(/ /g, ' ').replace(/[\n]/g, '<br>');
document.getElementById('text').innerHTML = str;
document.getElementById('description').value = str;
}
<textarea onkeyup="formatString(this)" cols="30" rows="10"></textarea>
<input id="description" name="description" hidden>
<div id="text"></div>
You can create a function nl2br() as folows:
function nl2br (str, is_xhtml) {
if (typeof str === 'undefined' || str === null) {
return '';
}
var breakTag = (is_xhtml || typeof is_xhtml === 'undefined') ? '<br />' : '<br>';
return (str + '').replace(/([^>\r\n]?)(\r\n|\n\r|\r|\n)/g, '$1' + breakTag + '$2');
}
You can see more here
Related
Does anyone know how to add like a link button into a form? For example, a user clicks a + button and they can add an URL. They can add another URL if they wish and remove any links if required. Would be good to have validation for links as well.
I know for validation of the URL I can use "Check if a JavaScript string is a URL", but will need something that will validate all links if multiple have been added.
The best way to explain what I am trying to do is by looking at "Can I insert a hyperlink in my form?" in the form builder.
I just want to add links, and I don't need to display text or anything like that.
Is this what are you looking for?
Your question is a bit unclear.
<!DOCTYPE html>
<html>
<head>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.4.1/jquery.min.js"></script>
<script>
let i = 0;
let ii = 0;
function isURL(s) {
var regexp = /(ftp|http|https):\/\/(\w+:{0,1}\w*#)?(\S+)(:[0-9]+)?(\/|\/([\w#!:.?+=&%#!\-\/]))?/
return regexp.test(s);
}
function removeLink(id, iid) {
console.log(id);
console.log(iid);
$(id).remove();
$(iid).remove();
return false;
}
function addLink(id) {
var input = prompt("Enter the link", "https://www.example.com");
var valid = isURL(input);
console.log(valid);
if(valid) {
var element = '<br><a id="_' + i + '" href="' + input + '">Link</a>';
console.log(element);
$(id).append(element);
let d = "'#_" + i + "'";
let dd = "'#__" + ii + "'";
let elment = ' <button type="button" id="__' + ii + '" onclick="removeLink(' + d + ', ' + dd + ')">Remove it!</button>';
$(id).append(elment);
console.log(elment);
i = i + 1;
ii = ii + 1;
}
else {
alert("The URL that you have entred is wrong.");
}
return false;
}
</script>
</head>
<body>
<form id="_form" method="POST">
<button type="button" onclick="addLink('#_form')">Add link</button>
</form>
</body>
</html>
Try it here: https://codepen.io/marchmello/pen/ZEGjMyR?editors=1000
What about DOM - not using longer form, so using URL as link text too.
function addUrl(e) {
var f = e.form;
var a = document.createElement("A");
a.href = e.value; // link URL
a.textContent = e.value; // link text
f.appendChild(a);
var x = document.createElement("INPUT");
x.type = "button";
x.value = "X";
x.onclick = remove;
f.appendChild(x);
f.appendChild(document.createElement("BR"));
}
function remove() {
var el = this, // button
parent = el.parentNode, // a must for remove
a = el.previousElementSibling; // anchor
if(el.nextSibling.tagName == 'BR') parent.removeChild(el.nextSibling);
parent.removeChild(el);
parent.removeChild(a);
}
<form>
<input name="url" size="50">
<input type="button" value="Add" onclick="addUrl(this.form.url)"><br>
</form>
I am trying to insert an underline or blank space in a div that is being affected with a keyup function. The objective is to be able to move where the blank space is in the text. The keyup function works fine, the inserting of the blank space (div class underline) isnt.
HTML:
<div class="bigwhitecard" id="bigwhitecard"></div>
<textarea id="text" placeholder="Type your card here" name="text"></textarea>
Javascript/Jquery:
$(document).ready(function () {
$('#text').keyup(function(){
$('#bigwhitecard').html($(this).val());
});
var blankplace = 0;
$('#rightbtn').click(function() {
blankplace++;
});
$('#leftbtn').click(function() {
blankplace--;
});
var b = '<div class="underline"></div>';
$('#bigwhitecard').each(function() {
var blankplace = 0;
var txt = $(this).text();
if (txt.length>0) {
$(this).html(''+txt.substring(0,blankplace)+'<div class="underline"> </div>');
}
});
});
So use a substr to get the remaining text length that is left over and add it after the text.
var filler = "__________";
var out = document.getElementById("bigwhitecard");
document.getElementById("text").addEventListener("keyup", function() {
var txt = this.value,
placeholder = txt.length<filler.length ? '<span class="underline">' + filler.substr(0,filler.length-txt.length) + '</span>' : '';
out.innerHTML = txt + placeholder;
});
.underline {
text-decoration: underline
}
<div class="bigwhitecard" id="bigwhitecard"></div>
<textarea id="text" placeholder="Type your card here" name="text"></textarea>
And based on your comment
var out = document.getElementById("bigwhitecard");
document.getElementById("text").addEventListener("keyup", function() {
var txt = this.value,
ind = 6,
len = this.value.length,
pre = len > ind ? txt.substr(0,ind) : txt,
suf = len > ind ? txt.substr(ind) : "";
out.innerHTML = pre + "<span>_</sapn>" + suf;
});
.underline {
text-decoration: underline
}
<div class="bigwhitecard" id="bigwhitecard"></div>
<textarea id="text" placeholder="Type your card here" name="text"></textarea>
i want output text oldnames not changes if user insert text 'false'
for example:
user input text "false toni" in textbox.
and i want output still "false toni"
why my code still changes text "toni" with "rina"?
<script type="text/javascript" charset="utf-8">
String.prototype.replaceArr = function(find, replace) {
var replaceString = this;
var regex;
for (var i = 0; i < find.length; i++) {
regex = new RegExp(find[i], "g");
replaceString = replaceString.replace(regex, replace[i]);
}
return replaceString;
}
function test() {
var x = document.getElementById("myText").value;
var oldNames = ['toni','rian'];
var newNames = ['rina','susi'];
if (oldNames== 'false ' + oldNames){
document.getElementById("check").innerHTML = x.replaceArr(oldNames, oldNames);
}else{
document.getElementById("check").innerHTML = x.replaceArr(oldNames, newNames);
}
}
</script>
<body>
ENTER TEXT: <br>
<textarea name="kata_cari" id="myText" style="width:100%; height:100px;"></textarea>
<br>
<input type="button" onclick="test();" value="Check!">
<br>
<p id="check"></p>
</body>
UPDATE:
Improve the question:
Trying enter text "My name is rian and my name is false toni" .
Posible to make output "rian" still change to "susi"?
use includes x.includes(value) to check whether the text area value contains a word that you want to replace . if it contains false then your oldnames not get changed.
If you are using IE then use x.indexOf(value)>0 instead of x.includes(value)
http://www.w3schools.com/jsref/jsref_includes.asp
<script type="text/javascript" charset="utf-8">
String.prototype.replaceArr = function(find, replace) {
var replaceString = this;
var regex;
for (var i = 0; i < find.length; i++) {
regex = new RegExp(find[i], "g");
replaceString = replaceString.replace(regex, replace);
}
return replaceString;
}
function test() {
var x = document.getElementById("myText").value;
var oldNames = ['toni', 'rian'];
var newNames = ['rina', 'susi'];
oldNames.forEach(function(value, index) {
/*if (x.includes('false '+value)){
var oldNames1=['false '+value];
x = x.replaceArr(oldNames1, oldNames1);
}*/
if (x.includes(value)) {
var oldNames1 = [value];
x = x.replaceArr(oldNames1, newNames[index]);
newNames1 = ['false ' + newNames[index]];
oldNames1 = ['false ' + value];
x = x.replaceArr(newNames1, oldNames1);
}
});
document.getElementById("check").innerHTML = x;
}
</script>
<body>
ENTER TEXT:
<br>
<textarea name="kata_cari" id="myText" style="width:100%; height:100px;"></textarea>
<br>
<input type="button" onclick="test();" value="Check!">
<br>
<p id="check"></p>
</body>
You false checking condition is wrong, you can do it using substr:
if (x.substr(0, 6) === 'false ') {
// The string starts with false
} else {
}
You can find more details on the substr from MDN.
UPDATE: As mentioned in the comment same can be done via startsWith and this is a better approach.
if (x.startsWith('false ')) {
// The string starts with false
} else {
}
try this. Compare array values instead of array.
<script type="text/javascript" charset="utf-8">
String.prototype.replaceArr = function(find, replace) {
var replaceString = this;
var regex;
for (var i = 0; i < find.length; i++) {
regex = new RegExp(find[i], "g");
replaceString = replaceString.replace(regex, replace[i]);
}
return replaceString;
}
function test() {
var x = document.getElementById("myText").value;
var oldNames = ['toni','rian'];
var newNames = ['rina','susi'];
if (x.indexOf('false') > -1 ){
document.getElementById("check").innerHTML = x.replaceArr(oldNames, oldNames);
}else{
document.getElementById("check").innerHTML = x.replaceArr(oldNames, newNames);
}
}
</script>
<body>
ENTER TEXT: <br>
<textarea name="kata_cari" id="myText" style="width:100%; height:100px;"></textarea>
<br>
<input type="button" onclick="test();" value="Check!">
<br>
<p id="check"></p>
</body>
I have an array in javascript like that :
var books = ['spring','last night','sweet heart','the sky','tomorrow'] ;
I have textarea
<textarea id="text" name="textpreview" class="text"></textarea>
So what I want is when I enter letter s then I will get two suggestions books just the first word not the second word I mean not sky Just spring and sweet heart .
I will get two spans
<textarea id="text" name="textpreview" class="text"></textarea>
<span>spring</span>
<span>sweet heart</span>
If I type again after s the p letter like sp in textarea then I will get just spring
<textarea id="text" name="textpreview" class="text"></textarea>
<span>spring</span>
and so on .
If I type n I will get nothing.
If I type t I will get tomorrow and the sky
Hope it can be done . Thanks for your support .
This help you :
<html>
<head>
<title></title>
</head>
<body>
<textarea id="text" name="textpreview" class="text"></textarea>
<p id="x"></p>
<script>
var x = document.getElementById("x");
var books = ['spring','last night','sweet heart','last night','the sky','tomorrow','tomorrow'];
var txt = document.getElementById("text");
txt.onkeyup = function(event) {
var str = "";
var arr = [];
var index = (txt.value).indexOf("#");
if(index !== -1 && (txt.value).substr(index + 1).length > 0) {
var value = (txt.value).substr(index + 1);
value = value.replace(/[\.\+\*\\\?]/g,'\\$&');
var patt = new RegExp("^" + value);
for(var i=0; i<books.length; i++) {
if(patt.test(books[i]) && arr.indexOf(books[i]) === -1) {
arr.push(books[i]);
}
}
}
if (arr.length < 1 )
x.innerHTML = "";
else {
for(var i=0; i<arr.length; i++)
str+=arr[i]+"<br>";
x.innerHTML = str;
}
}
</script>
</body>
</html>
This problem consists of two parts: Reading and writing your input/output from/to the DOM, and filtering your array books.
The reading and writing part should be easy, there are plenty of guides on how to achieve this.
To filter the books array, JavaScript offers a number of helpful functions:
var books = ['spring','last night','sweet heart','the sky','tomorrow'];
var input = 'S';
var result = books.filter(function(book) {
return book.toLowerCase().indexOf(input.toLowerCase()) === 0;
}).slice(0, 2);
console.log(result); // ['spring', 'sweet heart']
#TimoSta is correct that this is a two-part problem.
I expanded on his code a bit using angular to display the results in the DOM.
http://jsfiddle.net/kcmg9cae/
HTML:
<div ng-controller="MyCtrl">
<textarea id="text" name="textpreview" class="text" ng-model="startsWith"></textarea>
<span ng-repeat="book in sortedBooks()">{{ book }}</span>
</div>
Javascript:
var myApp = angular.module('myApp',[]);
function MyCtrl($scope) {
$scope.books = ['spring','last night','sweet heart','the sky','tomorrow'];
$scope.sortedBooks = function () {
var sortedBooks = [];
for (var i = 0; i < $scope.books.length; i++){
if ($scope.books[i].toLowerCase().indexOf($scope.startsWith.toLowerCase()) === 0)
sortedBooks.push($scope.books[i]);
}
return sortedBooks;
}
}
I'm trying to write something like an image font generator, but I can not check if the form value is an space, or give an URL to an whitespace image.
Here is my code:
<html><head><title>untitled</title>
<script type="text/javascript">
<!--
function fontgen(text) {
var url = './fonts/';
var letters = text.split('');
var imgStr = "";
for (var i in letters) {
imgStr += '<img src="' +url+letters[i]+ '.gif">';
}
document.getElementById('name').innerHTML = imgStr;
return false;
}
//-->
</script>
</head>
<body>
<form name="myform" action="">
<input type="text" name="myinput" size="20"><br>
<input type="button" value="Make Font" onclick="return fontgen(document.myform.myinput.value)">
</form>
<div id="name"></div>
</body>
</html>
function fontgen(text) {
var url = './fonts/',
letters = text.split(''),
imgStr = "";
// First, you need a valid for loop:
for (var i = 0; i < letters.length; i++) {
if (letters[i] !== ' ') { // then, check to see if it is a space
imgStr += '<img src="' +url+letters[i]+ '.gif">';
}
}
document.getElementById('name').innerHTML = imgStr;
return false;
}
From what I can tell from your question, you're looking for something like this:
for (var i=0;i<text.length;i++)
{
if (text.charAt(i) !== ' ')
{//using charAt, you're supporting all browsers, without having to split the string
console.log(text.charAt(i) + ' is not space');
}
}
But an easier way of doing this, without having to loop through all chars, 1 by 1, is this:
if (text.indexOf(' ') === -1)
{
console.log('No spaces in ' + text + ' found');
}
Or, if you want to, you can replace or remove all spaces in one go:
text = text.replace(/\s/g,'_');//replaces spaces with underscores
text = text.replace(/\s/g, '');//removes spaces
Regex-mania way. Suppose you have a certain set of chars as gifs, you can easily use a single regex to replace all of those chars with their corresponding images in one fell swoop:
var imgString = text.replace(/([a-z0-9\s])/gi, function(char)
{
if (char === ' ')
{
char = 'space';//name of space img
}
return '<img src="'url + char + '.gif"/>';
});
Same logic applies to chars like ! or ., since they're not exactly suitable for file names, use an object, array or switch to replace them with their corresponding file-names.Anyway, with input like foo bar, the output of the code above should look something like this:
<img src="./fonts/f.gif"/><img src="./fonts/o.gif"/><img src="./fonts/o.gif"/><img src="./fonts/space.gif"/><img src="./fonts/b.gif"/><img src="./fonts/a.gif"/><img src="./fonts/r.gif"/>
Not sure why your path is ./foo/[].gif, I suspect foo/[].gif would do just as well, but that's not the issue at hand here.
In case you're interested: here's some more about replacing using regex's and callbacks
try replacing letters[i]
with:
(letters[i] == " ") ? "spacefilename" : letters[i]
this is a ternary operator. basically a shorthand if statement that can be used directly in place of letters[i]
in a sense it would be like replacing letters[i] with myfilename(letters[i])
where the myfilename function is
function myfilename(char)
{
if (char == " ") {
return "space";
} else {
return char;
}
}
so your code would look like this:
<html><head><title>untitled</title>
<script type="text/javascript">
<!--
function fontgen(text) {
var url = './fonts/';
var letters = text.split('');
var imgStr = "";
for (var i = 0; i < letters.length; i++) {
imgStr += '<img src="' +url+(letters[i] == " ") ? "spacefilename" : letters[i]+ '.gif">';
}
document.getElementById('name').innerHTML = imgStr;
return false;
}
//-->
</script>
</head>
<body>
<form name="myform" action="">
<input type="text" name="myinput" size="20"><br>
<input type="button" value="Make Font" onclick="return fontgen(document.myform.myinput.value)">
</form>
<div id="name"></div>
</body>
</html>
/e also as someone else mentioned, the for loop is wrong. i corrected that just now.
a "for...in" loop could work there... don't want to get into all that though.
Try changing the character into a char code and having a corresponding image file for each code you want to support; you can also put a range check via if statement to make sure the codes fall within your accepted ranges.
function fontgen(text)
{
var imgStr = "";
for (var i = 0; i < text.length; i++)
imgStr += '<img src="./fonts/' + text[i].charCodeAt(0) + '.gif">';
document.getElementById('name').innerHTML = imgStr;
return false;
}
If you supply this function the phrase "this is a test" it will result in:
<div id="name">
<img src="./fonts/116.gif">
<img src="./fonts/104.gif">
<img src="./fonts/105.gif">
<img src="./fonts/115.gif">
<img src="./fonts/32.gif">
<img src="./fonts/105.gif">
<img src="./fonts/115.gif">
<img src="./fonts/32.gif">
<img src="./fonts/97.gif">
<img src="./fonts/32.gif">
<img src="./fonts/116.gif">
<img src="./fonts/101.gif">
<img src="./fonts/115.gif">
<img src="./fonts/116.gif">
</div>
<img src="./fonts/32.gif"> would be the space image.