The essential widget if you want your workspace to talk to the Serial Port JSON Server (SPJS). This widget enables numerous pubsub signals so you can publish to SPJS and receive data back when you subscribe to the appropriate signals.
All ChiliPeppr widgets/elements are defined using cpdefine() which is a method that mimics require.js. Each defined object must have a unique ID so it does not conflict with other ChiliPeppr widgets.
Item | Value |
---|---|
ID | com-chilipeppr-widget-serialport |
Name | Widget / Serial Port JSON Server |
Description | The essential widget if you want your workspace to talk to the Serial Port JSON Server (SPJS). This widget enables numerous pubsub signals so you can publish to SPJS and receive data back when you subscribe to the appropriate signals. |
chilipeppr.load() URL | http://raw.githubusercontent.com/robZeilinga/widget-spjs/master/auto-generated-widget.html |
Edit URL | http://ide.c9.io/robzedweb/widget-spjs-robz |
Github URL | http://github.com/robZeilinga/widget-spjs |
Test URL | https://preview.c9users.io/robzedweb/widget-spjs-robz/widget.html |
You can use the code below as a starting point for instantiating this widget inside a workspace or from another widget. The key is that you need to load your widget inlined into a div so the DOM can parse your HTML, CSS, and Javascript. Then you use cprequire() to find your widget's Javascript and get back the instance of it.
// Inject new div to contain widget or use an existing div with an ID
$("body").append('<' + 'div id="myDivWidgetSerialport"><' + '/div>');
chilipeppr.load(
"#myDivWidgetSerialport",
"http://raw.githubusercontent.com/robZeilinga/widget-spjs/master/auto-generated-widget.html",
function() {
// Callback after widget loaded into #myDivWidgetSerialport
// Now use require.js to get reference to instantiated widget
cprequire(
["inline:com-chilipeppr-widget-serialport"], // the id you gave your widget
function(myObjWidgetSerialport) {
// Callback that is passed reference to the newly loaded widget
console.log("Widget / Serial Port JSON Server just got loaded.", myObjWidgetSerialport);
myObjWidgetSerialport.init();
}
);
}
);
This widget/element publishes the following signals. These signals are owned by this widget/element and are published to all objects inside the ChiliPeppr environment that listen to them via the chilipeppr.subscribe(signal, callback) method. To better understand how ChiliPeppr's subscribe() method works see amplify.js's documentation at http://amplifyjs.com/api/pubsub/
Signal | Description |
---|---|
/com-chilipeppr-widget-serialport/list | Sends the list of serial ports shown in this widget including the connect state so other widgets/elements in ChiliPeppr can use the list including knowing what serial ports to send/recv from. Send in /getList and get back a /list with the JSON payload of the list. |
/com-chilipeppr-widget-serialport/listAfterMetaDataAdded | Similar to /list but the list will have meta data added to it like an image, or default baud rates, or a modified friendly name. It may even be marked as deleted for dual port scenarios where a port may be considered the 2nd port. |
/com-chilipeppr-widget-serialport/ws/onconnect | When the websocket connects. This widget currently supports only a single websocket. In the future, multiple websockets will be supported and a ws identifier will be attached. For now, you will receive the string "connected" in the payload. The 2nd parameter will be the websocket in case you need it like to retrieve the IP address of SPJS. For multiple websockets an additional parameter will be published with the ws:// url |
/com-chilipeppr-widget-serialport/ws/ondisconnect | When the websocket disconnects. |
/com-chilipeppr-widget-serialport/ws/sys | A system message. Mostly for visual display like an error. |
/com-chilipeppr-widget-serialport/ws/recv | A signal published when the websocket receives data from the serial port server. The serial port, i.e. COM21, the websocket identifier, and data are sent. |
/com-chilipeppr-widget-serialport/onportopen | Published when the Serial Port JSON Server tells us a port was opened. This could happen from the user clicking to open, or if another browser or websocket client opens it, we will fire off this signal as well. The payload looks like {Cmd: "Open", Desc: "Got register/open on port.", Port: "COM22", Baud: 115200, BufferType: "tinyg"} |
/com-chilipeppr-widget-serialport/onportclose | Published when the Serial Port JSON Server tells us a port was closed. This could happen from the user clicking to close, or if another browser, or SPJS, or websocket client closes it, we will fire off this signal. The payload looks like {Cmd: "Close", Desc: "Got unregister/close on port.", Port: "COM22", Baud: 115200} |
/com-chilipeppr-widget-serialport/onportopenfail | Published when the Serial Port JSON Server tells us a port was attempting to be opened but failed for some reason. This could happen from the user clicking to open, or if another browser tries to open, but an error arose such as the port being locked by another process. The payload looks like {Cmd: "OpenFail", Desc: "Got error reading on port. ", Port: "COM22", Baud: 115200} |
/com-chilipeppr-widget-serialport/recvline | We publish this signal in tandem with /ws/recv but we only publish this signal per newline. That way your widget can consume per line data which is typically the way you want it. We recommend you subscribe to this channel instead of /ws/recv to have less work to do of looking for newlines. When in setSingleSelectMode() we will only send you data for the port that is selected (in green in UI). You will not get this signal for secondary ports that are open. For secondary ports, you need to subscribe to /ws/recv and do lower level parsing. |
/com-chilipeppr-widget-serialport/recvVersion | We send you this back if you published a /requestVersion signal. This is so other widgets can pivot off of what version of Serial Port JSON Server is running. For example, the Arduino/Atmel programmer sends in a /requestVersion to get a callback on /recvVersion to determine if you are at version 1.83 or above to know whether you have the correct functionality. |
/com-chilipeppr-widget-serialport/recvSingleSelectPort | In case any other widget/element wants to know what port is single selected (when in setSingleSelectMode()), they can send a signal to /requestSingleSelectPort and we'll respond back with this signal with an object like: { "Name": "COM22", "Friendly": "USB Serial Port (COM22)", "IsOpen": true, "Baud": 115200, "RtsOn": true, "DtrOn": false, "BufferAlgorithm": "tinyg", "AvailableBufferAlgorithms": [ "default", "tinyg", "dummypause" ], "Ver": 1.7 }. Will send back a null if no ports or no singleSelectPort is defined. |
/com-chilipeppr-widget-serialport/onQueue | This signal is published when a command is queued on SPJS. Payload is {"Id":"123", "D":"G0 X1 ", "QCnt":1, "Port":"COM2"}. You get the data back because if another browser sent into the SPJS, you get that data reflected in other browsers which is important for synchronizing. See /jsonSend for more info. |
/com-chilipeppr-widget-serialport/onWrite | This signal is published when a command is written to the serial port on SPJS. Payload is {"Id":"123", "QCnt":0, "Port":"COM2"}. The serial command is not reiterated in this signal like it is in /onQueue. See /jsonSend for more info. |
/com-chilipeppr-widget-serialport/onComplete | This signal is published when a command is done being written on SPJS and is known to have been processed by the serial device. Payload is {"Id":"123"}. Please note that sometimes /onComplete could come back before /onWrite due to the multi-threaded nature of serial ports and writing/reading as well as network congestion. See /jsonSend for more info. |
/com-chilipeppr-widget-serialport/onError | This signal is published when a command produces an error in the CNC controller either due to a gcode syntax problem, or an unsupported gcode command. This signal can be used by the cnc-interface widget to handle for errors, or pause/cancel gcode execution so that the problem can be rectified. |
/com-chilipeppr-widget-serialport/onBroadcast | This signal is published when we see a broadcast message come in from SPJS and we simply regurgitate it out on this signal for any widget to listen to. To send a broadcast signal into SPJS you just use the command "broadcast blah blah" and then SPJS re-broadcasts that to all listeners with a packet like {Cmd:"Broadcast", Msg:"blah blah"}. For example, the ShuttleXpress CNC jog shuttle connects to SPJS on its own and when you click buttons on the device it broadcasts them to SPJS so widgets inside ChiliPeppr can respond to those clicks. |
/com-chilipeppr-widget-serialport/onAnnounce | This signal is published when we see an announce message come in from SPJS and we simply regurgitate it out on this signal for any widget to listen to. An announce signal is part of the Cayenn protocol. Basically an IoT device like an ESP8266 sends in a UDP broadcast to the network announcing its existence. SPJS listens for those and then sends a copy of the announcement to any SPJS listeners, like us. Then this SPJS widget publishes it out so other widgets inside ChiliPeppr can listen for the message. |
/com-chilipeppr-widget-serialport/onFeedRateOverride | This signal is published when we get a feed rate override update from SPJS. It will contain the payload similar to {"Cmd":"FeedRateOverride","Desc":"Providing you status of feed rate override.","Port":"COM7","FeedRateOverride":0,"IsOn":false} |
/com-chilipeppr-widget-serialport/recvStatus | Send in a /requestStatus and we will send you back a /recvStatus letting you know if SPJS is connected or not to the Serial Port JSON Server. The payload that comes to you in /recvStatus looks like {"Connected":true, "Websocket": ws } or {"connected":false, "websocket":null}. If you want to be pushed an event when the socket connects or disconnects you should subscribe to /ws/onconnect and /ws/ondisconnect |
This widget/element subscribes to the following signals. These signals are owned by this widget/element. Other objects inside the ChiliPeppr environment can publish to these signals via the chilipeppr.publish(signal, data) method. To better understand how ChiliPeppr's publish() method works see amplify.js's documentation at http://amplifyjs.com/api/pubsub/
Signal | Description |
---|---|
/com-chilipeppr-widget-serialport/ws/send | This widget subscribes to this signal so anybody can publish
to SPJS by publishing here. You can send any command that SPJS supports. Please see the
docs for all support SPJS commands on Github at
https://github.com/chilipeppr/serial-port-json-server#supported-commands.
Example chilipeppr.publish("/com-chilipeppr-widget-serialport/ws/send", "send COM22 G0 X0\n"); Example of sending non-buffered command chilipeppr.publish("/com-chilipeppr-widget-serialport/ws/send", "sendnobuf /dev/ttyUSB0 M3 S1000\n"); |
/com-chilipeppr-widget-serialport/send | This widget subscribes to this signal whereby you can simply send
to this pubsub channel (instead of /ws/send which is lower level) and the widget will
send to the default serial ports that you are connected to (the green highlight in the UI).
Most serial devices expect newline characters, so you should send those in your string as
this pubsub channel does not add them.
Example chilipeppr.publish("/com-chilipeppr-widget-serialport/send", "G1 X10 F500\n"); |
/com-chilipeppr-widget-serialport/jsonSend | This signal is like /send but a more structured version where you can send us commands like {"D": "G0 X1 ", "Id":"123"} or an array like [{"D": "G0 X1 ", "Id":"123"}, {"D": "G0 X2 ", "Id":"124"}] and then this widget will send callback signals in order of /onQueue, /onWrite, /onComplete. The payload is {"Id":"123"} on each of those. The SPJS has 3 steps to get your command to the serial device. Step 1 is /onQueue and this will come back immediately when SPJS has taken your command and queued it to memory/disk. Step 2 is /onWrite when SPJS actually has written your command to the serial device. If the device takes a while to execute the command it could be a bit of time until that command is physically executed. Step 3 is /onComplete which is SPJS attempting to watch for a response from the serial device to determine that indeed your command is executed. Please note /onComplete can come back prior to /onWrite based on your serial device and how fast it may have executed your serial command. You can omit the Id if you do not care about tracking. You will get callbacks with an empty Id so you will not be able to match them up. If you send in /jsonSend {"D": "G0 X1 G0 X0 ", "Id":"123"} you will get back /onQueue [{"D":"G0 X1 ","Id":"123","Buf":"Buf"},{"D":"G0 X0 ","Id":"123-part-2-2","Buf":"Buf"}] because technically those are 2 commands with one Id. Some commands sent into Serial Port JSON Server get additional commands auto-added. For example, if you send in a command to TinyG that would put it in text mode, SPJS appends a command to put TinyG back in JSON mode. In those cases you will get parts added to your command and will see that in the response. |
/com-chilipeppr-widget-serialport/getlist | In case any other widget/element wants to request the list at any time, they can send a signal to this channel and we'll respond back with a /list |
/com-chilipeppr-widget-serialport/requestVersion | Send in this signal to get back a /recvVersion. This is so other widgets can pivot off of what version of Serial Port JSON Server is running. For example, the Arduino/Atmel programmer sends in a /requestVersion to get a callback on /recvVersion to determine if you are at version 1.83 or above to know whether you have the correct functionality. |
/com-chilipeppr-widget-serialport/requestSingleSelectPort | In case any other widget/element wants to know what port is single selected (when in setSingleSelectMode()), they can send a signal to this channel and we'll respond back with a /recvSingleSelectPort with an object like: { "Name": "COM22", "Friendly": "USB Serial Port (COM22)", "IsOpen": true, "Baud": 115200, "RtsOn": true, "DtrOn": false, "BufferAlgorithm": "tinyg", "AvailableBufferAlgorithms": [ "default", "tinyg", "dummypause" ], "Ver": 1.7 }. Will send back a null if no ports or no singleSelectPort is defined. |
/com-chilipeppr-widget-serialport/requestFro | Send in this signal to have this widget send in a request to SPJS for the Feed Rate Override status on the singleSelectPort, i.e. the port that is hilited green. This widget will send SPJS something like "fro COM7" and then the data will come back and a publish will occur on /onFeedRateOverride. If you send in an empty payload this will simply request the status. If you send in a float or integer it will actually set the Feed Rate Override multiplier to that value. |
/com-chilipeppr-widget-serialport/requestStatus | If you want to request the connected/disconnected status of this widget, you can send this pubsub signal in and we will send you back the connected status in the /recvStatus signal. We will also include the websocket object in case you were interested in it. Please see docs for /recvStatus for further info. |
This widget/element publishes to the following signals that are owned by other objects. To better understand how ChiliPeppr's subscribe() method works see amplify.js's documentation at http://amplifyjs.com/api/pubsub/
Signal | Description |
---|---|
/com-chilipeppr-widget-serialport/com-chilipeppr-elem-flashmsg/flashmsg | We publish system messages from the serial port server to the flash message element to display informational messages to the user. |
/com-chilipeppr-widget-serialport/com-chilipeppr-interface-cnccontroller/plannerpause | We publish a planner pause if we see that the buffer count in the Serial Port JSON Server gets above 20,000. |
/com-chilipeppr-widget-serialport/com-chilipeppr-interface-cnccontroller/plannerresume | We publish a planner resume when we get back to 15,000. |
This widget/element publishes to the following signals that are owned by other objects. To better understand how ChiliPeppr's publish() method works see amplify.js's documentation at http://amplifyjs.com/api/pubsub/
Signal | Description |
---|---|
(No signals defined in this widget/element) |
The table below shows, in order, the methods and properties inside the widget/element.
Method / Property | Type | Description |
---|---|---|
id | string | "com-chilipeppr-widget-serialport" |
name | string | "Widget / Serial Port JSON Server" |
desc | string | "The essential widget if you want your workspace to talk to the Serial Port JSON Server (SPJS). This widget enables numerous pubsub signals so you can publish to SPJS and receive data back when you subscribe to the appropriate signals." |
url | string | "http://raw.githubusercontent.com/robZeilinga/widget-spjs/master/auto-generated-widget.html" |
fiddleurl | string | "http://ide.c9.io/robzedweb/widget-spjs-robz" |
githuburl | string | "http://github.com/robZeilinga/widget-spjs" |
testurl | string | "http://widget-spjs-robz-robzedweb.c9users.io/widget.html" |
publish | object | Please see docs above. |
subscribe | object | Please see docs above. |
foreignPublish | object | Please see docs above. |
isWsConnected | boolean | |
host | object | |
portlist | object | |
conn | object | |
isSingleSelectMode | boolean | |
singleSelectPort | object | |
buffertype | object | |
defaultBaud | object | |
defaultOptions | object | |
isInitted | boolean | |
init | function | function (host, buffertype, defaultBaud, buffertypeDescription) |
setupSubnetScan | function | function () |
setupRecentServerList | function | function () |
showRecentServerList | function | function () |
setupStatusPubSub | function | function () |
onRequestStatus | function | function () |
setupFroPubSub | function | function () |
onRequestFro | function | function (payload) |
version | object | |
versionFloat | number | |
setupVersionPubSub | function | function () |
onRequestVersion | function | function () |
onVersion | function | function (version) |
resetVersion | function | function () |
hideVersion | function | function () |
resetSpjsName | function | function () |
onSpjsName | function | function (spjsName) |
setupCloudServers | function | function () |
onCloudServerClick | function | function (evt) |
showBufferEncouragement | function | function () |
hideBufferEncouragement | function | function () |
bufferEncouragement | function | function (list, arg2) |
publishSingleSelectPort | function | function () |
onRemoteHostConnect | function | function () |
setSingleSelectMode | function | function () |
getPortListCount | number | |
getPortList | function | function () |
btnBarSetup | function | function () |
restartSpjs | function | function () |
exitSpjs | function | function () |
disconnect | function | function () |
consoleToggle | function | function () |
statusToggle | function | function () |
history | object | |
historyLastShownIndex | object | |
pushOntoHistory | function | function (cmd) |
onHistoryMenuClick | function | function (evt) |
consoleSetup | function | function () |
log | object | |
logIsShowing | boolean | |
appendLogOld | function | function (msg) |
appendLogEchoCmd | function | function (msg) |
logEls | object | |
appendLog | function | function (msg) |
sendbuf | object | |
isSendBufWaiting | boolean | |
sendBuffered | function | function (msg) |
sendBufferedDoNext | function | function () |
sendBufferedOnWsRecv | function | function (data) |
sendbufjson | object | |
isSendBufWaitingJson | boolean | |
clearBuffer | function | function () |
sendBufferedJson | function | function (msg) |
sendBufferedDoNextJson | function | function () |
sendBufferedOnWsRecvJson | function | function (data) |
sendFromConsole | function | function (msg) |
sendViaJson | function | function (json) |
onQueuedJson | function | function (data) |
onQueuedText | function | function (data) |
onWriteJson | function | function (data) |
onCompleteJson | function | function (data) |
onErrorJson | function | function (data) |
onBroadcast | function | function (data) |
onAnnounce | function | function (data) |
onFeedRateOverride | function | function (data) |
send | function | function (msg) |
sendNoBuf | function | function (msg) |
wsSend | function | function (msg) |
serialSaveCookie | function | function (portname, baud, isrts, isdtr, buffer) |
serialGetCookie | function | function (portname) |
serialConnect | function | function (portname, baud, buffer) |
serialDisconnect | function | function (portname) |
reconMsgShow | function | function () |
reconMsgHide | function | function () |
wsWasEverConnected | boolean | |
wsConnect | function | function (hostname, onsuccess, onfail) |
wsScan | function | function (callback, subnet) |
serverListSet | function | function (key, val) |
serverListGet | function | function () |
lastMsg | object | |
lastMsgTime | number | |
publishSysMsg | function | function (msg) |
deDupeLastMsg | object | |
isInDeDupeMode | boolean | |
publishMsg | function | function (msg) |
dataBuffer | object | |
onWsMessage | function | function (msg) |
configSendCtr | number | |
onPortOpen | function | function (data) |
onPortClose | function | function (data) |
onPortOpenFail | function | function (data) |
toSafePortName | function | function (portname) |
fromSafePortName | function | function (safeportname) |
onPlannerResumeSetup | function | function () |
onPlannerResume | function | function () |
queueMax | object | |
queueEls | object | |
sendPauseAt | number | |
sendResumeAt | number | |
isPlannerPaused | boolean | |
onUpdateQueueCnt | function | function (data) |
deviceMeta | object | |
setPortItemsFromMetaData | function | function (dm /*device meta*/, item /*port*/, portlistIndex) |
isInitting | boolean | |
onPortList | function | function (portlist) |
showAllPopovers | function | function () |
hideAllPopovers | function | function () |
onPortSetDefaultClicked | function | function (evt) |
onPortProgramClicked | function | function (evt) |
onPortConfigClicked | function | function (evt) |
onPortConfigModalSave | function | function (evt) |
currentUser | object | |
checkLogin | function | function () |
getUserDataKeysFromChiliPepprStorage | function | function () |
onCloudScriptFileClicked | function | function (evt) |
onPortFriendlyClicked | function | function (evt) |
onPortCbClicked | function | function (evt) |
bufferAlgorithms | object | |
getBufferAlgorithms | function | function () |
getBaudRates | function | function () |
onWsConnect | function | function (event) |
onWsDisconnect | function | function (event) |
statusWatcher | function | function () |
initBody | function | function (evt) |
toggleBody | function | function (evt) |
showBody | function | function (evt) |
hideBody | function | function (evt) |
forkSetup | function | function () |
ChiliPeppr is a hardware fiddle, meaning it is a website that lets you easily create a workspace to fiddle with your hardware from software. ChiliPeppr provides a Serial Port JSON Server that you run locally on your computer, or remotely on another computer, to connect to the serial port of your hardware like an Arduino or other microcontroller.
You then create a workspace at ChiliPeppr.com that connects to your hardware by starting from scratch or forking somebody else's workspace that is close to what you are after. Then you write widgets in Javascript that interact with your hardware by forking the base template widget or forking another widget that is similar to what you are trying to build.
ChiliPeppr is massively capable such that the workspaces for TinyG and Grbl CNC controllers have become full-fledged CNC machine management software used by tens of thousands.
ChiliPeppr has inspired many people in the hardware/software world to use the browser and Javascript as the foundation for interacting with hardware. The Arduino team in Italy caught wind of ChiliPeppr and now ChiliPeppr's Serial Port JSON Server is the basis for the Arduino's new web IDE. If the Arduino team is excited about building on top of ChiliPeppr, what will you build on top of it?