<?xml version="1.0" encoding="utf-8"?><feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en"><generator uri="https://jekyllrb.com/" version="4.4.1">Jekyll</generator><link href="https://www.kogics.net/feed.xml" rel="self" type="application/atom+xml"/><link href="https://www.kogics.net/" rel="alternate" type="text/html" hreflang="en"/><updated>2026-01-16T05:22:10+00:00</updated><id>https://www.kogics.net/feed.xml</id><title type="html">blank</title><subtitle>The Kogics Foundation Website. Kojo plus more... </subtitle><entry><title type="html">Celebrating the life of Shri. J. C. Pant</title><link href="https://www.kogics.net/blog/2025/jcpant/" rel="alternate" type="text/html" title="Celebrating the life of Shri. J. C. Pant"/><published>2025-06-30T06:39:00+00:00</published><updated>2025-06-30T06:39:00+00:00</updated><id>https://www.kogics.net/blog/2025/jcpant</id><content type="html" xml:base="https://www.kogics.net/blog/2025/jcpant/"><![CDATA[<div class="float-right ml-3 mb-1"> <figure> <picture> <source class="responsive-img-srcset" media="(max-width: 480px)" srcset="/assets/img/blog/jcpant-480.webp"/> <source class="responsive-img-srcset" media="(max-width: 800px)" srcset="/assets/img/blog/jcpant-800.webp"/> <source class="responsive-img-srcset" media="(max-width: 1400px)" srcset="/assets/img/blog/jcpant-1400.webp"/> <img src="/assets/img/blog/jcpant.jpeg" class="img-fluid rounded z-depth-1" width="300" height="auto" data-zoomable="" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture><figcaption class="caption"></figcaption> </figure> </div> <p>Kogics Foundation would like to celebrate the life of Shri J. C. Pant, who gave up his body and left for his onward journey on 13 th. June, 2025. Sh. Pant was the father of our Managing Trustee Lalit Pant, and inspired Lalit from a very early age to <em>think for himself</em> and <em>figure things out for himself</em>. This led Lalit on a lifelong journey of self-learning and the creation of many software products, and in time led to the creation of <a href="/kojo">Kojo</a> and the Kogics Foundation. Shri Pant was a pillar of support during this entire journey.</p> <p>Sh. Pant was a retired IAS officer (1961 batch), who held important positions in the Govt. of Uttar Pradesh (as Principal Secretary) and the Govt. of India (as Secretary). His notable contributions to Bharat include seminal work in the areas of Education – as Education Secretary of UP, water utilisation and Watershed Development – as Agriculture Secretary of India, Polio Eradication (via Pulse Polio immunization) – as Health and Family Welfare Secretary of India, and Disaster Management – as Chairman of the High-Power-Committee on Disaster Management constituted by Sh. Atal Bihari Bajpai, PM of India. He was also the Chairman of the Administrative Reforms Commision (ARC) of the newly created state of Uttarakhand.</p> <p>Sh. Pant was born in Almora, moved to Mussoorie at a young age, and studied till class 10 at the Hindi-medium Ghananand Inter-college. He then moved to the English-medium St. George’s school for classes 11 and 12. During this period of difficult transition in his education, he came in contact with Swami Bhramananda Saraswati, Shankaracharya of Badrinath (who gave Diksha to Sh. J. C. Pant’s father Sh. T. C. Pant). The satsang and blessings of Swami Bhramananda Saraswati changed the course of his life, got him going on the path of spiritual development, and inspired him to work hard and do well in his studies at St. George’s school. From a second division result in the grade 10 board exam at Ghananand Inter-college, he improved to being the topper in his grade 12 board exam at St. George’s school. From there he went on to Allahabad University to do a BSc and MSc in Math. After he finished his MSc studies, he had a year to spare before he could appear for the IAS exam, and he spent this year learning mountaineering at the National Institute of Mountaineering at Uttarkashi (basic course) and Darjeeling (advanced course). During this time, he climbed various peaks in the Himalayas as part of mountaineering expeditions from these Institutes.</p> <p>Sh. Pant then appeared for the IAS exams, was selected, and started his journey as a bureaucrat in 1961. He came in contact with Pandit Shriram Sharma Acharya in 1979. His first meeting with Acharyaji made a huge impact on him. In his own words:</p> <div class="float-right ml-3 mb-1"> <figure> <picture> <source class="responsive-img-srcset" media="(max-width: 480px)" srcset="/assets/img/blog/jcp-ap-acharyaji-480.webp"/> <source class="responsive-img-srcset" media="(max-width: 800px)" srcset="/assets/img/blog/jcp-ap-acharyaji-800.webp"/> <source class="responsive-img-srcset" media="(max-width: 1400px)" srcset="/assets/img/blog/jcp-ap-acharyaji-1400.webp"/> <img src="/assets/img/blog/jcp-ap-acharyaji.png" class="img-fluid rounded z-depth-1" width="400" height="auto" data-zoomable="" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture><figcaption class="caption"></figcaption> </figure> </div> <p>“During the meeting with Acharyasri, which may have been for about an hour, I seemed to be completely oblivious of the passage of time. I was experiencing a strange kind of elation mixed with disbelief whether what I was going through was real. The sense of elation seemed to be due to a subtle awareness that I had finally reached my destination, and the disbelief was due to a feeling that how could I possibly be so lucky as to be face to face with someone I could look up to as my master, my Guru. I was clearly overwhelmed by his presence without being overawed, and whatever I was experiencing was very pleasant and subtle. This awareness of his benevolent presence was to be my constant companion at all times, and is so to this day”.</p> <p>He went on to accept Acharyaji as his Guru, and with Acharyaji’s guidance and the support of his organization Shanti-Kunj, carried out many impactful programs for the betterment of Bharat via the machinery of the UP government. Sh. J. C. Pant’s ideas and body of work are being ably carried forward by REACHA, an NGO that he created in 1992.</p> <p>For more information on Sh. J. C. Pant’s life, you can download his book – <a href="https://www.reacha.org/Publications/panditsriramsharma">Pandit Sriram Sharma Acharya As I knew Him … The Memoirs of A Civil Servant</a>.</p> <p>Kogics Foundation, inspired by Sh. J. C. Pant’s words and his life, is commited to doing original/creative research, product development, and action – for the betterment of Bharat and the rest of the World.</p> <p>Om Shanti . Om Sadgati</p>]]></content><author><name></name></author><summary type="html"><![CDATA[]]></summary></entry><entry><title type="html">New Kojo Release — 2.9.27, plus more…</title><link href="https://www.kogics.net/blog/2023/kojo-release-2_9_27/" rel="alternate" type="text/html" title="New Kojo Release — 2.9.27, plus more…"/><published>2023-11-20T06:39:00+00:00</published><updated>2023-11-20T06:39:00+00:00</updated><id>https://www.kogics.net/blog/2023/kojo-release-2_9_27</id><content type="html" xml:base="https://www.kogics.net/blog/2023/kojo-release-2_9_27/"><![CDATA[<p>I’m pleased to announce a new release of Kojo. The following are the highlights (for Kojo and the activities around it) since the last announcement:</p> <ul id="markdown-toc"> <li><a href="#functional-gaming" id="markdown-toc-functional-gaming">Functional gaming</a></li> <li><a href="#object-oriented-gaming-with-kojo-gaming" id="markdown-toc-object-oriented-gaming-with-kojo-gaming">Object-oriented gaming with kojo-gaming</a></li> <li><a href="#kojo-ai" id="markdown-toc-kojo-ai">kojo-ai</a></li> <li><a href="#kojo-music" id="markdown-toc-kojo-music">kojo-music</a></li> <li><a href="#picture-clipping-and-masking" id="markdown-toc-picture-clipping-and-masking">Picture clipping and masking</a></li> <li><a href="#other-miscellaneous-enhancements" id="markdown-toc-other-miscellaneous-enhancements">Other miscellaneous enhancements</a></li> </ul> <hr/> <h3 id="functional-gaming">Functional gaming</h3> <p>Let’s start with a simple animation that runs via the <code class="language-plaintext highlighter-rouge">animateWithRedraw</code> command:</p> <div class="language-scala highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nf">cleari</span><span class="o">()</span>

<span class="k">case</span> <span class="k">class</span> <span class="nc">Model</span><span class="o">(</span><span class="n">n</span><span class="k">:</span> <span class="kt">Int</span><span class="o">)</span>

<span class="k">def</span> <span class="nf">initState</span> <span class="k">=</span> <span class="nc">Model</span><span class="o">(</span><span class="mi">1</span><span class="o">)</span>
<span class="k">def</span> <span class="nf">update</span><span class="o">(</span><span class="n">m</span><span class="k">:</span> <span class="kt">Model</span><span class="o">)</span> <span class="k">=</span> <span class="nv">m</span><span class="o">.</span><span class="py">copy</span><span class="o">(</span><span class="n">n</span> <span class="k">=</span> <span class="nv">m</span><span class="o">.</span><span class="py">n</span> <span class="o">+</span> <span class="mi">1</span><span class="o">)</span>
<span class="k">def</span> <span class="nf">view</span><span class="o">(</span><span class="n">m</span><span class="k">:</span> <span class="kt">Model</span><span class="o">)</span> <span class="k">=</span> <span class="nv">Picture</span><span class="o">.</span><span class="py">text</span><span class="o">(</span><span class="nv">m</span><span class="o">.</span><span class="py">n</span><span class="o">,</span> <span class="mi">30</span><span class="o">)</span>

<span class="nf">animateWithRedraw</span><span class="o">(</span><span class="n">initState</span><span class="o">,</span> <span class="n">update</span><span class="o">,</span> <span class="n">view</span><span class="o">)</span>
</code></pre></div></div> <p>With <code class="language-plaintext highlighter-rouge">animateWithRedraw</code>, you need to define the following:</p> <ul> <li>The state of your animation (i.e. the stuff that changes as your animation runs) – defined here via a <code class="language-plaintext highlighter-rouge">Model</code> case class.</li> <li>an <code class="language-plaintext highlighter-rouge">init</code> function that returns your initial state.</li> <li>an <code class="language-plaintext highlighter-rouge">update</code> function that returns the next state given the previous state.</li> <li>a <code class="language-plaintext highlighter-rouge">view</code> function that returns a picture given a state (the picture is the visual representation of the state).</li> </ul> <p>The animation is defined in a purely functional way with the above. To run it and show it on the screen, you call the <code class="language-plaintext highlighter-rouge">animateWithRedraw</code> command, passing it the <code class="language-plaintext highlighter-rouge">init</code>, <code class="language-plaintext highlighter-rouge">update</code>, and <code class="language-plaintext highlighter-rouge">view</code> functions.</p> <p>As the animation runs, it increments a counter in the center of the screen (do you see why?).</p> <p>Now, what you need (in general) to convert an animation into a game is <em>interactivity</em>, so that messages (like key presses and mouse clicks) from outside can get into your program, enabling you to react to them.</p> <p>Let’s do a simple cut of this with our animation above. Let’s just make the increasing counter move left/right on key presses, until it moves more than 100 pixels away from the origin:</p> <div class="language-scala highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nf">cleari</span><span class="o">()</span>
<span class="k">val</span> <span class="nv">speed</span> <span class="k">=</span> <span class="mi">5</span>
<span class="k">val</span> <span class="nv">limit</span> <span class="k">=</span> <span class="mi">100</span>

<span class="k">case</span> <span class="k">class</span> <span class="nc">Model</span><span class="o">(</span><span class="n">n</span><span class="k">:</span> <span class="kt">Int</span><span class="o">,</span> <span class="n">x</span><span class="k">:</span> <span class="kt">Double</span><span class="o">,</span> <span class="n">y</span><span class="k">:</span> <span class="kt">Double</span><span class="o">)</span>

<span class="k">trait</span> <span class="nc">Msg</span>
<span class="k">case</span> <span class="k">object</span> <span class="nc">Tick</span> <span class="k">extends</span> <span class="nc">Msg</span>
<span class="k">case</span> <span class="k">object</span> <span class="nc">Left</span> <span class="k">extends</span> <span class="nc">Msg</span>
<span class="k">case</span> <span class="k">object</span> <span class="nc">Right</span> <span class="k">extends</span> <span class="nc">Msg</span>
<span class="k">case</span> <span class="k">object</span> <span class="nc">Still</span> <span class="k">extends</span> <span class="nc">Msg</span>

<span class="k">def</span> <span class="nf">initState</span> <span class="k">=</span> <span class="nc">Model</span><span class="o">(</span><span class="mi">1</span><span class="o">,</span> <span class="mi">0</span><span class="o">,</span> <span class="mi">0</span><span class="o">)</span>

<span class="k">def</span> <span class="nf">update</span><span class="o">(</span><span class="n">m</span><span class="k">:</span> <span class="kt">Model</span><span class="o">,</span> <span class="n">msg</span><span class="k">:</span> <span class="kt">Msg</span><span class="o">)</span> <span class="k">=</span> <span class="n">msg</span> <span class="k">match</span> <span class="o">{</span>
    <span class="k">case</span> <span class="nc">Tick</span> <span class="k">=&gt;</span>
        <span class="nv">m</span><span class="o">.</span><span class="py">copy</span><span class="o">(</span><span class="n">n</span> <span class="k">=</span> <span class="nv">m</span><span class="o">.</span><span class="py">n</span> <span class="o">+</span> <span class="mi">1</span><span class="o">)</span>
    <span class="k">case</span> <span class="nc">Left</span> <span class="k">=&gt;</span>
        <span class="nv">m</span><span class="o">.</span><span class="py">copy</span><span class="o">(</span><span class="n">x</span> <span class="k">=</span> <span class="nv">m</span><span class="o">.</span><span class="py">x</span> <span class="o">-</span> <span class="n">speed</span><span class="o">)</span>
    <span class="k">case</span> <span class="nc">Right</span> <span class="k">=&gt;</span>
        <span class="nv">m</span><span class="o">.</span><span class="py">copy</span><span class="o">(</span><span class="n">x</span> <span class="k">=</span> <span class="nv">m</span><span class="o">.</span><span class="py">x</span> <span class="o">+</span> <span class="n">speed</span><span class="o">)</span>
    <span class="k">case</span> <span class="nc">Still</span> <span class="k">=&gt;</span>
        <span class="n">m</span>
<span class="o">}</span>

<span class="k">def</span> <span class="nf">view</span><span class="o">(</span><span class="n">m</span><span class="k">:</span> <span class="kt">Model</span><span class="o">)</span> <span class="k">=</span> <span class="nv">Picture</span><span class="o">.</span><span class="py">text</span><span class="o">(</span><span class="nv">m</span><span class="o">.</span><span class="py">n</span><span class="o">,</span> <span class="mi">30</span><span class="o">).</span><span class="py">withTranslation</span><span class="o">(</span><span class="nv">m</span><span class="o">.</span><span class="py">x</span><span class="o">,</span> <span class="nv">m</span><span class="o">.</span><span class="py">y</span><span class="o">)</span>

<span class="k">val</span> <span class="nv">tickSub</span><span class="k">:</span> <span class="kt">Sub</span><span class="o">[</span><span class="kt">Msg</span><span class="o">]</span> <span class="k">=</span> <span class="nv">Subscriptions</span><span class="o">.</span><span class="py">onAnimationFrame</span> <span class="o">{</span>
    <span class="nc">Tick</span>
<span class="o">}</span>

<span class="k">val</span> <span class="nv">keySub</span><span class="k">:</span> <span class="kt">Sub</span><span class="o">[</span><span class="kt">Msg</span><span class="o">]</span> <span class="k">=</span> <span class="nv">Subscriptions</span><span class="o">.</span><span class="py">onKeyDown</span> <span class="o">{</span>
    <span class="k">case</span> <span class="nv">Kc</span><span class="o">.</span><span class="py">VK_LEFT</span>  <span class="k">=&gt;</span> <span class="nc">Left</span>
    <span class="k">case</span> <span class="nv">Kc</span><span class="o">.</span><span class="py">VK_RIGHT</span> <span class="k">=&gt;</span> <span class="nc">Right</span>
    <span class="k">case</span> <span class="k">_</span>           <span class="k">=&gt;</span> <span class="nc">Still</span>
<span class="o">}</span>

<span class="k">def</span> <span class="nf">subs</span><span class="o">(</span><span class="n">m</span><span class="k">:</span> <span class="kt">Model</span><span class="o">)</span> <span class="k">=</span> <span class="o">{</span>
    <span class="nf">if</span> <span class="o">(</span><span class="nv">m</span><span class="o">.</span><span class="py">x</span> <span class="o">&gt;</span> <span class="o">-</span><span class="n">limit</span> <span class="o">&amp;&amp;</span> <span class="nv">m</span><span class="o">.</span><span class="py">x</span> <span class="o">&lt;</span> <span class="n">limit</span><span class="o">)</span> <span class="nc">Seq</span><span class="o">(</span><span class="n">tickSub</span><span class="o">,</span> <span class="n">keySub</span><span class="o">)</span>
    <span class="k">else</span> <span class="nc">Seq</span><span class="o">()</span>
<span class="o">}</span>

<span class="nf">runGame</span><span class="o">(</span><span class="n">initState</span><span class="o">,</span> <span class="n">update</span><span class="o">,</span> <span class="n">view</span><span class="o">,</span> <span class="n">subs</span><span class="o">)</span>
<span class="nf">activateCanvas</span><span class="o">()</span>
</code></pre></div></div> <p>Let us see what’s changed compared to the pure animation:</p> <ul> <li>You still have a <code class="language-plaintext highlighter-rouge">Model</code> case class to represent the state of the game. This contains an <code class="language-plaintext highlighter-rouge">x</code> and <code class="language-plaintext highlighter-rouge">y</code> now in addition to the counter value.</li> <li>You have a bunch of case classes / objects to represent the possible messages that can come into your game.</li> <li>You still have an <code class="language-plaintext highlighter-rouge">init</code> function that returns your initial state.</li> <li>You still have an <code class="language-plaintext highlighter-rouge">update</code> function that returns the next state given the previous state. But this function now takes an additional message paramter.</li> <li>You still have a view function as before.</li> <li>You have a new <code class="language-plaintext highlighter-rouge">subs</code> function that returns subscriptions for messages that the game is interested in, given the current state of the game. These subscriptions deliver the desired messages into the game.</li> </ul> <p>And there, you have the essentials of a purely functional game!</p> <p>Based on these ideas, <a href="https://github.com/litan/kojo-examples/blob/main/hunted-game-various-styles/06-hunted-functional-2.kojo">you can see a fuller game here</a>.</p> <p><em>Note</em> – Functional gaming in Kojo is a proof of concept prototype (partially based on ideas derived from elm). Many thanks to Anay Kamat for his inputs in this area.</p> <hr/> <h3 id="object-oriented-gaming-with-kojo-gaming">Object-oriented gaming with kojo-gaming</h3> <p><a href="https://github.com/litan/kojo-gaming">kojo-gaming</a> is a module/extension for Kojo, built with the goal of exposing older students (11th grade, 2nd/3rd year undergrad, and older) to core ideas in practical coding – in an interesting context, with the building of fun (hardware accelerated) games within Kojo that they can export to Desktop and Mobile.</p> <p>kojo-gaming is based on the object-oriented paradigm (this works very well for gaming in our mind, plus is also widely used in industry), with functional ideas coming in as needed to improve code.</p> <div class="float-right ml-3 mb-1"> <figure> <picture> <source class="responsive-img-srcset" media="(max-width: 480px)" srcset="/assets/img/blog/lunar-lander-480.webp"/> <source class="responsive-img-srcset" media="(max-width: 800px)" srcset="/assets/img/blog/lunar-lander-800.webp"/> <source class="responsive-img-srcset" media="(max-width: 1400px)" srcset="/assets/img/blog/lunar-lander-1400.webp"/> <img src="/assets/img/blog/lunar-lander.png" class="img-fluid rounded z-depth-1" width="400" height="auto" data-zoomable="" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture><figcaption class="caption">Lunar Lander Game</figcaption> </figure> </div> <p>The core ideas in kojo-gaming are the following:</p> <ul> <li>A simple entity component system, with the following features: <ul> <li>animated sprites with rendering based on textures, texture atlases, and particle systems.</li> <li>simple physics (kinematics).</li> <li>collision detection and response.</li> <li>world boundary behaviors (bouncing, wrapping, etc).</li> <li>and more…</li> </ul> </li> <li>A couple of different implementations: <ul> <li>One that works right within the Kojo canvas – for a quick and simple start, and the easy learning of fundamental ideas. This is called <code class="language-plaintext highlighter-rouge">game-engine-lite</code></li> <li>One that is based on <a href="https://github.com/libgdx/libgdx">libGDX</a> – for putting the fundamental ideas to use in creating fancier games that can be exported to Desktop and Mobile. In this approach, Kojo brings up a new window where all the action happens.</li> </ul> </li> </ul> <p>All of this will be described in an upcoming post. For now, to get going, you can just download the <a href="https://github.com/litan/kojo-gaming/releases/download/v0.2.0/game-engine-lite.zip"><code class="language-plaintext highlighter-rouge">game-engine-lite.zip</code> file</a>, unzip it anywhere, and then open/run any of the samples under <code class="language-plaintext highlighter-rouge">game-engine-lite/samples</code>. Or you can <a href="https://github.com/litan/kojo-gaming/releases">download the full release of kojo-gaming</a>.</p> <hr/> <h3 id="kojo-ai">kojo-ai</h3> <div class="float-right ml-3 mb-1"> <figure> <picture> <source class="responsive-img-srcset" media="(max-width: 480px)" srcset="/assets/img/blog/kojo-ai-480.webp"/> <source class="responsive-img-srcset" media="(max-width: 800px)" srcset="/assets/img/blog/kojo-ai-800.webp"/> <source class="responsive-img-srcset" media="(max-width: 1400px)" srcset="/assets/img/blog/kojo-ai-1400.webp"/> <img src="/assets/img/blog/kojo-ai.png" class="img-fluid rounded z-depth-1" width="400" height="auto" data-zoomable="" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture><figcaption class="caption">Kojo-AI examples</figcaption> </figure> </div> <p><a href="https://github.com/litan/kojo-ai-3">kojo-ai</a> is a module/extension for Kojo, built with the goal of providing older students a good learning ground for AI. kojo-ai provides support for things like the following:</p> <ul> <li>Learning the essential theoretical concepts in AI.</li> <li>Playing with these concepts within engaging projects.</li> <li>Getting hands-on with the Learning (Training) process of AI models.</li> <li>Building AI-enabled applications.</li> <li>Using pre-trained AI models within scripts.</li> <li>Using Generative AI Apps for design work for games written in Kojo.</li> <li>Gaining insights into generative AI and large-scale foundational models (like ChatGPT).</li> </ul> <p>More on this in an upcoming blog post. For now, to play with kojo-ai, you can use the <a href="https://github.com/litan/kojo-ai-3/releases">latest release and provided instructions</a>.</p> <hr/> <h3 id="kojo-music">kojo-music</h3> <div class="float-right ml-3 mb-1"> <figure> <picture> <source class="responsive-img-srcset" media="(max-width: 480px)" srcset="/assets/img/blog/kojo-music-workbench-480.webp"/> <source class="responsive-img-srcset" media="(max-width: 800px)" srcset="/assets/img/blog/kojo-music-workbench-800.webp"/> <source class="responsive-img-srcset" media="(max-width: 1400px)" srcset="/assets/img/blog/kojo-music-workbench-1400.webp"/> <img src="/assets/img/blog/kojo-music-workbench.png" class="img-fluid rounded z-depth-1" width="400" height="auto" data-zoomable="" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture><figcaption class="caption">Kojo Music Workbench</figcaption> </figure> </div> <p><a href="https://github.com/litan/kojo-music">kojo-music</a> is a module/extension for Kojo, built with the following basic goals:</p> <ul> <li>Provide music as a rich area for children to do creative coding.</li> <li>Enable children to have fun with music as creators and composers - via coding.</li> <li>Enable the usage of Kojo/coding as a new kind of musical instrument.</li> </ul> <p>kojo-music aims to provide an easy start via a <em>Music Workbench</em>, where musical compositions can be created and played, and then exported as code – to enable a gentle entry into coding for music.</p> <p>kojo-music uses <a href="https://alda.io">Alda</a> as its music server.</p> <p>kojo-music will be described in detail in an upcoming blog post. In the meantime, to play with kojo-music you can use the <a href="https://github.com/litan/kojo-music/releases">latest release and provided instructions</a>.</p> <hr/> <h3 id="picture-clipping-and-masking">Picture clipping and masking</h3> <p>As a quick reminder, Pictures are Kojo’s way of doing functional graphics. To work with Pictures:</p> <ul> <li>You create one or more pictures using predefined functions (for various shapes), or by using the turtle-graphics API, or by using lower level primitives from Java2D.</li> <li>You transform these pictures using various predefined transforms like translation, rotation, and scaling.</li> <li>You combine these pictures in rows, columns, and stacks as desired (with rows/columns/stacks of pictures themselves being pictures).</li> <li>And then you finally draw these pictures on the canvas (or use them in animations or games).</li> </ul> <p>Clipping and Masking are a couple of new transforms for Pictures. Let’s get right to them and see them in action.</p> <p>The following is our base picture (to which clipping and masking will be applied):</p> <div class="language-scala highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nf">cleari</span><span class="o">()</span>
<span class="nf">setBackground</span><span class="o">(</span><span class="nv">ColorMaker</span><span class="o">.</span><span class="py">hsl</span><span class="o">(</span><span class="mi">0</span><span class="o">,</span> <span class="mf">0.00</span><span class="o">,</span> <span class="mf">0.12</span><span class="o">))</span>

<span class="k">val</span> <span class="nv">w</span> <span class="k">=</span> <span class="mi">400</span>
<span class="k">val</span> <span class="nv">h</span> <span class="k">=</span> <span class="mi">200</span>
<span class="k">val</span> <span class="nv">fill</span> <span class="k">=</span> <span class="nv">cm</span><span class="o">.</span><span class="py">linearGradient</span><span class="o">(</span><span class="mi">0</span><span class="o">,</span> <span class="mi">0</span><span class="o">,</span> <span class="n">red</span><span class="o">,</span> <span class="mi">0</span><span class="o">,</span> <span class="n">h</span><span class="o">,</span> <span class="n">yellow</span><span class="o">)</span>
<span class="k">val</span> <span class="nv">rect</span> <span class="k">=</span> <span class="nv">Picture</span><span class="o">.</span><span class="py">rectangle</span><span class="o">(</span><span class="n">w</span><span class="o">,</span> <span class="n">h</span><span class="o">).</span><span class="py">withFillColor</span><span class="o">(</span><span class="n">fill</span><span class="o">)</span>

<span class="k">val</span> <span class="nv">rectWithReflection</span> <span class="k">=</span> <span class="nf">picStack</span><span class="o">(</span>
    <span class="n">rect</span><span class="o">,</span>
    <span class="nv">rect</span><span class="o">.</span><span class="py">withFading</span><span class="o">(</span><span class="n">h</span><span class="o">)</span>
        <span class="o">.</span><span class="py">withTranslation</span><span class="o">(</span><span class="mi">0</span><span class="o">,</span> <span class="mi">3</span><span class="o">)</span>
        <span class="o">.</span><span class="py">withFlippedY</span>
<span class="o">)</span>

<span class="nf">drawCentered</span><span class="o">(</span><span class="n">rectWithReflection</span><span class="o">)</span>
</code></pre></div></div> <div class="text-center m-4"> <figure> <picture> <source class="responsive-img-srcset" media="(max-width: 480px)" srcset="/assets/img/blog/rect-reflection-480.webp"/> <source class="responsive-img-srcset" media="(max-width: 800px)" srcset="/assets/img/blog/rect-reflection-800.webp"/> <source class="responsive-img-srcset" media="(max-width: 1400px)" srcset="/assets/img/blog/rect-reflection-1400.webp"/> <img src="/assets/img/blog/rect-reflection.png" class="img-fluid rounded z-depth-1" width="400" height="auto" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture><figcaption class="caption">The base Picture</figcaption> </figure> </div> <p>Let’s now clip the rectangle with a circle (so that only the portion of the rectangle that lies within the circle is visible):</p> <div class="language-scala highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nf">cleari</span><span class="o">()</span>
<span class="nf">setBackground</span><span class="o">(</span><span class="nv">ColorMaker</span><span class="o">.</span><span class="py">hsl</span><span class="o">(</span><span class="mi">0</span><span class="o">,</span> <span class="mf">0.0</span><span class="o">,</span> <span class="mf">0.12</span><span class="o">))</span>

<span class="k">val</span> <span class="nv">w</span> <span class="k">=</span> <span class="mi">400</span>
<span class="k">val</span> <span class="nv">h</span> <span class="k">=</span> <span class="mi">200</span>
<span class="k">val</span> <span class="nv">fill</span> <span class="k">=</span> <span class="nv">cm</span><span class="o">.</span><span class="py">linearGradient</span><span class="o">(</span><span class="mi">0</span><span class="o">,</span> <span class="mi">0</span><span class="o">,</span> <span class="n">red</span><span class="o">,</span> <span class="mi">0</span><span class="o">,</span> <span class="n">h</span><span class="o">,</span> <span class="n">yellow</span><span class="o">)</span>
<span class="k">val</span> <span class="nv">rect</span> <span class="k">=</span> <span class="nv">Picture</span><span class="o">.</span><span class="py">rectangle</span><span class="o">(</span><span class="n">w</span><span class="o">,</span> <span class="n">h</span><span class="o">).</span><span class="py">withFillColor</span><span class="o">(</span><span class="n">fill</span><span class="o">)</span>

<span class="k">val</span> <span class="nv">rectWithReflection</span> <span class="k">=</span> <span class="nf">picStack</span><span class="o">(</span>
    <span class="n">rect</span><span class="o">,</span>
    <span class="nv">rect</span><span class="o">.</span><span class="py">withFading</span><span class="o">(</span><span class="n">h</span><span class="o">)</span>
        <span class="o">.</span><span class="py">withTranslation</span><span class="o">(</span><span class="mi">0</span><span class="o">,</span> <span class="mi">3</span><span class="o">)</span>
        <span class="o">.</span><span class="py">withFlippedY</span>
<span class="o">)</span>

<span class="k">val</span> <span class="nv">clippingPic</span> <span class="k">=</span> <span class="nv">Picture</span><span class="o">.</span><span class="py">ellipseInRect</span><span class="o">(</span><span class="n">w</span><span class="o">,</span> <span class="n">h</span> <span class="o">*</span> <span class="mi">2</span><span class="o">).</span><span class="py">withTranslation</span><span class="o">(</span><span class="mi">0</span><span class="o">,</span> <span class="o">-</span><span class="n">h</span><span class="o">)</span>

<span class="k">val</span> <span class="nv">clippedPic</span> <span class="k">=</span>
    <span class="n">rectWithReflection</span>
        <span class="o">.</span><span class="py">withClipping</span><span class="o">(</span><span class="n">clippingPic</span><span class="o">)</span>
        <span class="o">.</span><span class="py">withPenColor</span><span class="o">(</span><span class="n">black</span><span class="o">)</span>
        <span class="o">.</span><span class="py">withPenThickness</span><span class="o">(</span><span class="mi">4</span><span class="o">)</span>

<span class="nf">drawCentered</span><span class="o">(</span><span class="n">clippedPic</span><span class="o">)</span>
</code></pre></div></div> <div class="row mt-3"> <div class="col-sm mt-3 mt-md-0"> <figure> <picture> <source class="responsive-img-srcset" media="(max-width: 480px)" srcset="/assets/img/blog/rect-reflection-480.webp"/> <source class="responsive-img-srcset" media="(max-width: 800px)" srcset="/assets/img/blog/rect-reflection-800.webp"/> <source class="responsive-img-srcset" media="(max-width: 1400px)" srcset="/assets/img/blog/rect-reflection-1400.webp"/> <img src="/assets/img/blog/rect-reflection.png" class="img-fluid rounded z-depth-1" width="auto" height="auto" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture> </figure> </div> <div class="col-sm mt-3 mt-md-0"> <figure> <picture> <source class="responsive-img-srcset" media="(max-width: 480px)" srcset="/assets/img/blog/clipping-pic-480.webp"/> <source class="responsive-img-srcset" media="(max-width: 800px)" srcset="/assets/img/blog/clipping-pic-800.webp"/> <source class="responsive-img-srcset" media="(max-width: 1400px)" srcset="/assets/img/blog/clipping-pic-1400.webp"/> <img src="/assets/img/blog/clipping-pic.png" class="img-fluid rounded z-depth-1" width="auto" height="auto" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture> </figure> </div> <div class="col-sm mt-3 mt-md-0"> <figure> <picture> <source class="responsive-img-srcset" media="(max-width: 480px)" srcset="/assets/img/blog/rect-reflection-clipped-480.webp"/> <source class="responsive-img-srcset" media="(max-width: 800px)" srcset="/assets/img/blog/rect-reflection-clipped-800.webp"/> <source class="responsive-img-srcset" media="(max-width: 1400px)" srcset="/assets/img/blog/rect-reflection-clipped-1400.webp"/> <img src="/assets/img/blog/rect-reflection-clipped.png" class="img-fluid rounded z-depth-1" width="auto" height="auto" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture> </figure> </div> </div> <div class="caption"> The base Picture, the Picture which defines the clip area, and the final clipped Picture. </div> <p>Finally, let’s apply a mask to the clipped picture. The mask is a black/white (or grayscale) picture, where black specifies transparent regions, and white specifies opaque regions (with gray in between, with darker grays being more transparent):</p> <div class="language-scala highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nf">cleari</span><span class="o">()</span>
<span class="nf">setBackground</span><span class="o">(</span><span class="nv">ColorMaker</span><span class="o">.</span><span class="py">hsl</span><span class="o">(</span><span class="mi">0</span><span class="o">,</span> <span class="mf">0.0</span><span class="o">,</span> <span class="mf">0.12</span><span class="o">))</span>

<span class="k">val</span> <span class="nv">w</span> <span class="k">=</span> <span class="mi">400</span>
<span class="k">val</span> <span class="nv">h</span> <span class="k">=</span> <span class="mi">200</span>
<span class="k">val</span> <span class="nv">fill</span> <span class="k">=</span> <span class="nv">cm</span><span class="o">.</span><span class="py">linearGradient</span><span class="o">(</span><span class="mi">0</span><span class="o">,</span> <span class="mi">0</span><span class="o">,</span> <span class="n">red</span><span class="o">,</span> <span class="mi">0</span><span class="o">,</span> <span class="n">h</span><span class="o">,</span> <span class="n">yellow</span><span class="o">)</span>
<span class="k">val</span> <span class="nv">rect</span> <span class="k">=</span> <span class="nv">Picture</span><span class="o">.</span><span class="py">rectangle</span><span class="o">(</span><span class="n">w</span><span class="o">,</span> <span class="n">h</span><span class="o">).</span><span class="py">withFillColor</span><span class="o">(</span><span class="n">fill</span><span class="o">)</span>

<span class="k">val</span> <span class="nv">rectWithReflection</span> <span class="k">=</span> <span class="nf">picStack</span><span class="o">(</span>
    <span class="n">rect</span><span class="o">,</span>
    <span class="nv">rect</span><span class="o">.</span><span class="py">withFading</span><span class="o">(</span><span class="n">h</span><span class="o">)</span>
        <span class="o">.</span><span class="py">withTranslation</span><span class="o">(</span><span class="mi">0</span><span class="o">,</span> <span class="mi">3</span><span class="o">)</span>
        <span class="o">.</span><span class="py">withFlippedY</span>
<span class="o">)</span>

<span class="k">val</span> <span class="nv">clippingPic</span> <span class="k">=</span> <span class="nv">Picture</span><span class="o">.</span><span class="py">ellipseInRect</span><span class="o">(</span><span class="n">w</span><span class="o">,</span> <span class="n">h</span> <span class="o">*</span> <span class="mi">2</span><span class="o">).</span><span class="py">withTranslation</span><span class="o">(</span><span class="mi">0</span><span class="o">,</span> <span class="o">-</span><span class="n">h</span><span class="o">)</span>

<span class="k">val</span> <span class="nv">clippedPic</span> <span class="k">=</span>
    <span class="n">rectWithReflection</span>
        <span class="o">.</span><span class="py">withClipping</span><span class="o">(</span><span class="n">clippingPic</span><span class="o">)</span>
        <span class="o">.</span><span class="py">withPenColor</span><span class="o">(</span><span class="n">black</span><span class="o">)</span>
        <span class="o">.</span><span class="py">withPenThickness</span><span class="o">(</span><span class="mi">4</span><span class="o">)</span>

<span class="k">val</span> <span class="nv">maskPic</span> <span class="k">=</span> <span class="nf">picStack</span><span class="o">(</span>
    <span class="nv">Picture</span><span class="o">.</span><span class="py">rectangle</span><span class="o">(</span><span class="n">w</span><span class="o">,</span> <span class="n">h</span> <span class="o">*</span> <span class="mi">2</span><span class="o">).</span><span class="py">withFillColor</span><span class="o">(</span><span class="n">white</span><span class="o">).</span><span class="py">withPenColor</span><span class="o">(</span><span class="n">white</span><span class="o">).</span><span class="py">withPenThickness</span><span class="o">(</span><span class="mi">4</span><span class="o">),</span>
    <span class="nv">Picture</span><span class="o">.</span><span class="py">arc</span><span class="o">(</span><span class="n">w</span> <span class="o">/</span> <span class="mi">2</span><span class="o">,</span> <span class="mi">180</span><span class="o">).</span><span class="py">withRotation</span><span class="o">(</span><span class="mi">90</span><span class="o">).</span><span class="py">withScaling</span><span class="o">(</span><span class="mf">0.9</span><span class="o">).</span><span class="py">withTranslation</span><span class="o">(</span><span class="n">w</span><span class="o">+</span><span class="mi">3</span><span class="o">,</span> <span class="n">h</span><span class="o">).</span><span class="py">withFillColor</span><span class="o">(</span><span class="n">black</span><span class="o">).</span><span class="py">withPenColor</span><span class="o">(</span><span class="n">black</span><span class="o">),</span>
    <span class="nv">Picture</span><span class="o">.</span><span class="py">arc</span><span class="o">(</span><span class="n">w</span> <span class="o">/</span> <span class="mi">2</span><span class="o">,</span> <span class="mi">180</span><span class="o">).</span><span class="py">withRotation</span><span class="o">(-</span><span class="mi">90</span><span class="o">).</span><span class="py">withScaling</span><span class="o">(</span><span class="mf">0.9</span><span class="o">).</span><span class="py">withTranslation</span><span class="o">(-</span><span class="mi">3</span><span class="o">,</span> <span class="n">h</span><span class="o">).</span><span class="py">withFillColor</span><span class="o">(</span><span class="n">black</span><span class="o">).</span><span class="py">withPenColor</span><span class="o">(</span><span class="n">black</span><span class="o">)</span>
<span class="o">)</span>

<span class="k">val</span> <span class="nv">maskedPic</span> <span class="k">=</span> <span class="nv">clippedPic</span><span class="o">.</span><span class="py">withMask</span><span class="o">(</span><span class="n">maskPic</span><span class="o">)</span>

<span class="nf">drawCentered</span><span class="o">(</span><span class="n">maskedPic</span><span class="o">)</span>
</code></pre></div></div> <div class="row mt-3"> <div class="col-sm mt-3 mt-md-0"> <figure> <picture> <source class="responsive-img-srcset" media="(max-width: 480px)" srcset="/assets/img/blog/rect-reflection-clipped-480.webp"/> <source class="responsive-img-srcset" media="(max-width: 800px)" srcset="/assets/img/blog/rect-reflection-clipped-800.webp"/> <source class="responsive-img-srcset" media="(max-width: 1400px)" srcset="/assets/img/blog/rect-reflection-clipped-1400.webp"/> <img src="/assets/img/blog/rect-reflection-clipped.png" class="img-fluid rounded z-depth-1" width="auto" height="auto" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture> </figure> </div> <div class="col-sm mt-3 mt-md-0"> <figure> <picture> <source class="responsive-img-srcset" media="(max-width: 480px)" srcset="/assets/img/blog/mask-pic-480.webp"/> <source class="responsive-img-srcset" media="(max-width: 800px)" srcset="/assets/img/blog/mask-pic-800.webp"/> <source class="responsive-img-srcset" media="(max-width: 1400px)" srcset="/assets/img/blog/mask-pic-1400.webp"/> <img src="/assets/img/blog/mask-pic.png" class="img-fluid rounded z-depth-1" width="auto" height="auto" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture> </figure> </div> <div class="col-sm mt-3 mt-md-0"> <figure> <picture> <source class="responsive-img-srcset" media="(max-width: 480px)" srcset="/assets/img/blog/rect-reflection-clipped-masked-480.webp"/> <source class="responsive-img-srcset" media="(max-width: 800px)" srcset="/assets/img/blog/rect-reflection-clipped-masked-800.webp"/> <source class="responsive-img-srcset" media="(max-width: 1400px)" srcset="/assets/img/blog/rect-reflection-clipped-masked-1400.webp"/> <img src="/assets/img/blog/rect-reflection-clipped-masked.png" class="img-fluid rounded z-depth-1" width="auto" height="auto" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture> </figure> </div> </div> <div class="caption"> The clipped Picture, The Picture which defines the mask, and the final masked Picture. </div> <hr/> <h3 id="other-miscellaneous-enhancements">Other miscellaneous enhancements</h3> <p>There have been many other enhancements since the last release announcement. Some of these are mentioned below (without a lot of detail for now – we’ll have explanatory blog posts on some of these in the future):</p> <ul> <li>Realtime note playing with the <code class="language-plaintext highlighter-rouge">setNoteInstrument(instrument)</code> and <code class="language-plaintext highlighter-rouge">playNote(note, duration)</code> commands. The <em>Showcase -&gt; Fireworks</em> sample in Kojo has a non-trivial example of this.</li> <li>Using <code class="language-plaintext highlighter-rouge">CanvasDraw</code> in animations. <code class="language-plaintext highlighter-rouge">CanvasDraw</code> offers a Processing-like api for simple shape drawing, and is useful where you don’t want retained-mode graphics (which is what you get with Pictures). <code class="language-plaintext highlighter-rouge">CanvasDraw</code> is used by <code class="language-plaintext highlighter-rouge">game-engine-lite</code> in kojo-gaming.</li> <li>Support for drawing text and images in <code class="language-plaintext highlighter-rouge">CanvasDraw</code>.</li> <li>Support for spawning external processes from within Kojo. To use this, your script should contain the <code class="language-plaintext highlighter-rouge">#exec</code> pragma at the top. This feature is used by kojo-gaming to spawn external libGDX processes.</li> <li>Improved curve drawing.</li> <li>Neural Style Transfer refinements.</li> <li>Apple silicon support.</li> <li>New samples.</li> <li>Turkish enhancements.</li> </ul> <hr/> <p>That’s it for now…</p> <p>As always, the new version of Kojo is available from the <a href="https://www.kogics.net/kojo-download">Kojo Download Page</a>. If you run into any difficulties, let us know.</p> <p>Enjoy!</p>]]></content><author><name></name></author><category term="kojo"/><category term="announce"/><summary type="html"><![CDATA[Kojo has a new release]]></summary></entry><entry><title type="html">New Kojo Release — 2.9.23, plus more…</title><link href="https://www.kogics.net/blog/2022/kojo-release-2_9_23/" rel="alternate" type="text/html" title="New Kojo Release — 2.9.23, plus more…"/><published>2022-08-16T15:09:00+00:00</published><updated>2022-08-16T15:09:00+00:00</updated><id>https://www.kogics.net/blog/2022/kojo-release-2_9_23</id><content type="html" xml:base="https://www.kogics.net/blog/2022/kojo-release-2_9_23/"><![CDATA[<p>I’m pleased to announce a new release of Kojo. The following are the highlights (for Kojo and the activities around it) since the last announcement:</p> <ul id="markdown-toc"> <li><a href="#support-for-with-and-thats-transforms-for-pictures" id="markdown-toc-support-for-with-and-thats-transforms-for-pictures">Support for .with and .thats transforms for Pictures</a></li> <li><a href="#support-for-declarative-animations" id="markdown-toc-support-for-declarative-animations">Support for declarative animations</a></li> <li><a href="#the-kojo-code-exchange--a-new-website" id="markdown-toc-the-kojo-code-exchange--a-new-website">The Kojo code exchange – a new website</a></li> <li><a href="#kojo-in-the-goa-government-curriculum--an-update" id="markdown-toc-kojo-in-the-goa-government-curriculum--an-update">Kojo in the Goa government curriculum – an update</a></li> <li><a href="#turkish-enhancements" id="markdown-toc-turkish-enhancements">Turkish enhancements</a></li> <li><a href="#other-miscellaneous-enhancements" id="markdown-toc-other-miscellaneous-enhancements">Other miscellaneous enhancements</a></li> </ul> <hr/> <h3 id="support-for-with-and-thats-transforms-for-pictures">Support for .with and .thats transforms for Pictures</h3> <p>Pictures in Kojo can now be transformed using method based .withXx and .thatsXx transforms. So the following program using the earlier object-functional transforms:</p> <div class="language-scala highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nf">cleari</span><span class="o">()</span>
 
<span class="k">val</span> <span class="nv">pic</span> <span class="k">=</span>
  <span class="nf">trans</span><span class="o">(</span><span class="mi">100</span><span class="o">,</span> <span class="mi">0</span><span class="o">)</span> <span class="o">*</span>
    <span class="nf">rot</span><span class="o">(</span><span class="mi">45</span><span class="o">)</span> <span class="o">*</span>
    <span class="nf">trans</span><span class="o">(</span><span class="mi">50</span><span class="o">,</span> <span class="mi">0</span><span class="o">)</span> <span class="o">-&gt;</span>
    <span class="nv">Picture</span><span class="o">.</span><span class="py">rectangle</span><span class="o">(</span><span class="mi">100</span><span class="o">,</span> <span class="mi">50</span><span class="o">)</span>
 
<span class="nf">draw</span><span class="o">(</span><span class="n">pic</span><span class="o">)</span>
</code></pre></div></div> <p>now becomes:</p> <div class="language-scala highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nf">cleari</span><span class="o">()</span>
 
<span class="k">val</span> <span class="nv">pic</span> <span class="k">=</span> <span class="nv">Picture</span><span class="o">.</span><span class="py">rectangle</span><span class="o">(</span><span class="mi">100</span><span class="o">,</span> <span class="mi">50</span><span class="o">)</span>
  <span class="o">.</span><span class="py">withTranslation</span><span class="o">(</span><span class="mi">50</span><span class="o">,</span> <span class="mi">0</span><span class="o">)</span>
  <span class="o">.</span><span class="py">thatsRotated</span><span class="o">(</span><span class="mi">45</span><span class="o">)</span>
  <span class="o">.</span><span class="py">withTranslation</span><span class="o">(</span><span class="mi">100</span><span class="o">,</span> <span class="mi">0</span><span class="o">)</span>
 
<span class="nf">draw</span><span class="o">(</span><span class="n">pic</span><span class="o">)</span>
</code></pre></div></div> <p>The available method-functional transforms can be seen via code completion on any picture <code class="language-plaintext highlighter-rouge">pic</code> by typing <code class="language-plaintext highlighter-rouge">pic.with</code> + <em>Ctrl+Space</em> or <code class="language-plaintext highlighter-rouge">pic.thats</code> + <em>Ctrl+Space</em>.</p> <p>The <code class="language-plaintext highlighter-rouge">.withXx</code> and the corresponding <code class="language-plaintext highlighter-rouge">.thatXx</code> transforms do the same thing, and can be used interchangeably to make your code nicely readable – the way you like it.</p> <p>Both the earlier object-functional and the new method-functional transform syntaxes are fully supported. You are free to pick and choose whatever works best for you.</p> <p>Here’s a larger program that shows the new transforms in action:</p> <div class="language-scala highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nf">cleari</span><span class="o">()</span>
 
<span class="k">val</span> <span class="nv">cb</span> <span class="k">=</span> <span class="n">canvasBounds</span>
<span class="k">val</span> <span class="nv">bg</span> <span class="k">=</span> <span class="nv">cm</span><span class="o">.</span><span class="py">linearGradient</span><span class="o">(</span><span class="nv">cb</span><span class="o">.</span><span class="py">x</span><span class="o">,</span> <span class="nv">cb</span><span class="o">.</span><span class="py">y</span><span class="o">,</span> <span class="nv">cm</span><span class="o">.</span><span class="py">black</span><span class="o">,</span> <span class="nv">cb</span><span class="o">.</span><span class="py">x</span> <span class="o">+</span> <span class="nv">cb</span><span class="o">.</span><span class="py">width</span><span class="o">,</span> <span class="nv">cb</span><span class="o">.</span><span class="py">y</span> <span class="o">+</span> <span class="nv">cb</span><span class="o">.</span><span class="py">height</span><span class="o">,</span> <span class="nv">cm</span><span class="o">.</span><span class="py">gray</span><span class="o">,</span> <span class="kc">false</span><span class="o">)</span>
<span class="nf">setBackground</span><span class="o">(</span><span class="n">bg</span><span class="o">)</span>
 
<span class="k">val</span> <span class="nv">fillc</span> <span class="k">=</span> <span class="nv">cm</span><span class="o">.</span><span class="py">linearGradient</span><span class="o">(</span><span class="mi">0</span><span class="o">,</span> <span class="mi">0</span><span class="o">,</span> <span class="nv">ColorMaker</span><span class="o">.</span><span class="py">hsl</span><span class="o">(</span><span class="mi">40</span><span class="o">,</span> <span class="mf">1.00</span><span class="o">,</span> <span class="mf">0.40</span><span class="o">),</span>  <span class="mi">0</span><span class="o">,</span> <span class="mi">150</span><span class="o">,</span> <span class="nv">cm</span><span class="o">.</span><span class="py">yellow</span><span class="o">,</span> <span class="kc">false</span><span class="o">)</span>
 
<span class="k">def</span> <span class="nf">halfPetal</span> <span class="k">=</span> <span class="nc">Picture</span> <span class="o">{</span>
  <span class="nf">left</span><span class="o">(</span><span class="mi">45</span><span class="o">)</span>
  <span class="nf">right</span><span class="o">(</span><span class="mi">90</span><span class="o">,</span> <span class="mi">120</span><span class="o">)</span>
<span class="o">}</span>
 
<span class="k">def</span> <span class="nf">petal</span> <span class="k">=</span> <span class="nf">picStack</span><span class="o">(</span><span class="n">halfPetal</span><span class="o">,</span> <span class="nv">halfPetal</span><span class="o">.</span><span class="py">withFlippedX</span><span class="o">)</span>
  <span class="o">.</span><span class="py">withFillColor</span><span class="o">(</span><span class="n">fillc</span><span class="o">)</span>
  <span class="o">.</span><span class="py">withPenColor</span><span class="o">(</span><span class="nv">cm</span><span class="o">.</span><span class="py">darkGoldenrod</span><span class="o">)</span>
  <span class="o">.</span><span class="py">withPenThickness</span><span class="o">(</span><span class="mi">1</span><span class="o">)</span>
 
<span class="k">val</span> <span class="nv">nump</span> <span class="k">=</span> <span class="mi">7</span>
 
<span class="k">def</span> <span class="nf">flower</span><span class="o">(</span><span class="n">petals</span><span class="k">:</span> <span class="kt">Int</span><span class="o">)</span><span class="k">:</span> <span class="kt">Picture</span> <span class="o">=</span> <span class="o">{</span>
  <span class="nf">if</span> <span class="o">(</span><span class="n">petals</span> <span class="o">==</span> <span class="mi">1</span><span class="o">)</span>
    <span class="n">petal</span>
  <span class="k">else</span>
    <span class="nf">picStack</span><span class="o">(</span><span class="n">petal</span><span class="o">,</span> <span class="nf">flower</span><span class="o">(</span><span class="n">petals</span> <span class="o">-</span> <span class="mi">1</span><span class="o">).</span><span class="py">thatsRotated</span><span class="o">(</span><span class="mf">360.0</span> <span class="o">/</span> <span class="n">nump</span><span class="o">))</span>
<span class="o">}</span>
 
<span class="nf">draw</span><span class="o">(</span><span class="nf">flower</span><span class="o">(</span><span class="n">nump</span><span class="o">))</span>
</code></pre></div></div> <p>And here’s the output of the program:</p> <div class="text-center mt-4 mb-4"> <figure> <picture> <source class="responsive-img-srcset" media="(max-width: 480px)" srcset="/assets/img/blog/flower.webp-480.webp"/> <source class="responsive-img-srcset" media="(max-width: 800px)" srcset="/assets/img/blog/flower.webp-800.webp"/> <source class="responsive-img-srcset" media="(max-width: 1400px)" srcset="/assets/img/blog/flower.webp-1400.webp"/> <img src="/assets/img/blog/flower.webp" class="img-fluid rounded z-depth-1" width="700" height="auto" title="kojo creations" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture> </figure> </div> <hr/> <h3 id="support-for-declarative-animations">Support for declarative animations</h3> <p>Kojo now has support for animations based on Transitions and Timelines. Here’s some sample code for a Transition based animation:</p> <div class="language-scala highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nf">cleari</span><span class="o">()</span>
<span class="nf">drawStage</span><span class="o">(</span><span class="n">white</span><span class="o">)</span>
 
<span class="c1">// pic to be animated</span>
<span class="k">def</span> <span class="nf">pic</span> <span class="k">=</span> <span class="nv">Picture</span><span class="o">.</span><span class="py">rectangle</span><span class="o">(</span><span class="mi">100</span><span class="o">,</span> <span class="mi">50</span><span class="o">)</span>
 
<span class="c1">// the properties within the animation state</span>
<span class="k">def</span> <span class="nf">xProp</span><span class="o">(</span><span class="n">s</span><span class="k">:</span> <span class="kt">Seq</span><span class="o">[</span><span class="kt">Double</span><span class="o">])</span> <span class="k">=</span> <span class="nf">s</span><span class="o">(</span><span class="mi">0</span><span class="o">)</span>
<span class="k">def</span> <span class="nf">yProp</span><span class="o">(</span><span class="n">s</span><span class="k">:</span> <span class="kt">Seq</span><span class="o">[</span><span class="kt">Double</span><span class="o">])</span> <span class="k">=</span> <span class="nf">s</span><span class="o">(</span><span class="mi">1</span><span class="o">)</span>
<span class="k">def</span> <span class="nf">hueProp</span><span class="o">(</span><span class="n">s</span><span class="k">:</span> <span class="kt">Seq</span><span class="o">[</span><span class="kt">Double</span><span class="o">])</span> <span class="k">=</span> <span class="nf">s</span><span class="o">(</span><span class="mi">2</span><span class="o">)</span>
<span class="k">def</span> <span class="nf">scaleProp</span><span class="o">(</span><span class="n">s</span><span class="k">:</span> <span class="kt">Seq</span><span class="o">[</span><span class="kt">Double</span><span class="o">])</span> <span class="k">=</span> <span class="nf">s</span><span class="o">(</span><span class="mi">3</span><span class="o">)</span>
 
<span class="c1">// makes a pic for the given animation state</span>
<span class="k">def</span> <span class="nf">makePic</span><span class="o">(</span><span class="n">s</span><span class="k">:</span> <span class="kt">Seq</span><span class="o">[</span><span class="kt">Double</span><span class="o">])</span> <span class="k">=</span> <span class="o">{</span>
    <span class="nf">fillColor</span><span class="o">(</span><span class="nv">cm</span><span class="o">.</span><span class="py">hsl</span><span class="o">(</span><span class="nf">hueProp</span><span class="o">(</span><span class="n">s</span><span class="o">),</span> <span class="mi">1</span><span class="o">,</span> <span class="mf">0.5</span><span class="o">))</span> <span class="o">*</span>
        <span class="nf">trans</span><span class="o">(</span><span class="nf">xProp</span><span class="o">(</span><span class="n">s</span><span class="o">),</span> <span class="nf">yProp</span><span class="o">(</span><span class="n">s</span><span class="o">))</span> <span class="o">*</span>
        <span class="nf">scale</span><span class="o">(</span><span class="nf">scaleProp</span><span class="o">(</span><span class="n">s</span><span class="o">))</span> <span class="o">-&gt;</span>
        <span class="n">pic</span>
<span class="o">}</span>
 
<span class="c1">// animation definition</span>
<span class="k">val</span> <span class="nv">anim</span> <span class="k">=</span> <span class="nc">Transition</span><span class="o">(</span>
    <span class="mi">2</span><span class="o">,</span> <span class="c1">// duration</span>
    <span class="nc">Seq</span><span class="o">(</span><span class="mi">0</span><span class="o">,</span> <span class="mi">100</span><span class="o">,</span> <span class="mi">0</span><span class="o">,</span> <span class="mi">1</span><span class="o">),</span> <span class="c1">// initial state</span>
    <span class="nc">Seq</span><span class="o">(</span><span class="mi">300</span><span class="o">,</span> <span class="mi">50</span><span class="o">,</span> <span class="mi">240</span><span class="o">,</span> <span class="mf">0.7</span><span class="o">),</span> <span class="c1">// final state</span>
    <span class="nv">easing</span><span class="o">.</span><span class="py">QuadInOut</span><span class="o">,</span> <span class="c1">// how animation moves from initial to final state </span>
    <span class="n">makePic</span><span class="o">,</span> <span class="c1">// a function to make a pic for the current state</span>
    <span class="kc">false</span> <span class="c1">// hide when done?</span>
<span class="o">)</span>
 
<span class="c1">// run the animation</span>
<span class="nf">run</span><span class="o">(</span><span class="n">anim</span><span class="o">)</span>
</code></pre></div></div> <p>The basic idea with transition based animations (as shown in the code above and described below) is the following:</p> <ul> <li>You define a picture that you want to animate.</li> <li>You define the state of your animation. This consists of properties of the animation picture that change over the course of the animation.</li> <li>The animation state is a sequence of doubles. It’s up to you to interpret these doubles however you want. You can do this is a principled way by defining property functions that pick out the relevant double value from the state sequence.</li> <li>You define a function that can make an animation frame/picture for you for any given state.</li> <li>You then define the actual animation, with a duration, a start state, an end state, an easing function, and the frame making function from the previous step. <ul> <li>The easing function defines how Kojo interpolates your animation state from the start state to the end state. Kojo comes with many predefined easing funtions.</li> </ul> </li> <li>Finally you run the animation!</li> </ul> <p>Once you have one or more animation definitions, you can do the following:</p> <ul> <li>Reverse an animation to create a new animation that does the given animation in reverse.</li> <li>Do <code class="language-plaintext highlighter-rouge">anim.repeated(count)</code> to create a new animation that does the given animation repeatedly for the given number of times.</li> <li>Combine animations using <code class="language-plaintext highlighter-rouge">animSeq</code> – to create a new animations that does the given animations one after the other.</li> <li>Combine animations using <code class="language-plaintext highlighter-rouge">animPar</code> – to create a new animations that does the given animations concurrently.</li> </ul> <p>The above describes a Transition based animation. If what you want to do is difficult with a Transition, you can use a Timeline. A Timeline differs from a Transition in the following important way:</p> <p>Instead of being able to specify only an initial and a final state for an animation, you can specify states over the whole lifecycle of the animation using key-frames.</p> <p>More on this and other aspects of the animation feature in a future blog post. For now, let me finish off this section with a quick couple of animations submitted by students – after a few sessions of coding with this feature:</p> <div class="text-center m-4"> <a href="https://vimeo.com/739377144"> <figure> <picture> <source class="responsive-img-srcset" media="(max-width: 480px)" srcset="/assets/img/blog/car-animation-480.webp"/> <source class="responsive-img-srcset" media="(max-width: 800px)" srcset="/assets/img/blog/car-animation-800.webp"/> <source class="responsive-img-srcset" media="(max-width: 1400px)" srcset="/assets/img/blog/car-animation-1400.webp"/> <img src="/assets/img/blog/car-animation.png" class="img-fluid rounded z-depth-1" width="600" height="auto" title="car animation" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture> </figure> </a> </div> <div class="text-center m-4"> <a href="https://vimeo.com/739989054"> <figure> <picture> <source class="responsive-img-srcset" media="(max-width: 480px)" srcset="/assets/img/blog/flight-animation-480.webp"/> <source class="responsive-img-srcset" media="(max-width: 800px)" srcset="/assets/img/blog/flight-animation-800.webp"/> <source class="responsive-img-srcset" media="(max-width: 1400px)" srcset="/assets/img/blog/flight-animation-1400.webp"/> <img src="/assets/img/blog/flight-animation.png" class="img-fluid rounded z-depth-1" width="600" height="auto" title="car animation" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture> </figure> </a> </div> <p>Many thanks (once again!) to Anay Kamat from the Goa government’s <em>CM-CARES</em> team for his contributions to this feature. And many thanks (once again!) to the <em>Kojo Code Hackers</em> group of students for their experiments and feedback with this feature.</p> <hr/> <h3 id="the-kojo-code-exchange--a-new-website">The Kojo code exchange – a new website</h3> <p>The Kojo code exchange is a site where users of Kojo can share their creations. Earlier this year, we released a new version of this site. This cut makes it easier to display your creations and enjoy and learn from the creations of others.</p> <p>Here’s a quick screenshot of the new site:</p> <div class="text-center mt-4 mb-4"> <figure> <picture> <source class="responsive-img-srcset" media="(max-width: 480px)" srcset="/assets/img/blog/codex.webp-480.webp"/> <source class="responsive-img-srcset" media="(max-width: 800px)" srcset="/assets/img/blog/codex.webp-800.webp"/> <source class="responsive-img-srcset" media="(max-width: 1400px)" srcset="/assets/img/blog/codex.webp-1400.webp"/> <img src="/assets/img/blog/codex.webp" class="img-fluid rounded z-depth-1" width="700" height="auto" title="codex" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture> </figure> </div> <p>Take a minute or two to browse the pages of the site and view the numerous interesting creations there! Many thanks to Vasu Sethia and Anusha Pant for their contributions to the code exchange website.</p> <hr/> <h3 id="kojo-in-the-goa-government-curriculum--an-update">Kojo in the Goa government curriculum – an update</h3> <p>The Goa Government has released a teacher’s handbook for grade 7 for Coding/ICT. Kojo features prominently in the book:</p> <div class="text-center mt-4 mb-4"> <a href="/assets/pdf/Goa-Std-7-Regular.pdf"> <figure> <picture> <source class="responsive-img-srcset" media="(max-width: 480px)" srcset="/assets/img/blog/ict-handbook-480.webp"/> <source class="responsive-img-srcset" media="(max-width: 800px)" srcset="/assets/img/blog/ict-handbook-800.webp"/> <source class="responsive-img-srcset" media="(max-width: 1400px)" srcset="/assets/img/blog/ict-handbook-1400.webp"/> <img src="/assets/img/blog/ict-handbook.png" class="img-fluid rounded z-depth-1" width="700" height="auto" title="kojo book" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture> </figure> </a> </div> <p>I’m looking forward to some exciting action with Kojo in Goa over the next few years (especially after seeing some of the <a href="https://codex.kogics.net/codesketch?sketchId=1853">wonderful</a> <a href="https://codex.kogics.net/codesketch?sketchId=1968">creations</a> by Goan teachers and students on the Kojo Code Exchange).</p> <hr/> <h3 id="turkish-enhancements">Turkish enhancements</h3> <p>Bulent Basaran has been busy refining the Turkish translation of Kojo and adding more and more features to it. I will request him to provide an update in a guest blog post here. In the meantime, take a look at his commits – and be impressed 😉 :</p> <p>https://github.com/litan/kojo/commits?author=bulent2k2</p> <hr/> <h3 id="other-miscellaneous-enhancements">Other miscellaneous enhancements</h3> <p>There have been many other enhancements since the last release announcement. Some of these include:</p> <ul> <li>Chess support contributed by Ida Rasmark and the team at Lund University. More on this in a future blog post.</li> <li>Code completion improvements.</li> <li>Breakpoint pane improvements.</li> <li>New commands for animation loops that run in a more functional way – without the need for mutable variables.</li> <li>A <em>Look and Feel</em> upgrade.</li> <li>A Java upgrade.</li> <li>And more…</li> </ul> <hr/> <p>That’s it for now…</p> <p>As always, the new version of Kojo is available from the Kojo Download Page. If you run into any difficulties, let us know.</p> <p>Enjoy!</p>]]></content><author><name></name></author><category term="kojo"/><category term="announce"/><summary type="html"><![CDATA[Kojo has a new release]]></summary></entry><entry><title type="html">Blog migration</title><link href="https://www.kogics.net/blog/2022/migration/" rel="alternate" type="text/html" title="Blog migration"/><published>2022-08-15T15:09:00+00:00</published><updated>2022-08-15T15:09:00+00:00</updated><id>https://www.kogics.net/blog/2022/migration</id><content type="html" xml:base="https://www.kogics.net/blog/2022/migration/"><![CDATA[<p>The Kojo blog has moved from <a href="https://kojoenv.wordpress.com/">it’s Wordpress location</a> to <a href="/blog/">this website</a>.</p> <p>All the earlier posts from 2010 to 2022 are still available on the <a href="https://kojoenv.wordpress.com/">previous Wordpress blog</a>.</p>]]></content><author><name></name></author><category term="kojo"/><summary type="html"><![CDATA[The Kojo blog has moved here]]></summary></entry></feed>