Navigation

    Logo
    • Register
    • Login
    • Search
    • Recent
    • Tags
    • Unread
    • Categories
    • Unreplied
    • Popular
    • GitHub
    • Docu
    • Hilfe
    1. Home
    2. Deutsch
    3. Skripten / Logik
    4. JavaScript
    5. [gelöst] MiRobot Map per Telegram

    NEWS

    • Neuer Blog: Fotos und Eindrücke aus Solingen

    • ioBroker@Smart Living Forum Solingen, 14.06. - Agenda added

    • ioBroker goes Matter ... Matter Adapter in Stable

    [gelöst] MiRobot Map per Telegram

    This topic has been deleted. Only users with topic management privileges can see it.
    • 0
      0018 last edited by 0018

      Hallo zusammen,

      ich möchte gerne meine Saugerkarte vom Sauger per Telegram versenden.
      Bin auf diesen Thread hier gestoßen.

      Leider erhalte ich bei dem Script folgenden Fehler:

      javascript.0	2019-12-03 22:29:36.526	info	(11897) Stop script script.js.common.4_MiRobot.MiRobot_Map_neu
      javascript.0	2019-12-03 22:29:33.802	error	(11897) at Script.runInContext (vm.js:133:20)
      javascript.0	2019-12-03 22:29:33.802	error	(11897) at script.js.common.4_MiRobot.MiRobot_Map_neu:226:1
      javascript.0	2019-12-03 22:29:33.801	error	(11897) at send (script.js.common.4_MiRobot.MiRobot_Map_neu:164:22)
      javascript.0	2019-12-03 22:29:33.801	error	(11897) TypeError: Cannot read property 'toBuffer' of undefined
      javascript.0	2019-12-03 22:29:33.800	error	(11897) ^
      javascript.0	2019-12-03 22:29:33.800	error	(11897) var buf = canvas.toBuffer();
      javascript.0	2019-12-03 22:29:33.798	error	(11897) script.js.common.4_MiRobot.MiRobot_Map_neu: script.js.common.4_MiRobot.MiRobot_Map_neu:164
      javascript.0	2019-12-03 22:29:33.676	info	(11897) Start javascript script.js.common.4_MiRobot.MiRobot_Map_neu
      

      hier nochmal mein Script:

      createState('vis.RockroboMap', '');
      
      var fs = require("fs");
      
      const {
         createCanvas,
         Canvas
      } = require('canvas')
      const {
         Image
      } = require('canvas')
      const request = require('request');
      const XMLHttpRequest = require("xmlhttprequest").XMLHttpRequest;
      
      //________________________________________________________________________________________________________________________________________________
      // Farben änder
      const COLOR_FLOOR = "#23465e";
      const COLOR_WALLS = "#2b2e30";
      const COLOR_PATH = "white";
      
      // Telegram
      const SENDTELEGRAM = true;
      const FINISHTEXT = 'Saugen erfolgreich beendet!'
      const ERRORTEXT = 'Beim saugen ist ein fehler aufgetreten!'
      
      //________________________________________________________________________________________________________________________________________________
      
      
      
      //Robot Image
      const rocky = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAfCAMAAAHGjw8oAAAAAXNSR0IArs4c6QAAAARnQU1BAACxjwv8YQUAAADbUExURQAAAICAgICAgICAgICAgICAgHx8fH19fX19fYCAgIGBgX5+foCAgH5+foCAgH9/f39/f35+foCAgH9/f39/f4CAgH5+foGBgYCAgICAgIGBgX9/f39/f35+foCAgH9/f39/f4CAgIODg4eHh4mJiZCQkJycnJ2dnZ6enqCgoKSkpKenp62trbGxsbKysry8vL29vcLCwsXFxcbGxsvLy87OztPT09XV1d/f3+Tk5Ojo6Ozs7O3t7e7u7vHx8fLy8vPz8/X19fb29vf39/j4+Pn5+f39/f7+/v///9yECocAAAAgdFJOUwAGChgcKCkzOT5PVWZnlJmfsLq7wcrS1Nre4OXz+vr7ZhJmqwAAAAlwSFlzAAAXEQAAFxEByibzPwAAAcpJREFUKFNlkolaWkEMhYPggliBFiwWhGOx3AqCsggI4lZt8/5P5ElmuEX5P5hMMjeZJBMRafCvUKnbIqpcioci96owTQWqP0QKC54nImUAyr9k7VD1me4YvibHlJKpVUzQhR+dmdTRSDUvdHh8NK8nhqUVch7cITmXA3rtYDmH+3OL4XI1T+BhJUcXczQxOBXJuve0/daeUr5A6g9muJzo5NI2kPKtyRSGBStKQZ5RC1hENWn6NSRTrDUqLD/lsNKoFTNRETlGMn9dDoGdoDcT1fHPi7EuUDD9dMBw4+6vMQVyInnPXDsdW+8tjWfbYTbzg/OstcagzSlb0+wL/6k+1KPhCrj6YFhzS5eXuHcYNF4bsGtDYhFLTOSMqTsx9e3iyKfynb1SK+RqtEq70RzZPwEGKwv7G0OK1QA42Y+HIgct9P3WWG9ItI/mQTgvoeuWAMdlTRclO/+Km2jwlhDvinGNbyJH6EWV84AJ1wl8JowejqTqTmv+0GqDmVLlg/wLX5Mp2rO3WRs2Zs5fznAVd1EzRh10OONr7hhhM4ctevhiVVxHdYsbq+JzHzaIfdjs5CZ9tGInSfoWEXuL7//fwtn9+Jp7wSryDjBFqnOGeuUxAAAAAElFTkSuQmCC";
      const charger = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABgAAAAYCAMAAADXqc3KAAAAdVBMVEUAAAA44Yo44Yo44Yo44Yo44Yo44Yo44Yo44Yp26q844Yr///9767Kv89DG9t2g8Md26q5C44/5/vvz/fjY+ei19NNV5ZtJ45T2/fmY78KP7r1v6atq6Kjs/PPi+u7e+uvM9+Gb8MSS7r+H7bhm6KVh56JZ5p3ZkKITAAAACnRSTlMABTr188xpJ4aepd0A4wAAANZJREFUKM9VklmCgzAMQwkQYCSmLKWl2+zL/Y9YcIUL7wvkJHIUJyKkVcyy+JIGCZILGF//QLEqlTmMdsBEXi56igfH/QVGqvXSu49+1KftCbn+dtxB5LOPfNGQNRaKaQNkTJ46OMGczZg8wJB/9TB+J3nFkyqJMp44vBrnWYhJJmOn/5uVzAotV/zACnbUtTbOpHcQzVx8kxw6mavdpYP90dsNcE5k6xd8RoIb2Xgk6xAbfm5C9NiHtxGiXD/U2P96UJunrS/LOeV2GG4wfBi241P5+NwBnAEUFx9FUdUAAAAASUVORK5CYII=";
      
      //last map
      let last_map;
      
      var canvasimg = new Canvas();
      var ctximg = canvasimg.getContext('2d');
      var res = {};
      
      var img = new Image(); // Create a new Image
      img.src = rocky
      
      const img_charger = new Image();
      img_charger.src = charger;
      
      const robotIp = "192.168.20.60"; // IP of the robot
      const robotState = "mihome-vacuum.0.info.state" // e.g : "mihome-vacuum.0.info.state"
      
      httpGetAsync("http://" + robotIp + "/api/map/latest", updateMapPage);
      
      
      // get actuel map data from Valetudo
      function httpGetAsync(theUrl, callback) {
         var xmlHttp = new XMLHttpRequest();
         var jdata = {};
         xmlHttp.onreadystatechange = function () {
             //console.log(JSON.stringify(xmlHttp));
             if (xmlHttp.readyState == 4 && xmlHttp.status == 200) {
                 try {
                     jdata = JSON.parse(xmlHttp.responseText)
                     //console.log(JSON.stringify(jdata));
                 } catch (err) {}
                 callback(jdata);
             }
      
         }
         xmlHttp.open("GET", theUrl, true); // true for asynchronous 
         xmlHttp.send(null);
      }
      
      function updateMapPage(res) {
         var canvas = createCanvas();
         var ctx = canvas.getContext('2d');
      
         let mapImageData;
         var map;
         canvas.height = 1024 * 4 //res.image.dimensions.height;
         canvas.width = 1024 * 4 //res.image.dimensions.width;
      
         // Male Boden
         if (res.image.pixels.floor && res.image.pixels.floor.length !== 0) {
             ctx.fillStyle = COLOR_FLOOR;
             res.image.pixels.floor.forEach(function (coord) {
                 ctx.fillRect(coord[0] * 4 + res.image.position.left * 4, coord[1] * 4 + res.image.position.top * 4, 4, 4);
      
             });
         }
         // Male Wände
         if (res.image.pixels.obstacle_strong && res.image.pixels.obstacle_strong.length !== 0) {
             ctx.fillStyle = COLOR_WALLS;
             res.image.pixels.obstacle_strong.forEach(function (coord) {
                 ctx.fillRect(coord[0] * 4 + res.image.position.left * 4, coord[1] * 4 + res.image.position.top * 4, 4, 4);
      
             });
         }
      
         // Male den Pfad
         if (res.path.points && res.path.points.length !== 0) {
             ctx.fillStyle = COLOR_PATH;
             let first = true;
             let cold1, cold2;
      
      
      
             res.path.points.forEach(function (coord) {
                 if (first) {
                     ctx.fillRect(coord[0] / 12.5, coord[1] / 50, 2, 2);
                     cold1 = coord[0] / 12.5;
                     cold2 = coord[1] / 12.5;
                 } else {
                     ctx.beginPath();
                     ctx.lineWidth = 1;
                     ctx.strokeStyle = "#FFFFFF";
                     ctx.moveTo(cold1, cold2);
                     ctx.lineTo(coord[0] / 12.5, coord[1] / 12.5);
                     ctx.stroke();
      
                     cold1 = coord[0] / 12.5
                     cold2 = coord[1] / 12.5
                 }
                 first = false
      
             });
         }
         // Zeichne Roboter
         ctx.beginPath();
         if (res.robot) {
             if (res.path.current_angle && typeof res.robot[0] !== "undefined" && typeof res.robot[1] !== "undefined") {
                 canvasimg = rotateRobo(img, res.path.current_angle);
                 ctx.drawImage(canvasimg, res.robot[0] / 12.5 - 15, res.robot[1] / 12.5 - 15, img.width, img.height);
             } else {
                 ctx.drawImage(img, res.robot[0] / 12.5 - 15, res.robot[1] / 12.5 - 15, img.width, img.height);
             }
         }
         // Zeichne Ladestation wenn vorhanden
         if (res.charger) {
             if (typeof res.charger[0] !== "undefined" && typeof res.charger[1] !== "undefined") {
                 ctx.beginPath();
                 ctx.drawImage(img_charger, res.charger[0] / 12.5 - 15, res.charger[1] / 12.5 - 15);
             }
         }
      
      
      
         // crop image
         let canvas_final = createCanvas();
         let ctx_final = canvas_final.getContext('2d');
         var trimmed = ctx.getImageData(res.image.position.left * 4, res.image.position.top * 4, res.image.dimensions.width * 4, res.image.dimensions.height * 4);
      
         canvas_final.height = res.image.dimensions.height * 4;
         canvas_final.width = res.image.dimensions.width * 4;
      
         ctx_final.putImageData(trimmed, 0, 0);
      
      
         map = canvas_final.toDataURL();
         last_map = canvas_final;
         setState("javascript.0.vis.RockroboMap", '<img src="' + canvas_final.toDataURL() + '" /style="width: auto ;height: 100%;">');
         //log('<img src="' + canvas_final.toDataURL() + '" />');
      }
      
      function send(canvas){
         var buf = canvas.toBuffer();
         fs.writeFile("/opt/iobroker/vac_map.png", buf, (err) => {
             if (err) throw err;
             log('The file has been saved!');
         });
      
         setTimeout(function(){
         // sendTo('telegram.0', '/opt/iobroker/vac_map.png');
             sendTo('telegram.0', {text: '/opt/iobroker/vac_map.png', caption: 'Fertig mit saugen!'});
         }, 3000);
      }
      
      function rotateRobo(img, angle) {
         var canvasimg = createCanvas(img.width, img.height);
         var ctximg = canvasimg.getContext('2d');
         const offset = 90;
      
         ctximg.clearRect(0, 0, img.width, img.height);
         ctximg.translate(img.width / 2, img.width / 2);
         ctximg.rotate((angle + offset) * Math.PI / 180);
         ctximg.translate(-img.width / 2, -img.width / 2);
         ctximg.drawImage(img, 0, 0);
         return canvasimg;
      }
      
      
      schedule("*2 * * * * *", function () {
         var robyState = getState(robotState).val;
      
         if (robyState === 5 || robyState === 11 || robyState === 17) httpGetAsync("http://" + robotIp + "/api/map/latest", updateMapPage);
      });
      
      subscribe({
         id: 'mihome-vacuum.0.info.state' ,
         change: "ne"
      }, function (obj) {
         if (SENDTELEGRAM) {
             if (obj.newState.val === 8 && obj.oldState.val !== 8) {
                 send(last_map, FINISHTEXT);
             } else if ((obj.oldState.val === 5 || obj.oldState.val === 11 || obj.oldState.val === 17) && obj.newState.val !== 6) {
                 send(last_map, ERRORTEXT);
             }
         }
      
      });
      
      

      die zusätzlichen NPM Module habe ich im Adapter hinterlegt.
      Vielleicht weis ja jemand hier weiter.... Evtl @Meistertr ?

      Danke 🙂

      1 Reply Last reply Reply Quote 0
      • 0
        0018 last edited by

        Jemand eine Idee hierzu?

        1 Reply Last reply Reply Quote 0
        • 0
          0018 last edited by

          Gelöst. Habe das Script nochmal neu aufgesetzt und siehe da... jetzt läuft es. Hatte bestimmt einen Copy & Paste Fehler.

          1 Reply Last reply Reply Quote 0
          • First post
            Last post

          Support us

          ioBroker
          Community Adapters
          Donate

          790
          Online

          31.8k
          Users

          80.0k
          Topics

          1.3m
          Posts

          1
          3
          290
          Loading More Posts
          • Oldest to Newest
          • Newest to Oldest
          • Most Votes
          Reply
          • Reply as topic
          Log in to reply
          Community
          Impressum | Datenschutz-Bestimmungen | Nutzungsbedingungen
          The ioBroker Community 2014-2023
          logo