Просмотр исходного кода

add html extra for webusb example

hathach 4 лет назад
Родитель
Сommit
b5d218e684

+ 1 - 1
README.rst

@@ -122,7 +122,7 @@ in your project.
 .. |Build Status| image:: https://github.com/hathach/tinyusb/workflows/Build/badge.svg
    :target: https://github.com/hathach/tinyusb/actions
 .. |Documentation Status| image:: https://readthedocs.org/projects/tinyusb/badge/?version=latest
-   :target: https://openinput.readthedocs.io/en/latest/?badge=latest
+   :target: https://tinyusb.readthedocs.io/en/latest/?badge=latest
 .. |License| image:: https://img.shields.io/badge/license-MIT-brightgreen.svg
    :target: https://opensource.org/licenses/MIT
 

+ 3 - 0
docs/conf.py

@@ -39,4 +39,7 @@ html_theme_options = {
     'sidebar_hide_name': True,
 }
 
+# examples for webusb
+html_extra_path = ['html_extra']
+
 todo_include_todos = True

+ 107 - 0
docs/html_extra/examples/webusb-serial/application.css

@@ -0,0 +1,107 @@
+.main-content {
+  width: 1440px;
+  margin: auto;
+  font-size: 14px;
+}
+
+.connect-container {
+  margin: 20px 0;
+}
+
+.container {
+  display: flex;
+}
+
+.sender, .receiver {
+  flex: 1;
+}
+
+.sender {
+  margin-right: 8px;
+}
+
+.receiver {
+  margin-left: 8px;
+}
+
+.lines-header {
+  height: 30px;
+  width: 100%;
+  box-sizing: border-box;
+  background-color: #444;
+  line-height: 30px;
+  color: white;
+  padding-left: 10px;
+}
+
+.lines-body {
+  width: 100%;
+  background-color: #222;
+  min-height: 300px;
+  padding: 10px 0 20px 0;
+}
+
+.line, .command-line {
+  box-sizing: border-box;
+  width: 100%;
+  color: #f1f1f1;
+  background-color: #222;
+  outline: none;
+  border: none;
+  padding: 5px 10px;
+  font-size: 14px;
+}
+
+.line:hover {
+   background-color: #444;
+}
+
+.button::before {
+    -webkit-border-radius: 3px;
+    -moz-border-radius: 3px;
+    -webkit-box-shadow: #959595 0 2px 5px;
+    -moz-box-shadow: #959595 0 2px 5px;
+    border-radius: 3px;
+    box-shadow: #959595 0 2px 5px;
+    content: "";
+    display: block;
+    left: 0;
+    padding: 2px 0 0;
+    position: absolute;
+    top: 0;
+}
+
+.button:active::before { padding: 1px 0 0; }
+
+.button.black {
+    background: #656565;
+    background: -webkit-gradient(linear, 0 0, 0 bottom, from(#656565), to(#444));
+    background: -moz-linear-gradient(#656565, #444);
+    background: linear-gradient(#656565, #444);
+    border: solid 1px #535353;
+    border-bottom: solid 3px #414141;
+    box-shadow: inset 0 0 0 1px #939393;
+    color: #fff;
+    text-shadow: 0 1px 0 #2f2f2f;
+    padding: 8px 16px;
+    outline: none;
+}
+
+.button.black:hover {
+    background: #4c4c4c;
+    background: -webkit-gradient(linear, 0 0, 0 bottom, from(#4c4c4c), to(#565656));
+    background: -moz-linear-gradient(#4c4c4c, #565656);
+    background: linear-gradient(#4c4c4c, #565656);
+    border: solid 1px #464646;
+    border-bottom: solid 3px #414141;
+    box-shadow: inset 0 0 0 1px #818181;
+}
+
+.button.black:active {
+    background: #474747;
+    background: -webkit-gradient(linear, 0 0, 0 bottom, from(#474747), to(#444));
+    background: -moz-linear-gradient(#474747, #444);
+    background: linear-gradient(#474747, #444);
+    border: solid 1px #2f2f2f;
+    box-shadow: inset 0 10px 15px 0 #3e3e3e;
+}

+ 90 - 0
docs/html_extra/examples/webusb-serial/application.js

@@ -0,0 +1,90 @@
+(function() {
+  'use strict';
+
+  document.addEventListener('DOMContentLoaded', event => {
+    let connectButton = document.querySelector("#connect");
+    let statusDisplay = document.querySelector('#status');
+    let port;
+
+    function addLine(linesId, text) {
+      var senderLine = document.createElement("div");
+      senderLine.className = 'line';
+      var textnode = document.createTextNode(text);
+      senderLine.appendChild(textnode);
+      document.getElementById(linesId).appendChild(senderLine);
+      return senderLine;
+    }
+
+    let currentReceiverLine;
+
+    function appendLine(linesId, text) {
+      if (currentReceiverLine) {
+        currentReceiverLine.innerHTML =  currentReceiverLine.innerHTML + text;
+      } else {
+        currentReceiverLine = addLine(linesId, text);
+      }
+    }
+
+    function connect() {
+      port.connect().then(() => {
+        statusDisplay.textContent = '';
+        connectButton.textContent = 'Disconnect';
+
+        port.onReceive = data => {
+          let textDecoder = new TextDecoder();
+          console.log(textDecoder.decode(data));
+          if (data.getInt8() === 13) {
+            currentReceiverLine = null;
+          } else {
+            appendLine('receiver_lines', textDecoder.decode(data));
+          }
+        };
+        port.onReceiveError = error => {
+          console.error(error);
+        };
+      }, error => {
+        statusDisplay.textContent = error;
+      });
+    }
+
+    connectButton.addEventListener('click', function() {
+      if (port) {
+        port.disconnect();
+        connectButton.textContent = 'Connect';
+        statusDisplay.textContent = '';
+        port = null;
+      } else {
+        serial.requestPort().then(selectedPort => {
+          port = selectedPort;
+          connect();
+        }).catch(error => {
+          statusDisplay.textContent = error;
+        });
+      }
+    });
+
+    serial.getPorts().then(ports => {
+      if (ports.length === 0) {
+        statusDisplay.textContent = 'No device found.';
+      } else {
+        statusDisplay.textContent = 'Connecting...';
+        port = ports[0];
+        connect();
+      }
+    });
+
+
+    let commandLine = document.getElementById("command_line");
+
+    commandLine.addEventListener("keypress", function(event) {
+      if (event.keyCode === 13) {
+        if (commandLine.value.length > 0) {
+          addLine('sender_lines', commandLine.value);
+          commandLine.value = '';
+        }
+      }
+
+      port.send(new TextEncoder('utf-8').encode(String.fromCharCode(event.which || event.keyCode)));
+    });
+  });
+})();

+ 33 - 0
docs/html_extra/examples/webusb-serial/index.html

@@ -0,0 +1,33 @@
+<!DOCTYPE html>
+<html>
+  <head>
+    <title>TinyUSB</title>
+    <script src="serial.js"></script>
+    <script src="application.js"></script>
+    <link rel="stylesheet" href="application.css">
+  </head>
+  <body>
+    <div class="main-content">
+      <h1>TinyUSB - WebUSB Serial Example</h1>
+      <div class="connect-container">
+        <button id="connect" class="button black">Connect</button>
+        <span id="status"></span>
+      </div>
+      <div class="container">
+        <div class="sender">
+          <div class="lines-header">Sender</div>
+          <div class="lines-body">
+            <div id="sender_lines" class="lines"></div>
+            <input id="command_line" class="command-line" placeholder="Start typing ...." />
+          </div>
+        </div>
+        <div class="receiver">
+          <div class="lines-header">Receiver</div>
+          <div class="lines-body">
+            <div id="receiver_lines" class="lines"></div>
+          </div>
+        </div>
+      </div>
+    </div>
+  </body>
+</html>

+ 89 - 0
docs/html_extra/examples/webusb-serial/serial.js

@@ -0,0 +1,89 @@
+var serial = {};
+
+(function() {
+  'use strict';
+
+  serial.getPorts = function() {
+    return navigator.usb.getDevices().then(devices => {
+      return devices.map(device => new serial.Port(device));
+    });
+  };
+
+  serial.requestPort = function() {
+    const filters = [
+      { 'vendorId': 0x239A }, // Adafruit boards
+      { 'vendorId': 0xcafe }, // TinyUSB example
+    ];
+    return navigator.usb.requestDevice({ 'filters': filters }).then(
+      device => new serial.Port(device)
+    );
+  }
+
+  serial.Port = function(device) {
+    this.device_ = device;
+    this.interfaceNumber = 0;
+    this.endpointIn = 0;
+    this.endpointOut = 0;
+  };
+
+  serial.Port.prototype.connect = function() {
+    let readLoop = () => {
+      this.device_.transferIn(this.endpointIn, 64).then(result => {
+        this.onReceive(result.data);
+        readLoop();
+      }, error => {
+        this.onReceiveError(error);
+      });
+    };
+
+    return this.device_.open()
+        .then(() => {
+          if (this.device_.configuration === null) {
+            return this.device_.selectConfiguration(1);
+          }
+        })
+        .then(() => {
+          var interfaces = this.device_.configuration.interfaces;
+          interfaces.forEach(element => {
+            element.alternates.forEach(elementalt => {
+              if (elementalt.interfaceClass==0xFF) {
+                this.interfaceNumber = element.interfaceNumber;
+                elementalt.endpoints.forEach(elementendpoint => {
+                  if (elementendpoint.direction == "out") {
+                    this.endpointOut = elementendpoint.endpointNumber;
+                  }
+                  if (elementendpoint.direction=="in") {
+                    this.endpointIn =elementendpoint.endpointNumber;
+                  }
+                })
+              }
+            })
+          })
+        })
+        .then(() => this.device_.claimInterface(this.interfaceNumber))
+        .then(() => this.device_.selectAlternateInterface(this.interfaceNumber, 0))
+        .then(() => this.device_.controlTransferOut({
+            'requestType': 'class',
+            'recipient': 'interface',
+            'request': 0x22,
+            'value': 0x01,
+            'index': this.interfaceNumber}))
+        .then(() => {
+          readLoop();
+        });
+  };
+
+  serial.Port.prototype.disconnect = function() {
+    return this.device_.controlTransferOut({
+            'requestType': 'class',
+            'recipient': 'interface',
+            'request': 0x22,
+            'value': 0x00,
+            'index': this.interfaceNumber})
+        .then(() => this.device_.close());
+  };
+
+  serial.Port.prototype.send = function(data) {
+    return this.device_.transferOut(this.endpointOut, data);
+  };
+})();