{"id":9165,"date":"2020-02-07T13:10:17","date_gmt":"2020-02-07T13:10:17","guid":{"rendered":"https:\/\/dev.adambowie.com\/?p=9165"},"modified":"2023-08-28T23:18:51","modified_gmt":"2023-08-28T22:18:51","slug":"magic-mirror","status":"publish","type":"post","link":"https:\/\/dev.adambowie.com\/blog\/2020\/02\/magic-mirror\/","title":{"rendered":"Magic Mirror"},"content":{"rendered":"\n<p><em>Note: Taking good photos of mirrors is very hard! This photo suggests lots of double images, but in fact they&#8217;re not visible to the human eye, and the text is nice and sharp! Nor can you see acrylic marks in the screen. Yes, the mirror still works as a mirror. And yes, I&#8217;ve intentionally blurred a portion of the screen here.<\/em><\/p>\n\n\n\n<p><em>Also note that as is the way of these things, everything here was true in January 2020 using a Raspberry Pi 3B+ with Raspbian Buster. Some elements of this may change over time!<\/em><\/p>\n\n\n\n<p>Smart mirrors or magic mirrors are pieces of mirror-glass with a screen behind them that can display data. The idea is that they provide useful information in a non-intrusive screen &#8211; you probably have mirrors hanging on your wall after all.<\/p>\n\n\n\n<p>The basis of them is a two-way mirror in front of a screen. If the screen is mostly black, with white writing, then the bright parts come through, and you get a mirror for the most part. Commonly people re-purpose old monitors to provide the screen.<\/p>\n\n\n\n<p>The latest issue of the always great MagPi magazine featured a magic mirror on the cover, and when I looked at what was needed to replicate their model, I realised that I had most of the parts already, or could get them inexpensively.<\/p>\n\n\n\n<p>MagPi magazine, incidentally, uploads free PDFs of their publications which is rather generous of them. I like to buy the print versions anyway &#8211; but find it useful to go back to PDFs later if needed.<a href=\"https:\/\/magpi.raspberrypi.org\/issues\/90\"> Issue 90 which features this project is here<\/a>. There&#8217;s a laser printed cover mounted Raspberry Pi mount (not for this project). You don&#8217;t get that with the PDF!<\/p>\n\n\n\n<p>Anyway, the design in MagPi uses a Pi (they used a 4 but I used a 3 B+), the official touchscreen (the most expensive part of this build), a \u00a33.50 IKEA Ribba frame, and a \u00a37.00 A5 sheet of two-way mirror.<\/p>\n\n\n\n<p>(Ribba frames are great for projects because of their depth. <a href=\"https:\/\/dev.adambowie.com\/2019\/08\/hack-an-ikea-ribba-frame-to-make-a-lightbox\/\">I previously used one to make a lightbox<\/a>).<\/p>\n\n\n\n<p>The whole thing uses <A HREF=\"https:\/\/magicmirror.builders\/\">MagicMirror<sup>2<\/sup><\/A> to produce a good looking display. This is an opensource modular system with various extra functionality developed by a global community.<\/p>\n\n\n\n<p>You obviously also need a micro-USB power supply and an SD card. The official power supply is white and has a mostly white cable, so I&#8217;ll use that since my mirror will be wall mounted.<\/p>\n\n\n\n<p>Obviously MagPi magazine gives you most of the information you need. I followed the instructions and I was up and running with no problems. Note that the Pi does still boot to desktop before the MagicMirror app takes over &#8211; just wait a few seconds.<\/p>\n\n\n\n<p>Here are a few things that came up for me while I was building my mirror.<\/p>\n\n\n\n<h4 class=\"wp-block-heading\">Rotate the Screen<\/h4>\n\n\n\n<p><em>Note: I originally used a Raspberry Pi 3B+ for this, and it worked. See update below for instructions for Raspberry Pi 4.<\/em><\/p>\n\n\n\n<p>I wanted my magic mirror to be portrait (or vertical) in orientation. To this, from a command line:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>sudo nano \/boot\/config.txt<\/code><\/pre>\n\n\n\n<p>Then add this line to rotate it 90 degrees:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>display_rotate=1<\/code><\/pre>\n\n\n\n<p>(Incidentally if you change <em>1<\/em> to <em>2<\/em> you get a 180 degree rotation, and if you change it to <em>3 <\/em>you get a 270 degree rotation).<\/p>\n\n\n\n<p><em>Update mid-2023: I rebuilt my MagicMirror using a Raspberry Pi 4, and the above does not work. The best route is to use the built-in &#8220;Screen Configuration&#8221; tool to reorient the screen. Either plug a keyboard and mouse in, or enable and use VNC. If MagicMirror is already up and running Ctrl-Esc should get the menu up. Then use Preferences > Screen Configuration. Select the display &#8211; DSI-1 for me.<\/em> <em>Right-hand click on it and choose Orientation > Right (in my case).<\/em><\/p>\n\n\n\n<h4 class=\"wp-block-heading\">Automatic Installation Scripts<\/h4>\n\n\n\n<p>In MagPi they give the code for an automatic installer, but when I went to the <a href=\"https:\/\/docs.magicmirror.builders\/getting-started\/installation.html#manual-installation\">Magic Mirror installation page<\/a> they state that as of the start of 2020 they&#8217;d removed the automatic installer. <\/p>\n\n\n\n<p>MagPi&#8217;s instructions are actually for an installer script, but the linked script on the installation page is actually that of a different user. <a href=\"https:\/\/github.com\/sdetweil\/MagicMirror_scripts\">So I used this version.<\/a><\/p>\n\n\n\n<h4 class=\"wp-block-heading\">Turning Off the Screensavers<\/h4>\n\n\n\n<p>You want to do this because otherwise the screen will time out. Touching the touchscreen wakes it up, but with a couple of sheets of acrylic in front of the screen, that may well not work, and in any case, you&#8217;ll be getting fingerprints all over your lovely mirror!<\/p>\n\n\n\n<p>Now what I <em>should<\/em> have done is carried on reading down the installation script page where a second script does the job for you!<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>bash -c \"$(curl -sL https:\/\/raw.githubusercontent.com\/sdetweil\/MagicMirror_scripts\/master\/screensaveroff.sh)\"<\/code><\/pre>\n\n\n\n<p>But since I did it the hard way, I&#8217;ll share what I did. I edited two different files and added the same extra lines. First:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>sudo nano \/etc\/xdg\/lxsession\/LXDE-pi\/autostart<\/code><\/pre>\n\n\n\n<p>And add:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>@xset s noblank\n@xset s off\n@xset -dpms<\/code><\/pre>\n\n\n\n<p>Then I edited the very similar:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>sudo nano \/etc\/xdg\/lxsession\/LXDE\/autostart<\/code><\/pre>\n\n\n\n<p>And I added the same lines as above. I <em>think<\/em> only the first changes need to be made, but I changed both and it works for me! In any case, running the script above may be easier.<\/p>\n\n\n\n<h4 class=\"wp-block-heading\">Editing the MagicMirror Configuration File<\/h4>\n\n\n\n<p>What actually gets displayed in MagicMirror comes via the configuration file. To edit it type:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>nano \/home\/pi\/MagicMirror\/config\/config.js<\/code><\/pre>\n\n\n\n<p>The installation script should have put a sample version in there. It&#8217;s then a question of editing that file to get things to work. Instructions are in the <a href=\"https:\/\/docs.magicmirror.builders\/getting-started\/configuration.html#raspberry-specific\">MagicMirror documentation<\/a>.<\/p>\n\n\n\n<p>I always find it useful to &#8220;comment out&#8221; unwanted sections of the code rather than just deleting them. I can then easily un-comment them if I want them back. Use \/\/ at the start of a line to comment it out. In the Nano editor, the code will turn blue to indicate comments.<\/p>\n\n\n\n<p>For example, I commented out the whole of the the &#8220;Compliments&#8221; module:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>\/\/       {\n\/\/             module: \"compliments\",\n\/\/             position: \"lower_third\"\n\/\/       },<\/code><\/pre>\n\n\n\n<p>That turns off the annoying &#8220;You look sexy today&#8221; lines that rotate across the mirror!<\/p>\n\n\n\n<h4 class=\"wp-block-heading\">Adding A News Feed<\/h4>\n\n\n\n<p>The default news feed at the bottom was fine, using the New York Times&#8217; RSS feed. But note that while the MagicMirror documentation tells you how to add extra feeds, <a href=\"https:\/\/docs.magicmirror.builders\/modules\/newsfeed.html#screenshot\">the example for the BBC feed is outdated<\/a>. I used  <a href=\"http:\/\/feeds.bbci.co.uk\/news\/rss.xml\">http:\/\/feeds.bbci.co.uk\/news\/rss.xml<\/a>  for BBC News Top Stories.<\/p>\n\n\n\n<h4 class=\"wp-block-heading\">Fixing the Calendar<\/h4>\n\n\n\n<p>The default set-up includes a calendar, but to show it working, the system uses a calendar of US public holidays. The problem is that the default *.ics file is now defunct. Either way, you probably don&#8217;t want that list in particular. Just go ahead and get an ics link to your calendar from something like Google Calendars (Settings &gt; Settings for my Calendars &gt; [Select calendar if you have more than one] &gt; Integrate calendar &gt; Secret address in iCal format) and paste that into the config file.<\/p>\n\n\n\n<h4 class=\"wp-block-heading\">Setting Up Weather<\/h4>\n\n\n\n<p>The default config file has weather set up, but you do need to <a href=\"https:\/\/openweathermap.org\/api\">register for an API<\/a>. This all seems to be free incidentally. <\/p>\n\n\n\n<p>Getting set up is all very painless, but as their confirmation emails state, it does take a couple of hours before your API is live. What this means is that even when you cut and paste your various API numbers into the code, weather won&#8217;t work instantly. Just wait a few hours!<\/p>\n\n\n\n<h4 class=\"wp-block-heading\">Transport<\/h4>\n\n\n\n<p>I also registered for with <a href=\"https:\/\/developer.transportapi.com\/\">TransportAPI<\/a> because &#8211; you guessed it &#8211; I want train times (and bus times) on here.<\/p>\n\n\n\n<p>There are two modules to do that. <a href=\"https:\/\/github.com\/nwootton\/MMM-UKNationalRail\">MMM-UKNationalRail<\/a> can get you train times, and <a href=\"https:\/\/github.com\/nwootton\/MMM-UKLiveBusStopInfo\">MMM-UKLiveBusStopInfo<\/a> can (sort of) get you bus times. <\/p>\n\n\n\n<p>The slight problem is that the author of both is no longer using MagicMirror and so isn&#8217;t maintaining them. That said, they both seem to work, and the instructions are clear and concise.<\/p>\n\n\n\n<p>For the rail module, the sample code shows you how to get everything working with your TransportAPI details. The only other thing you need to add is your stations&#8217; CRS code. These can be found on the web &#8211; <a href=\"https:\/\/www.nationalrail.co.uk\/stations_destinations\/48541.aspx\">here&#8217;s a link to a National Rail list<\/a>.<\/p>\n\n\n\n<p>The issue with the bus code is that by default it doesn&#8217;t have live timings. To do that requires the NextBus API which the author says is expensive. <a href=\"https:\/\/www.travelinedata.org.uk\/traveline-open-data\/nextbuses-api\/\">I went and had a look<\/a>, and it seems to be free for the first 180,000 calls in six months, and then \u00a30.96 per 1000 calls. That would seem to be OK, but I realise that one call per minute would exceed 180,000 over six months.<\/p>\n\n\n\n<p>So as things stand, I only have the expected bus <em>times<\/em> and not realtime departures.<\/p>\n\n\n\n<p>The other thing you need to know for your bus times, is your bus stop&#8217;s ATCO code. In London you can find this by visiting <a href=\"https:\/\/tfl.gov.uk\/travel-information\/stations-stops-and-piers\/\">TFL&#8217;s stations, stops and piers site<\/a>. Select buses, then pick a bus number that goes to the stop you want. This should list all the stops on the route. Click on the arrow to the right, and you&#8217;ll get live bus times for that stop. And in the URL you will see a code &#8211; that for London begins 490xxxxxxx. That&#8217;s your stop&#8217;s ATCO code.<\/p>\n\n\n\n<p>If you&#8217;re <em>outside<\/em> London, then you need to first find your ATCO prefix by <a href=\"http:\/\/naptan.app.dft.gov.uk\/Reports\/frmStopsSummaryReport\">clicking here and finding your authority area<\/a>. For example, if you live in Cambridgeshire your code is 050. The visit <a href=\"http:\/\/naptan.app.dft.gov.uk\/datarequest\/help\">here<\/a> and look for the &#8216;NaPTAN data by local authority.&#8217; You want the CSV file, and you need to adjust the link to include your code. So for Cambridgeshire it would be:  <a href=\"http:\/\/naptan.app.dft.gov.uk\/DataRequest\/Naptan.ashx?format=csv&amp;LA=050\">http:\/\/naptan.app.dft.gov.uk\/DataRequest\/Naptan.ashx?format=csv&amp;LA=050<\/a> <\/p>\n\n\n\n<p>That should give you a ZIP file within another ZIP file. Finally you should have a list of CSV files &#8211; one of which is Stops.csv. Open that up in spreadsheet or text editor, and you will have a long list of all the stops in your area (nearly 4000 in Cambridgeshire). Identify your stop, and the code you want is in the first column. Phew!<\/p>\n\n\n\n<p><em>Update mid-2023: I&#8217;ll be honest, and say that I removed all of this in my revised version. The data provider wanted money, and it just wasn&#8217;t worth the effort in trying to keep it updated.<\/em><\/p>\n\n\n\n<p><strong>Zoom Level<\/strong> <strong>[Update]<\/strong><\/p>\n\n\n\n<p>I didn&#8217;t mention this previously, and it&#8217;s important if you&#8217;re using similar sized screens to me. You may well want to change the zoom level of the browser to make fonts bigger\/smaller. The easiest way is to either:<\/p>\n\n\n\n<p>a) Plug in a mouse and keyboard and use Ctrl +\/- to set the zoom level<\/p>\n\n\n\n<p>b) Use VNC to do the same. (You will need to go into the Raspberry Pi 4 and turn on VNC. I used SSH via PuTTY and ran <strong>sudo raspi-config<\/strong>. Then I went into <strong>3 Interface Options<\/strong> and then <strong>I3 VNC <\/strong>which I enabled. That allows me to connect with VNC Viewer on my PC.)<\/p>\n\n\n\n<p>Either way, I did find that while Ctrl- worked to make the font smaller, sometimes Ctrl+ <em>didn&#8217;t<\/em>! If you end up going too small, use Ctrl 0 to reset the zoom level.<\/p>\n\n\n\n<h4 class=\"wp-block-heading\">Still To Do<\/h4>\n\n\n\n<p>There are some things that I still need to sort out. <\/p>\n\n\n\n<p>While the IKEA Ribba frame does encompass the Pi and screen without running into space issues, I found that the GPIO jumper cables&#8217; hoods &#8211; that is, the plastic elements that slide onto the Raspberry Pi&#8217;s pins &#8211; are too deep, and they extend beyond the back of the frame.<\/p>\n\n\n\n<p>So far I&#8217;ve not found any &#8220;stubby hood&#8221; jumper cables, so my workaround is likely to be some of these <a href=\"https:\/\/thepihut.com\/products\/adafruit-small-alligator-clip-to-female-jumper-wire-bundle-6-pieces-ada4304\">Adafruit jumper cables<\/a> with little alligator clips. I&#8217;m hoping I can use these in a way that I can mount the frame firmly to the wall. <\/p>\n\n\n\n<p>I plan to use <a href=\"https:\/\/amzn.to\/2H1LHaj\">Command Strips<\/a> to attach the frame to the wall. <\/p>\n\n\n\n<p>Finally, I still want to try to use Crontab to turn off the screen when I&#8217;m not around or using it. E.g. Overnight, and during weekdays when I&#8217;m out.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Note: Taking good photos of mirrors is very hard! This photo suggests lots of double images, but in fact they&#8217;re not visible to the human eye, and the text is nice and sharp! Nor can you see acrylic marks in the screen. Yes, the mirror still works as a mirror. And yes, I&#8217;ve intentionally blurred [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":9171,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[11,9],"tags":[1003,921],"amp_enabled":true,"_links":{"self":[{"href":"https:\/\/dev.adambowie.com\/blog\/wp-json\/wp\/v2\/posts\/9165"}],"collection":[{"href":"https:\/\/dev.adambowie.com\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/dev.adambowie.com\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/dev.adambowie.com\/blog\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/dev.adambowie.com\/blog\/wp-json\/wp\/v2\/comments?post=9165"}],"version-history":[{"count":8,"href":"https:\/\/dev.adambowie.com\/blog\/wp-json\/wp\/v2\/posts\/9165\/revisions"}],"predecessor-version":[{"id":77819,"href":"https:\/\/dev.adambowie.com\/blog\/wp-json\/wp\/v2\/posts\/9165\/revisions\/77819"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/dev.adambowie.com\/blog\/wp-json\/wp\/v2\/media\/9171"}],"wp:attachment":[{"href":"https:\/\/dev.adambowie.com\/blog\/wp-json\/wp\/v2\/media?parent=9165"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/dev.adambowie.com\/blog\/wp-json\/wp\/v2\/categories?post=9165"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/dev.adambowie.com\/blog\/wp-json\/wp\/v2\/tags?post=9165"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}