How would one change the text of a div to another string of text after a certain period of time using node.js and the setTimeout function?
The main caveat is that the text should be changed for all users at the same time.
Let's say an h2 title on the index page would initially say "Welcome to this page."
5 seconds later (after the server time, not after the time of a request), that h2 title should change to "Let's get started."
If another request came in 6 seconds after the server started, they should see "Let's get started." and never see "Welcome to this page." since the h2 title should have been universally changed.
Any guidance hugely appreciated.
Here is what you may try (Express + SocketIO 1.0 example):
server.js:
var app = require('express')();
var server = require('http').createServer(app);
var io = require('socket.io')(server);
server.listen(80);
var dir = __dirname;
app.get('/', function(req, res) {
res.sendfile(dir + '/index.html');
});
var header = 'Welcome to this page.';
setTimeout(function() {
header = 'Let\'s get started.';
io.emit('change_header', {
header: header
});
}, 5000);
io.on('connection', function(socket) {
socket.emit('change_header', {
header: header
});
});
index.html:
<!DOCTYPE html>
<html>
<head>
<script src="/socket.io/socket.io.js"></script>
<script>
document.addEventListener('DOMContentLoaded', function() {
var socket = io();
socket.on('change_header', function(data) {
document.getElementById('header').innerHTML = data.header;
});
});
</script>
</head>
<body>
<h2 id="header"></h2>
</body>
</html>
Related
I'm new on node.js, i'm trying to make a simple sharing picture app, and my problem is:
with the server i get an error on line 13 that says "require(...).listen is not a function"
and how can i implement that when i upload a picture as a client that other clients can see the picture for 1 hour and in that 1 hour they can save it and if they want the other clients can add a new picture instead of the one that has been added so other clients can save it and can see it.
My main goal is:
Frontend: Which allows the customer to take a photo and upload it at a specific time.
When the time comes, you need to show the image to anyone who opens your site.
Back End: That allows each of your customers to take a photo and save it until time runs out and shows all customers the photo.
my code:
server with an error on line 13 that I couldn't resolve
var express = require("express");
var app = express();
var http = require('http');
var fs = require('fs');
var server = http.createServer(function(req, res) {
fs.readFile('./index.html', 'utf-8', function(error, content) {
res.writeHead(200, {"Content-Type": "text/html"});
res.end(content);
});
});
var io = require('socket.io').listen(server);
io.sockets.on('connection',function(socket){
socket.on('user image',function (image){
io.sockets.emit('addimage', {'src' :image});
});
});
app.get('/',function (req,res) {
res.render('index');
})
server.listen(8080,function () {
console.log('listen port 8080')
})
html page:
<!DOCTYPE html>
<html>
<head>
<meta charset=utf-8 />
<title>Upload your Image</title>
<style>
article, aside, figure, footer, header, hgroup,
menu, nav, section { display: block; }
</style>
</head>
<body>
<div><input type='file' onchange="readURL(this);" /></div></b>
<div><img id="img" src="" /></div>
<script class="jsbin" src="http://ajax.googleapis.com/ajax/libs/jquery/1/jquery.min.js"></script>
<script class="jsbin" src="http://ajax.googleapis.com/ajax/libs/jqueryui/1.8.0/jquery-ui.min.js"></script>
<script src="/socket.io/socket.io.js"></script>
<script>
var socket = io.connect('http://localhost:8080');
socket.on('addimage',function(msg){
//reading src property from msg as per changes
$('#img')
.attr('src', msg.src)
.width(800)
.height(400);
});
function readURL(input) {
if (input.files && input.files[0]) {
var reader = new FileReader();
reader.onload = function (e) {
$('#img')
.attr('src', e.target.result)
.width(800)
.height(400);
socket.emit('user image', e.target.result);
};
reader.readAsDataURL(input.files[0]);
}
}
</script>
<script src="http://html5shiv.googlecode.com/svn/trunk/html5.js"></script>
</body>
</html>
In your JS,
Try using:
var server = http.createServer(app);
and on line 13:
var { Server } = require("socket.io");
var io = new Server(server);
and instead of:
io.sockets.on('connection',function(socket){
socket.on('user image',function (image){
io.sockets.emit('addimage', {'src' :image});
});
});
try using:
io.on('connection', function(socket) {
socket.on('user image', function(image) {
io.emit('addimage', {'src' :image});
});
});
Edit: also, to serve the client your home page, try this in app.get("/", function(req, res) {...})
app.get('/', function(req, res) {
res.sendFile(__dirname + '/index.html');
});
and in your internal JS in your HTML file:
var socket = io('http://localhost:8080');
// if above does not work, try the below instead:
var socket = io();
I don't know if it will help you but hopefully it will. However you might need to change some of the code to work with the below suggestions.
The suggestions were based off the Socket.io documentation. Also you might want to see their example on building a chat application. Might help you with something:
Reference
Socket.io
Documentation
Chat Application
i prepared a simple chat system while practicing node.js. but theres a problem while sending messages. quite a good amount of delay taking place while sending messages and i couldnt figure out why. can anyone help me how to improve attached code ?
server.js
var app = require('express')();
var http = require('http').Server(app);
var io = require('socket.io')(http);
app.get('/', function(request, response) {
response.sendFile(__dirname + '/index.html');
});
io.on('connection', function(client) {
client.on('messageSend', function(data) {
client.broadcast.emit('messageRecieve', data);
});
});
http.listen(9090, function() {
console.log('Listening on port 9090');
io.on('connect', function(socket) {
console.log("Connection established : " + socket.client.conn.remoteAddress);
})
});
index.html
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<title>Socket Test</title>
<script src="/socket.io/socket.io.js"></script>
<script>
var socket = io();
function messageSend() {
var message = document.getElementById("messageInput").value;
console.log(message);
var ul = document.getElementById("messageNode");
var li = document.createElement("li");
li.appendChild(document.createTextNode(message));
li.setAttribute("style", "font-style : italic; color : red;");
ul.appendChild(li);
socket.emit('messageSend', message);
}
socket.on('messageRecieve', function(data) {
var message = data;
var ul = document.getElementById("messageNode");
var li = document.createElement("li");
li.appendChild(document.createTextNode(message));
ul.appendChild(li);
console.log(message);
});
</script>
</head>
<body>
<input id="messageInput" type="text"> <button onclick="messageSend()">Send</button><br>
<ul id="messageNode">
</ul>
</body>
</html>
the official socket.io example sends the message to everyone, including yourself
io.on('connection', function(socket){
socket.on('chat message', function(msg){
io.emit('chat message', msg);
});
});
You sent to everyone except yourself (which is the most accurate method)
io.on('connection', function(client) {
client.on('messageSend', function(data) {
client.broadcast.emit('messageRecieve', data);
});
});
The reason for your slowdown is probably becouse your browser puts your out-of-focus tabs in a sort of sleep mode, which makes it update much less frequently... If you compare your code vs socket.io's code between computer and phone via lan. I would guess the speed for your server-sent message would be the same
Right now you are basically competing versus socket.io's "optimistic updates". It pushes the message to your client directly without waiting for the server, which your own code does. As well as browser out-of-focus low priority mode
I'm new to Node.js and JavaScript. I have a specific problem but mostly need advice on the best solution.
I'm running a Node server. I want the client to be able to submit a string to the server, then the server to display a new HTML page that shows the string data.
I'm using Express and Socket.io.
In the following files, the client sees index.html, then after submitting the form it sees return.html. I print the input string to the console, and the output is as expected (whatever the user enters). But the return.html is never updated with the input string.
I also tried sending the return.html page and the change_result call in an async series, but the sendFile function never ends and the second function in the series is never called. In previous attempts it worked intermittently with a setTimeout around the emit('change_result') function.
Why doesn't the call to change_result do anything? I used the same technique to update the headings of the original index.html in previous versions. Should I be routing to localhost.../return.html and sending the post data there, or something like that?
server.js
var express = require('express');
var app = express();
var server = require('http').createServer(app);
var io = require('socket.io')(server);
var bodyParser = require('body-parser') //for POST request
app.use( bodyParser.json() ); // to support JSON-encoded bodies
app.use(bodyParser.urlencoded({ // to support URL-encoded bodies
extended: true
}));
server.listen(8080, function() {
console.log("Server running on port 8080.");
});
var dir = __dirname;
app.get('/', function(req, res) {
res.sendFile(dir + '/index.html');
});
app.post('/', function(req, res) {
var query1=req.body.input1
console.log("Server: In post request.")
console.log(query1);
res.sendFile(dir + '/return.html');
io.emit('change_result', {
result: query1
});
});
index.html
<!DOCTYPE html>
<html>
<body id="body">
<form method="post" action="http://localhost:8080">
String: <input type="text" name="input1" id="input1" />
<input type="submit" id="button1" value="Submit" />
</form>
</body>
</html>
return.html
<!DOCTYPE html>
<html>
<body id="body">
<p id="heading1">Result: </p>
<script>
document.addEventListener('DOMContentLoaded', function() {
var socket = io();
socket.on('change_result', function(data) {
document.getElementById('heading1').innerHTML = "Result: \""+data.result"\"";
});
});
</script>
</body>
</html>
I'm not knee-deep inside socket.io, but IMO the problem is, that the server has no way to know if any listeners are ready.
I think you should emit a 'ready' event, once the return.html is loaded, then listen to 'change_result'. Also separate the socket communication from the POST response on the server. Like so.
server.js
var query;
app.get('/', function(req, res) {
res.sendFile(dir + '/index.html');
});
app.post('/', function(req, res) {
query = req.body.input1;
console.log("Server: In post request.");
console.log(query);
res.sendFile(dir + '/return.html');
});
io.on('connection', function(socket) {
socket.on('ready', function() {
socket.emit('change_result', {result: query});
});
});
return.html
<script>
document.addEventListener('DOMContentLoaded', function() {
var socket = io();
socket.emit('ready', function(data) {});
socket.on('change_result', function(data) {
document.getElementById('heading1').innerHTML = "Result: \""+data.result + "\"";
});
});
</script>
Here is my code
server.js
var http = require('http');
var app = require('express')();
var server = http.createServer(app).listen(process.env.PORT, process.env.IP);
var io = require('socket.io').listen(server);
var textData = "some random initial text that will be changed forever, never to be restored to its original state."
app.get('/', function(req, res){
res.sendFile(__dirname + '/index.html');
});
var users = 0;
io.on('connection', function(socket){
users++;
console.log(users + " users are here.");
//broadcast recieved data
socket.on('textChange', function(text){
textData = text;
socket.broadcast.emit('updatedText', textData);
});
socket.on("disconnect", function(){
users--;
console.log(users + " users are here.");
})
});
index.html
<!DOCTYPE html>
<html>
<head>
<script type="text/javascript" src="https://code.jquery.com/jquery-latest.min.js"></script>
<script src="/socket.io/socket.io.js"></script>
<script>
/* global io */
var socket = io();
$(document).ready(function() {
//send value on key up
$('#textarea').keyup(function(){
socket.emit('textChange', $('#textarea').val());
});
//recieve changed value
socket.on('updatedText', function(text){
$('#textarea').val(text);
});
});
</script>
<style type="text/css">
form, form * {
width: 100%;
height: 400px;
}
</style>
</head>
<body>
<h1>HELLO</h1>
<h2></h2>
<form action="">
<textarea id="textarea"></textarea>
</form>
</body>
</html>
It is working as inteded but when the two people type simultaniously, it alternates between them and just bugs out. How can I make it so that two people can type together.
I am thinking about using diff-patch but Im not sure if it will even solve this issue.
Please Help.
maybe you can add some user identifier(e.g. sessionid or uuid or other stuff) to recognize the users,etc:
// add user id
var user = Math.random();
$('#textarea').keyup(function(){
socket.emit('textChange', {name: user, val: $('#textarea').val()});
});
//recieve changed value
socket.on('updatedText', function(text){
if (text.user == user) {
$('#textarea').val(text.val);
}
});
I am trying to use node.js and socket.io library to establish websocket connection between client and server. The server will generate a random number per second and it will emit a event which allow client to detect.
The problem is the client(a webpage) can detect the event and display the random number send by server, but it's not real-time. I had to refresh my browser in order to display a new random number. I want the client to display the random number in real-time but I don't know why my websocket app appears to be not real-time.
Server(main.js) source code:
var app = require('express')();
var server = require('http').Server(app);
var io = require('socket.io')(server);
app.get('/', function(req, res){
res.sendFile(__dirname + '/index.html');
});
randomNum();
function randomNum(){
io.on('connection', function(socket){
socket.emit('random', Math.floor((Math.random() * 100) + 1));
});
setInterval(randomNum, 1000);
}
server.listen(8080);
Client(index.html) source code:
<!doctype html>
<html>
<head>
<meta charset="utf-8">
<title>Websocket</title>
<script src="/socket.io/socket.io.js"></script>
<script>
var socket = io();
socket.on('random', function(data){
document.getElementById("displayNum").innerHTML = data;
});
</script>
</head>
<body>
<p id="displayNum"></p>
</body>
</html>
You shouldn't do this:
function randomNum(){
io.on('connection', function(socket){
socket.emit('random', Math.floor((Math.random() * 100) + 1));
});
setInterval(randomNum, 1000);
}
You set io.on connection every 1s. You should make function for emiting your random and set interval outside this function