patternjavascriptMinor
Automation project
Viewed 0 times
projectautomationstackoverflow
Problem
There are buttons on a page, each corresponding to a different code that needs to be sent to PubNub DSN, which is published to my home server to operate specific on/off commands for various lights in home. This is primarily a learning experience for now.
I currently have 4 basic buttons on page:
NOTE: "Name is the code that needs to be sent, depending on which button is clicked, corresponding to the specific device"
Here is all the JavaScript I built to make it work. This was pretty easy and works perfectly:
```
(function(){
//DOM
var button1 = document.querySelector('button[name=d_on]');
var button2 = document.querySelector('button[name=d_off]');
var button3 = document.querySelector('button[name=a_on]');
var button4 = document.querySelector('button[name=a_off]');
var code1 = button1.name;
var code2 = button2.name;
var code3 = button3.name;
var code4 = button4.name;
// PubNub Channel Name
var channel = 'demo';
//Init - Sub and Pub key
var p = PUBNUB.init({
subscribe_key: 'sub-c...',
publish_key: 'pub-c...'
});
// Sending data
function jetson1(){
p.publish({
channel : channel,
message : {"text":"From Website",
"code": button1.name}
});
}
function jetson2(){
p.publish({
channel : channel,
message : {"text":"From Website",
"code": button2.name}
});
}
function jetson3(){
p.publish({
channel : channel,
message : {"text":"From Website",
"code": button3.name}
});
}
function jetson4(){
p.publish({
channel : channel,
message : {"text":"From Website",
"code": button4.name}
});
}
//C
I currently have 4 basic buttons on page:
Dining Room On
Dining Room Off
Bedroom On
Bedroom Off
NOTE: "Name is the code that needs to be sent, depending on which button is clicked, corresponding to the specific device"
Here is all the JavaScript I built to make it work. This was pretty easy and works perfectly:
```
(function(){
//DOM
var button1 = document.querySelector('button[name=d_on]');
var button2 = document.querySelector('button[name=d_off]');
var button3 = document.querySelector('button[name=a_on]');
var button4 = document.querySelector('button[name=a_off]');
var code1 = button1.name;
var code2 = button2.name;
var code3 = button3.name;
var code4 = button4.name;
// PubNub Channel Name
var channel = 'demo';
//Init - Sub and Pub key
var p = PUBNUB.init({
subscribe_key: 'sub-c...',
publish_key: 'pub-c...'
});
// Sending data
function jetson1(){
p.publish({
channel : channel,
message : {"text":"From Website",
"code": button1.name}
});
}
function jetson2(){
p.publish({
channel : channel,
message : {"text":"From Website",
"code": button2.name}
});
}
function jetson3(){
p.publish({
channel : channel,
message : {"text":"From Website",
"code": button3.name}
});
}
function jetson4(){
p.publish({
channel : channel,
message : {"text":"From Website",
"code": button4.name}
});
}
//C
Solution
You're on the right track, but you need to use jquery more effectively. I'm sorry, I thought you were already using jQuery. I see now that you have your own little homegrown jQuery-like function. You should just use jQuery instead, and that'll make this a lot easier.
Once you've added jQuery, then just by adding a class to the buttons you want this to happen on, and then binding an onclick event handler to that class you can remove all of your code duplication. As a note, you might not be able to run the stack snippet - I was getting some errors about XSS issues, but I have a weird browser configuration so I don't know if it'll affect you.
If you're going to continue to add more of these, however, you're probably going to want some dynamically generated HTML. The specifics of that are beyond the scope of this question, but I encourage you to look into those solutions as this project expands.
At times it is also desirable to not use any external libraries if possible, and I'm a firm believer that knowing how to do something in pure JavaScript (not just jQuery) is important. I also think that in many cases, adding jQuery as a dependency is unnecessary. Here you can easily accomplish the same thing in an almost identical fashion without adding jQuery. You'll notice that I actually had to change very little about your code - I just assigned the onclick event to an actual function, and I cleaned up a bit towards the end.
Once you've added jQuery, then just by adding a class to the buttons you want this to happen on, and then binding an onclick event handler to that class you can remove all of your code duplication. As a note, you might not be able to run the stack snippet - I was getting some errors about XSS issues, but I have a weird browser configuration so I don't know if it'll affect you.
(function(){
var pubnubChannelName = 'demo'
var p = PUBNUB.init({
subscribe_key: 'sub-c...',
publish_key: 'pub-c...'
});
function publishData(code) {
p.publish({
channel: pubnubChannelName,
message: {
"text": "From Website",
"code": code
}
});
}
$(document).ready(function() {
$('.pubnub_button').click(function() {
publishData($(this).attr('name'));
});
});
})();
Dining Room On
Dining Room Off
Bedroom On
Bedroom Off
If you're going to continue to add more of these, however, you're probably going to want some dynamically generated HTML. The specifics of that are beyond the scope of this question, but I encourage you to look into those solutions as this project expands.
At times it is also desirable to not use any external libraries if possible, and I'm a firm believer that knowing how to do something in pure JavaScript (not just jQuery) is important. I also think that in many cases, adding jQuery as a dependency is unnecessary. Here you can easily accomplish the same thing in an almost identical fashion without adding jQuery. You'll notice that I actually had to change very little about your code - I just assigned the onclick event to an actual function, and I cleaned up a bit towards the end.
(function() {
var channel = 'demo';
var p = PUBNUB.init({
subscribe_key: 'sub-c-',
publish_key: 'pub-c'
});
function jetson(code) {
p.publish({
channel: channel,
message: {
"text": "From Website",
"code": code
}
});
}
var $ = function(selector) {
return document.querySelectorAll(selector);
};
var buttons = $('#main > button');
for (var button in buttons) {
button.onclick = function() {
jetson(button.getAttribute('name'));
};
}
})();
Context
StackExchange Code Review Q#135072, answer score: 2
Revisions (0)
No revisions yet.