{"id":559,"date":"2022-11-19T01:44:33","date_gmt":"2022-11-19T00:44:33","guid":{"rendered":"http:\/\/jimblackler.com\/blog\/?p=559"},"modified":"2022-11-19T01:44:33","modified_gmt":"2022-11-19T00:44:33","slug":"nonogram-pro-a-puzzle-game-written-in-es6typescript-for-node-js-and-the-web","status":"publish","type":"post","link":"https:\/\/jimblackler.com\/?p=559","title":{"rendered":"Nonogram Pro; a puzzle game written in ES6+Typescript for node.js and the web"},"content":{"rendered":"\n<p>I\u2019ve made a new project which is online in an App Engine instance at <a href=\"https:\/\/nonogrampro.appspot.com\/\">https:\/\/nonogrampro.appspot.com\/<\/a><\/p>\n\n\n\n<h2 class=\"wp-block-heading\">About<\/h2>\n\n\n\n<p>I\u2019m a fan of Nonogram puzzles, also known as Picross and many other names. Nonogram puzzles were invented in 1987 by Non Ishida and independently by Tetsuya Nishio. Players have to complete a grid to discover which cells are shaded based on number clues in the rows and columns. The <a href=\"https:\/\/en.wikipedia.org\/wiki\/Nonogram\" data-type=\"URL\" data-id=\"https:\/\/en.wikipedia.org\/wiki\/Nonogram\">Wikipedia article on Nonograms<\/a> is a good source of history of the puzzle type as well as information on how to play.<\/p>\n\n\n\n<p>There are many Nonogram games that can be played online. However some may know that I made a website based Solitaire game which has become modestly popular over the years. <a href=\"https:\/\/jimblackler.com\/blog\/?p=303\">https:\/\/jimblackler.com\/blog\/?p=303<\/a> People have said they appreciate the clean design with no advertisements or flashy effects that distract from the game. I thought maybe I could do the same for Nonogram puzzles.\u00a0<\/p>\n\n\n\n<figure class=\"wp-block-image size-large is-resized\"><img loading=\"lazy\" decoding=\"async\" src=\"https:\/\/jimblackler.com\/blog\/wp-content\/uploads\/2022\/11\/nono_guide-291x1024.png\" alt=\"\" class=\"wp-image-560\" width=\"222\" height=\"782\" srcset=\"https:\/\/jimblackler.com\/wp-content\/uploads\/2022\/11\/nono_guide-291x1024.png 291w, https:\/\/jimblackler.com\/wp-content\/uploads\/2022\/11\/nono_guide-85x300.png 85w, https:\/\/jimblackler.com\/wp-content\/uploads\/2022\/11\/nono_guide.png 320w\" sizes=\"auto, (max-width: 222px) 100vw, 222px\" \/><figcaption>How Nonograms are completed<\/figcaption><\/figure>\n\n\n\n<h2 class=\"wp-block-heading\">Completing the project<\/h2>\n\n\n\n<p>First something of a confession; I actually started this project in 2017. I made a lot of progress, but I must have got distracted by something, so I left it unfinished. Sadly as many tinkerers like me have found it\u2019s a lot easier to start something than it is to finish. This project was still in the back of my mind though, so I made the decision to pick it up again recently, and have successfully completed it. This just shows it\u2019s never too late to resurrect an abandoned project.<\/p>\n\n\n\n<p>I did update it to the latest tech though. It\u2019s now written in Typescript, and I converted the old Python back end to one written in Node.js. This is the tech that I\u2019m really enjoying working with these days. One advantage of using Node.js is that code can be easily shared between client and server and that can be useful for puzzle processing. This is handy for the \u2018hint\u2019 function I\u2019ve supplied with the game; it uses the same solver that is used server-side to make sure that puzzles can be completed.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">How it works<\/h2>\n\n\n\n<p>The client works by rendering the puzzle as an SVG created in script.I could have used Canvas, but using SVG handles the graphical updates efficiently and allows me to use CSS to style the puzzles.<\/p>\n\n\n\n<p>Having written the game I needed some actual puzzle designs to use. I could probably have done some drawings but I\u2019m not really that artistic and I wanted about 50 or so. I hit on the idea of creating puzzles using libraries of icon images that can be freely remixed; i.e. ones that have a Creative Commons or public domain licence. Even better if they were stored in a vector format like SVG; they could be then scaled to the Nonogram grid.<\/p>\n\n\n\n<p>This approach worked surprisingly well. My importer can iterate through whole libraries and render the images in a very large grid. It then \u2018trims\u2019 off the vertical and horizontal edges that contain no content, then shrinks the leftover image to a pattern of shaded cells of the required grid size.<\/p>\n\n\n\n<p>However you might be surprised to learn that more often than not importing an image like that would create a puzzle that either had more than one solution or that would require advanced solution techniques because they couldn\u2019t be solved one row or column at a time. That\u2019s no fun for the player, so the importer actually attempts to solve the puzzle first from the generated clues. If it\u2019s not possible to complete it using the standard set of techniques the puzzle isn\u2019t used. If it is possible to complete it, the number of rounds required to complete with the standard method becomes the \u2018difficulty\u2019 shown with the puzzle.<\/p>\n\n\n\n<figure class=\"wp-block-image size-large is-resized\"><img loading=\"lazy\" decoding=\"async\" src=\"https:\/\/jimblackler.com\/blog\/wp-content\/uploads\/2022\/11\/importer-1.png\" alt=\"\" class=\"wp-image-563\" width=\"195\" height=\"558\" srcset=\"https:\/\/jimblackler.com\/wp-content\/uploads\/2022\/11\/importer-1.png 353w, https:\/\/jimblackler.com\/wp-content\/uploads\/2022\/11\/importer-1-105x300.png 105w\" sizes=\"auto, (max-width: 195px) 100vw, 195px\" \/><figcaption>How graphics can be converted into puzzles.<\/figcaption><\/figure>\n\n\n\n<p>I then look at the generated puzzles and select the best ones to publish on the front page.<\/p>\n\n\n\n<p>I tried to include a variety of grid sized puzzles, 5&#215;5, 10&#215;10, etc. up to 30 x 30. And the import worked so well that I smashed my target of 50 puzzles. There are over 600 in the collection.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Game and editor<\/h2>\n\n\n\n<p>The game uses the browser\u2019s local storage to keep track of which puzzles you\u2019ve completed.&nbsp;<\/p>\n\n\n\n<p>I\u2019ve even included an editor so you can design and publish your own Nonogram puzzles!<\/p>\n\n\n\n<p>You can try them in your own browser, or publish them on the site. This creates a link for the puzzles that could be sent to other people so they can try them. To do that requires signing in with a Google account and selecting an author name for your puzzles.<\/p>\n\n\n\n<p>If you have generated any puzzle you\u2019re particularly pleased with, let me know by email and I\u2019ll consider adding them to the selection of puzzles that everyone sees on the front page of the site.<\/p>\n\n\n\n<p>As usual the code for my projects <a href=\"https:\/\/github.com\/jimblackler\/NonogramPro\" data-type=\"URL\" data-id=\"https:\/\/github.com\/jimblackler\/NonogramPro\">is on GitHub<\/a> so that anyone can see how it works, and made available with an open source licence. <\/p>\n","protected":false},"excerpt":{"rendered":"<p>I\u2019ve made a new project which is online in an App Engine instance at https:\/\/nonogrampro.appspot.com\/ About I\u2019m a fan of Nonogram puzzles, also known as Picross and many other names. Nonogram puzzles were invented in 1987 by Non Ishida and independently by Tetsuya Nishio. Players have to complete a grid to discover which cells are [&hellip;]<\/p>\n","protected":false},"author":2,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[1],"tags":[],"class_list":["post-559","post","type-post","status-publish","format-standard","hentry","category-uncategorized"],"_links":{"self":[{"href":"https:\/\/jimblackler.com\/index.php?rest_route=\/wp\/v2\/posts\/559","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/jimblackler.com\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/jimblackler.com\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/jimblackler.com\/index.php?rest_route=\/wp\/v2\/users\/2"}],"replies":[{"embeddable":true,"href":"https:\/\/jimblackler.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=559"}],"version-history":[{"count":3,"href":"https:\/\/jimblackler.com\/index.php?rest_route=\/wp\/v2\/posts\/559\/revisions"}],"predecessor-version":[{"id":565,"href":"https:\/\/jimblackler.com\/index.php?rest_route=\/wp\/v2\/posts\/559\/revisions\/565"}],"wp:attachment":[{"href":"https:\/\/jimblackler.com\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=559"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/jimblackler.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=559"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/jimblackler.com\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=559"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}