hmkim
Published © LGPL

Remote-Controlled 8x8 LED Matrix

Remote-controlled 8x8 LED matrix in real-time by the HTML5 Websocket.

BeginnerShowcase (no instructions)8 hours11,813
Remote-Controlled 8x8 LED Matrix

Things used in this project

Story

Read more

Schematics

Connections

LED ----- PHPoC Shield
VCC ----- 5V
GND ----- GND
SDA ----- A4(SDA)
SCL ----- A5(SCL)

Code

PHPoC Shield source code

HTML
1. Upload PHPoC Shield source code
Please refert to the manual of PHPoC Debugger below and upload the source code(matrix.php).
http://www.phpoc.com/support/manual/phpoc_debugger_manual/contents.php?id=major_upload

- matrix.php
<!DOCTYPE html>
<html>
<head>
<title>PHPoC Shield - 8x8 LED Matrix for Arduino</title>
<meta name="viewport" content="width=device-width, initial-scale=0.7, maximum-scale=0.7">
<style>
body { font-family: verdana, Helvetica, Arial, sans-serif, gulim; text-align: center; }
h1 { font-weight: bold; font-size: 25pt; }
h2 { font-weight: bold; font-size: 15pt; }
#remote { margin:0 auto; width: 500px; background: #333; border-radius: 2%; }
.cell { 
        display: inline-block; width: 45px; height: 45px; 
        background: #eee; margin: 8px; border-radius: 10%;
}
</style>
<script>
var push_info = [];
var ws;
var push_length = 64;
function init()
{    
    if(ws == null)
    {
        ws = new WebSocket("ws://<?echo _SERVER("HTTP_HOST")?>/matrix", "text.phpoc");
        document.getElementById("ws_state").innerHTML = "CONNECTING";
        
        ws.onopen = ws_onopen;
        ws.onclose = ws_onclose;
        ws.onmessage = ws_onmessage; 
    }
    else
        ws.close();
    
    for(var push_id = 0; push_id < push_length; push_id++)
    {
        push_info[push_id] = {state:false, identifier:null};
        update_push(push_id, false);
    }
 
    var remote = document.getElementById("remote");
    
    remote.addEventListener("touchstart", touch_move);
    remote.addEventListener("touchmove", touch_move);
    remote.addEventListener("mousedown", mouse_down);
    remote.addEventListener("mouseover", mouse_down);
}
function connect_onclick()
{
    if(ws == null)
    {
        var ws_host_addr = "<?echo _SERVER("HTTP_HOST")?>";
        //var debug = document.getElementById("debug");
 
        if((navigator.platform.indexOf("Win") != -1) && (ws_host_addr.charAt(0) == "["))
        {
            // network resource identifier to UNC path name conversion
            ws_host_addr = ws_host_addr.replace(/[\[\]]/g, '');
            ws_host_addr = ws_host_addr.replace(/:/g, "-");
            ws_host_addr += ".ipv6-literal.net";
        }
 
        //debug.innerHTML = "<br>" + navigator.platform + " " + ws_host_addr;
        ws = new WebSocket("ws://" + ws_host_addr + "/remote_push", "text.phpoc");
 
        document.getElementById("ws_state").innerHTML = "CONNECTING";
 
        ws.onopen = ws_onopen;
        ws.onclose = ws_onclose;
        ws.onmessage = ws_onmessage;
    }
    else
        ws.close();
}
function ws_onopen()
{
    document.getElementById("ws_state").innerHTML = "<font color='blue'>CONNECTED</font>";
    document.getElementById("bt_connect").innerHTML = "Disconnect";
 
    for(var push_id = 0; push_id < push_length; push_id++)
        update_push(push_id, false);
}
function ws_onclose()
{
    document.getElementById("ws_state").innerHTML = "<font color='gray'>CLOSED</font>";
    document.getElementById("bt_connect").innerHTML = "Connect";
 
    ws.onopen = null;
    ws.onclose = null;
    ws.onmessage = null;
    ws = null;
 
    for(var push_id = 0; push_id < push_length; push_id++)
        update_push(push_id, false);
}
function ws_onmessage(e_msg)
{
    e_msg = e_msg || window.event; // MessageEvent
 
    alert("msg : " + e_msg.data);
}
function update_push(push_id, state)
{
    var button = document.getElementById(push_id);
    var push = push_info[push_id];
 
    if(ws && (ws.readyState == 1))
    {
        if(state)
            button.style.backgroundColor = "#7DFF05";
        else
            button.style.backgroundColor = "grey";
    }
    else
        button.style.backgroundColor = "#555";
 
    push.state = state;
 
    if(!state)
        push.identifier = null;
 
    if(ws && (ws.readyState == 1))
    {
        if(state)
            ws.send(Number(push_id) + "\n"); // on
        else
            ws.send(100+Number(push_id) + "\n"); // off
    }
    
}
function mouse_down(event)
{
    //var debug = document.getElementById("debug");
 
    var push_id = event.target.id;    
    
    if(event.changedTouches)
    {
        
        for(var touch_id = 0; touch_id < event.changedTouches.length; touch_id++)
        {
            var touch = event.changedTouches[touch_id];
 
            if(push_id < push_length)
            {
                var push = push_info[push_id];
 
                if(push.state == false)
                {
                    update_push(push_id, true);
                    push.identifier = touch.identifier;
 
                //    debug.innerHTML += ("+" + push_id + "/" + touch.identifier + " ");
                }
                else
                {
                    update_push(push_id, false);
                }
 
                //debug.innerHTML += (push_id + " ");
            }
        }
    }
    else
    {
        if(push_id < push_length)
        {
                var push = push_info[push_id];
                if(push.state == false)
                {
                    update_push(push_id, true);
 
                    //debug.innerHTML += ("+" + push_id + "/" + touch.identifier + " ");
                }
                else
                {
                    update_push(push_id, false);
                }
                
            //debug.innerHTML += (push_id + " ");
        }
    }
 
    event.preventDefault();
}
 
var origin_push_id = null;
function touch_move(event)
{
    var debug = document.getElementById("debug");
 
    var target = document.elementFromPoint(event.changedTouches[0].pageX, event.changedTouches[0].pageY);
     //debug.innerHTML += " " + target.id;
     
    var push_id = target.id;
      
    if(origin_push_id != push_id)
    {
        if(event.changedTouches)
        {
        
            for(var touch_id = 0; touch_id < event.changedTouches.length; touch_id++)
            {
                var touch = event.changedTouches[touch_id];
 
                if(push_id < push_length)
                {
                    var push = push_info[push_id];
 
                    if(push.state == false)
                    {
                        update_push(push_id, true);
                        push.identifier = touch.identifier;
 
                    //    debug.innerHTML += ("+" + push_id + "/" + touch.identifier + " ");
                    }
                    else
                    {
                        update_push(push_id, false);
                    }
 
                    //debug.innerHTML += (push_id + " ");
                }
            }
        }
        else
        {
            if(push_id < push_length)
            {
                    var push = push_info[push_id];
                    if(push.state == false)
                    {
                        update_push(push_id, true);
 
                        //debug.innerHTML += ("+" + push_id + "/" + touch.identifier + " ");
                    }
                    else
                    {
                        update_push(push_id, false);
                    }
                
                //debug.innerHTML += (push_id + " ");
            }
        }
        
    }
    origin_push_id = push_id;
    event.preventDefault();
}
 
window.onload = init;
</script>
</head>
 
<body>
<h1>8x8 LED Matrix</h1>
<br /><br />
<div id="remote">
<?php
    for ($i=0; $i<64; $i++)
        echo "<div class='cell' id='" . (string) $i . "'></div>";
?>
</div>
<br /><br />
<h2>WebSocket <font id="ws_state" color="gray">CLOSED</font></h2>
<button id="bt_connect" type="button" onclick="connect_onclick();">Connect</button>
<span id="debug"></span>
</body>
</html>

Arduino Source code

Arduino
2. Upload Arduino source code
- Add Arduino library
Please add releted libraries from [Sketch] > [Include Library] > [Manager Libraries...]
Adafruit_LEDBackpack library, Adafruit-GFX-Library, PHPoC Library
(Learn more : https://learn.adafruit.com/adafruit-led-backpack/bi-color-8x8-matrix)

- Upload Arduino sketch
/*************************************************** 
  This is a library for our I2C LED Backpacks

  Designed specifically to work with the Adafruit LED Matrix backpacks 
  ----> http://www.adafruit.com/products/872
  ----> http://www.adafruit.com/products/871
  ----> http://www.adafruit.com/products/870

  These displays use I2C to communicate, 2 pins are required to 
  interface. There are multiple selectable I2C addresses. For backpacks
  with 2 Address Select pins: 0x70, 0x71, 0x72 or 0x73. For backpacks
  with 3 Address Select pins: 0x70 thru 0x77

  Adafruit invests time and resources providing this open source code, 
  please support Adafruit and open-source hardware by purchasing 
  products from Adafruit!

  Written by Limor Fried/Ladyada for Adafruit Industries.  
  BSD license, all text above must be included in any redistribution
 ****************************************************/

#include <Wire.h>
#include <Adafruit_GFX.h>
#include "Adafruit_LEDBackpack.h"
#include "SPI.h"
#include "Phpoc.h"

Adafruit_BicolorMatrix matrix = Adafruit_BicolorMatrix();

PhpocServer server(80);
String ledPushId; 

void setup() {
  Serial.begin(9600);
  while(!Serial)
    ;

  Serial.println("8x8 LED Matrix Test");
  
  Phpoc.begin(PF_LOG_SPI | PF_LOG_NET);
  
  server.beginWebSocket("matrix");

  Serial.print("WebSocket server address : ");
  Serial.println(Phpoc.localIP());  
  
  matrix.begin(0x70);  // pass in the address
  matrix.setRotation(3); 
}

void loop() {
  
  // wait for a new client:
  PhpocClient client = server.available();
  
  if (client) {
      if (client.available() > 0) {
        // read the bytes incoming from the client:
        char thisChar = client.read();
        ledPushId += thisChar;
        
        if (thisChar == '\n')
        {
            ledPushId.trim();
  
            if (ledPushId.toInt() / 100 == 1) //off
            {
                int push_id = ledPushId.toInt() - 100;
                int x = push_id % 8;
                int y = push_id / 8;
                            
                matrix.drawPixel(x, y, LED_OFF);          
                matrix.writeDisplay();
            }
            else
            {
                int push_id = ledPushId.toInt();
                int x = push_id % 8;
                int y = push_id / 8;
              
                matrix.drawPixel(x, y, LED_GREEN);              
                matrix.writeDisplay();
            }
  
            ledPushId = ""; // Clear recieved buffer
        }
      }  
  }
}

Credits

hmkim

hmkim

1 project • 24 followers

Comments