<?xml version="1.0" encoding="UTF-8"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
    <title> - Rust</title>
    <link rel="self" type="application/atom+xml" href="https://jangermad.srht.site/topics/rust/atom.xml"/>
    <link rel="alternate" type="text/html" href="https://jangermad.srht.site/"/>
    <generator uri="https://www.getzola.org/">Zola</generator>
    <updated>2026-09-28T00:00:00+00:00</updated>
    <id>https://jangermad.srht.site/topics/rust/atom.xml</id>
    <entry xml:lang="en">
        <title>How Rust made me Roll</title>
        <published>2026-09-28T00:00:00+00:00</published>
        <updated>2026-09-28T00:00:00+00:00</updated>
        
        <author>
          <name>Jengamon</name>
        </author>
        
        <link rel="alternate" type="text/html" href="https://jangermad.srht.site/blog/language-of-interfaces/"/>
        <id>https://jangermad.srht.site/blog/language-of-interfaces/</id>
        
        <content type="html" xml:base="https://jangermad.srht.site/blog/language-of-interfaces/">&lt;p&gt;I’ve seen a number of blog and forum posts about difficulties with Rust and the things it forces you learn about, so
I wanted to share a happy accident, where the systems of Rust pushed me into creating something that I &lt;em&gt;really&lt;/em&gt; like in
hindsight.&lt;/p&gt;
&lt;h2 id=&quot;so-what-was-it&quot;&gt;&lt;a class=&quot;zola-anchor&quot; href=&quot;#so-what-was-it&quot; aria-label=&quot;Anchor link for: so-what-was-it&quot;&gt;So, What Was It?&lt;/a&gt;&lt;/h2&gt;
&lt;p&gt;I was prototyping a fighting game&lt;sup class=&quot;footnote-reference&quot; id=&quot;fr-1-1&quot;&gt;&lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fn-1&quot;&gt;[1]&lt;/a&gt;&lt;/sup&gt; in Bevy with my (current) massive amount of free time&lt;sup class=&quot;footnote-reference&quot; id=&quot;fr-2-1&quot;&gt;&lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fn-2&quot;&gt;[2]&lt;/a&gt;&lt;/sup&gt;, so I copied my
template and started working. A &lt;em&gt;big&lt;/em&gt; concept in this type of game is input buffering: inputs are stored
over a number of frames, and at fixed times read to determine the game actions to execute.&lt;/p&gt;
&lt;p&gt;I wrote the input buffer code so that I can tweak and adjust the amount of frames stored in the buffer
without changing the code&lt;sup class=&quot;footnote-reference&quot; id=&quot;fr-3-1&quot;&gt;&lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fn-3&quot;&gt;[3]&lt;/a&gt;&lt;/sup&gt;:&lt;/p&gt;
&lt;pre class=&quot;giallo&quot; style=&quot;color: #CDD6F4; background-color: #1E1E2E;&quot; &gt;&lt;code data-lang=&quot;rust&quot;&gt;&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;#&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;[&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;derive&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;(&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;Component&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; Debug&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;)]&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;pub struct&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; InputBuffer&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;const&lt;/span&gt;&lt;span style=&quot;color: #FAB387;&quot;&gt; N&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;:&lt;/span&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt; usize&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; T&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt; {&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;    /// The *accumlating* input. Invisible to the rest of game state.&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;    pub&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;(&lt;/span&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;crate&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;)&lt;/span&gt;&lt;span&gt; current&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;:&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; T&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;    pub&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;(&lt;/span&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;crate&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;)&lt;/span&gt;&lt;span&gt; buffer&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;:&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt; [&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;T&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; N&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;],&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;}&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;then I added code to handle the buffering operations: accumulating input for the “next” frame, and updating the
buffer, resetting the accumulator in the process:&lt;/p&gt;
&lt;pre class=&quot;giallo&quot; style=&quot;color: #CDD6F4; background-color: #1E1E2E;&quot; &gt;&lt;code data-lang=&quot;rust&quot;&gt;&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;impl&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;const&lt;/span&gt;&lt;span style=&quot;color: #FAB387;&quot;&gt; N&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;:&lt;/span&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt; usize&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; T&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;:&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; Copy&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt; +&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; Default&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; InputBuffer&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;N&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; T&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt; {&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;  /// Get the next state of input (for accumulation)&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;  pub fn&lt;/span&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt; next&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;(&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;&amp;amp;&lt;/span&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;mut&lt;/span&gt;&lt;span style=&quot;color: #F38BA8;&quot;&gt; self&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;)&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt; -&amp;gt; &amp;amp;&lt;/span&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;mut&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; T&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt; {&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;      &amp;amp;&lt;/span&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;mut&lt;/span&gt;&lt;span style=&quot;color: #F38BA8;&quot;&gt; self&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;.&lt;/span&gt;&lt;span&gt;current&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;  }&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;  /// Update the input buffer&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;  pub fn&lt;/span&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt; update&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;(&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;&amp;amp;&lt;/span&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;mut&lt;/span&gt;&lt;span style=&quot;color: #F38BA8;&quot;&gt; self&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;) {&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;      // shift up previous inputs&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #F38BA8;&quot;&gt;      self&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;.&lt;/span&gt;&lt;span&gt;buffer&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;.&lt;/span&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt;copy_within&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;(&lt;/span&gt;&lt;span style=&quot;color: #FAB387;&quot;&gt;1&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;..&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;N&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;span style=&quot;color: #FAB387;&quot;&gt; 0&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;);&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;      // copy the accumulating input into the last position&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #F38BA8;&quot;&gt;      self&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;.&lt;/span&gt;&lt;span&gt;buffer&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;[&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;N&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt; -&lt;/span&gt;&lt;span style=&quot;color: #FAB387;&quot;&gt; 1&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;]&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt; =&lt;/span&gt;&lt;span style=&quot;color: #F38BA8;&quot;&gt; self&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;.&lt;/span&gt;&lt;span&gt;current&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;      // clear accumulating input&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #F38BA8;&quot;&gt;      self&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;.&lt;/span&gt;&lt;span&gt;current &lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;=&lt;/span&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt; default&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;();&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;  }&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;  // more c*de goes here...&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;}&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;Writing the buffer this way allows me to use one of Rust’s main
strengths: the ability to write code that is agnostic to future use. The plan is to eventually just add this to
my template,
and never have to write another input buffer again&lt;sup class=&quot;footnote-reference&quot; id=&quot;fr-5-1&quot;&gt;&lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fn-5&quot;&gt;[4]&lt;/a&gt;&lt;/sup&gt;~&lt;/p&gt;
&lt;p&gt;Then came the problem: how do I read the buffer?&lt;/p&gt;
&lt;h2 id=&quot;reading-the-buffer&quot;&gt;&lt;a class=&quot;zola-anchor&quot; href=&quot;#reading-the-buffer&quot; aria-label=&quot;Anchor link for: reading-the-buffer&quot;&gt;Reading the Buffer&lt;/a&gt;&lt;/h2&gt;
&lt;p&gt;Having all the inputs in one place is all fine and dandy, but to do the game part of the game, you have to be able to
&lt;em&gt;read&lt;/em&gt; those inputs.&lt;/p&gt;
&lt;p&gt;A naïve solution would be to expose the buffer for outside code to read and understand the inputs
themselves, but that would lead to maintenance hell, where wanting to change how an input is read would require
going to every place where the buffer is being read and changing it, not to mention the effort it would take
to add a &lt;em&gt;new&lt;/em&gt; input after-the-fact.&lt;/p&gt;
&lt;p&gt;This is a good place for reification&lt;sup class=&quot;footnote-reference&quot; id=&quot;fr-21-1&quot;&gt;&lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fn-21&quot;&gt;[5]&lt;/a&gt;&lt;/sup&gt;:  give the buffer a bunch of things we want to
see in some sequence, and the buffer tells you if it found it or not.&lt;/p&gt;
&lt;pre class=&quot;giallo&quot; style=&quot;color: #CDD6F4; background-color: #1E1E2E;&quot; &gt;&lt;code data-lang=&quot;rust&quot;&gt;&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;// A type that can be matched to an input&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;pub trait&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; InputMatcher&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;T&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt; {&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;    fn&lt;/span&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt; matches&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;(&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;        &amp;amp;&lt;/span&gt;&lt;span style=&quot;color: #F38BA8;&quot;&gt;self&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #EBA0AC;&quot;&gt;        input&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;: &amp;amp;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;T&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;    )&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt; -&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; bool&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;;&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;#&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;[&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;derive&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;(&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;Debug&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;)]&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;pub enum&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; SequencedAction&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;&amp;#39;&lt;/span&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt;a&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; C&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt; {&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;  // ...borrows of input matchers with variants about where to&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;  // search in the buffer for the input matcher&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;impl&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;const&lt;/span&gt;&lt;span style=&quot;color: #FAB387;&quot;&gt; N&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;:&lt;/span&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt; usize&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; T&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;:&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;&quot;&gt; std&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;::&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;&quot;&gt;fmt&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;::&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;Debug&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; InputBuffer&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;N&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; T&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt; {&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;    /// Check if this buffer represents an execution of a sequence of inputs&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;    pub fn&lt;/span&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt; matches&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;&amp;#39;&lt;/span&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt;a&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; C&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;:&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; InputMatcher&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;T&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt; +&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt; &amp;#39;&lt;/span&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt;a&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;(&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;        &amp;amp;&lt;/span&gt;&lt;span style=&quot;color: #F38BA8;&quot;&gt;self&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #EBA0AC;&quot;&gt;        first_action&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;: &amp;amp;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;&amp;#39;&lt;/span&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt;a&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; C&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #EBA0AC;&quot;&gt;        sequence&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;: &amp;amp;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;[&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;SequencedAction&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;&amp;#39;&lt;/span&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt;a&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; C&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;],&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;    )&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt; -&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; bool&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;    {&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;      // code not reproduced here...&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;    }&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;}&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;
&lt;blockquote&gt;
&lt;p&gt;Wait, since &lt;code&gt;C&lt;/code&gt; is always behind a borrow, do we need to know its size?&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h2 id=&quot;why-ask&quot;&gt;&lt;a class=&quot;zola-anchor&quot; href=&quot;#why-ask&quot; aria-label=&quot;Anchor link for: why-ask&quot;&gt;Why Ask?&lt;/a&gt;&lt;/h2&gt;
&lt;p&gt;Rust provides lots of interfaces to reason about assumptions. &lt;a class=&quot;external-link&quot; rel=&quot;noreferrer external&quot; href=&quot;https://doc.rust-lang.org/std/marker/trait.Sized.html&quot;&gt;Sized&lt;/a&gt; is one of them and is put on everything
that the Rust compiler can tell has a fixed size at compile time&lt;sup class=&quot;footnote-reference&quot; id=&quot;fr-8-1&quot;&gt;&lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fn-8&quot;&gt;[6]&lt;/a&gt;&lt;/sup&gt;.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Rust loves putting things on the stack.&lt;/li&gt;
&lt;li&gt;To put something on the stack, you need to know its size at compile time.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;So to simplify the language, type parameters have an implicit &lt;code&gt;+ Sized&lt;/code&gt; bound.
However, a parameter can opt-out of this by explicitly adding a &lt;code&gt;+ ?Sized&lt;/code&gt; bound,
which enables trait objects (&lt;code&gt;dyn Trait&lt;/code&gt;) to be used as an argument.&lt;/p&gt;
&lt;p&gt;We always works with input matchers through a reference&lt;sup class=&quot;footnote-reference&quot; id=&quot;fr-22-1&quot;&gt;&lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fn-22&quot;&gt;[7]&lt;/a&gt;&lt;/sup&gt;, which are always &lt;code&gt;Sized&lt;/code&gt; even if the type they are
reference is not, so I added the &lt;code&gt;+ ?Sized&lt;/code&gt; bound, which allows &lt;code&gt;C&lt;/code&gt; to be &lt;code&gt;dyn InputMatcher&amp;lt;T&amp;gt;&lt;/code&gt;:&lt;/p&gt;
&lt;pre class=&quot;giallo&quot; style=&quot;color: #CDD6F4; background-color: #1E1E2E;&quot; &gt;&lt;code data-lang=&quot;rust&quot;&gt;&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;// earlier code...&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;#&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;[&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;derive&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;(&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;Debug&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;)]&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;pub enum&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; SequencedAction&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;&amp;#39;&lt;/span&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt;a&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; C&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;: ?&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;Sized&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt; {&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;  // ...borrows of input matchers with variants about where to&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;  // search in the buffer for the input matcher&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;impl&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;const&lt;/span&gt;&lt;span style=&quot;color: #FAB387;&quot;&gt; N&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;:&lt;/span&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt; usize&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; T&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;:&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;&quot;&gt; std&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;::&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;&quot;&gt;fmt&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;::&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;Debug&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; InputBuffer&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;N&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; T&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt; {&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;    /// Check if this buffer represents an execution of a sequence of inputs&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;    pub fn&lt;/span&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt; matches&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;&amp;#39;&lt;/span&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt;a&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; C&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;:&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; InputMatcher&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;T&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt; + ?&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;Sized&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt; +&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt; &amp;#39;&lt;/span&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt;a&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;(&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;        &amp;amp;&lt;/span&gt;&lt;span style=&quot;color: #F38BA8;&quot;&gt;self&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #EBA0AC;&quot;&gt;        first_action&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;: &amp;amp;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;&amp;#39;&lt;/span&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt;a&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; C&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #EBA0AC;&quot;&gt;        sequence&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;: &amp;amp;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;[&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;SequencedAction&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;&amp;#39;&lt;/span&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt;a&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; C&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;],&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;    )&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt; -&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; bool&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;    {&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;      // code not reproduced here either...&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;    }&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;}&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;So I wrote up some tests&lt;sup class=&quot;footnote-reference&quot; id=&quot;fr-9-1&quot;&gt;&lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fn-9&quot;&gt;[8]&lt;/a&gt;&lt;/sup&gt;, and was about move on with my day until I remembered: wait, how &lt;em&gt;do&lt;/em&gt; I specify my inputs?&lt;/p&gt;
&lt;h2 id=&quot;what-are-you-on-about&quot;&gt;&lt;a class=&quot;zola-anchor&quot; href=&quot;#what-are-you-on-about&quot; aria-label=&quot;Anchor link for: what-are-you-on-about&quot;&gt;What are you on about?&lt;/a&gt;&lt;/h2&gt;
&lt;p&gt;This reified matcher system is good on the buffer side: when I want to create a new input that can be read from
the buffer, how the buffer matches that input doesn’t change and it automatically works with all ways to sequence
buffer checks that already exist.&lt;/p&gt;
&lt;p&gt;&lt;em&gt;But how do I make the inputs to this function in the first place?&lt;/em&gt;&lt;/p&gt;
&lt;p&gt;The most straightforward, common, right-in-your-face solution is to stick them all into an enum and call it a day:&lt;/p&gt;
&lt;pre class=&quot;giallo&quot; style=&quot;color: #CDD6F4; background-color: #1E1E2E;&quot; &gt;&lt;code data-lang=&quot;rust&quot;&gt;&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;// b/c fighting game, assume &amp;quot;Numpad&amp;quot; and &amp;quot;Button&amp;quot; are inputs that read the joystick and button state&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;// respectively&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;enum&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; FrameInput&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt; {&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt;  Button&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;(&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;Button&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;),&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt;  Numpad&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;(&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;Numpad&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;),&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;  // more as necessary...&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;}&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;impl&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; InputMatcher&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;InputFrame&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt; for&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; FrameInput&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt; {&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;  // ..use a match, and delegate to the wrapped input&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;}&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;I didn’t want to do that because:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;the problem is just shifted up one layer: how do I make &lt;code&gt;FrameInput&lt;/code&gt;s?&lt;/li&gt;
&lt;li&gt;I don’t want to solve this using serde b/c that seems verbose for an input system&lt;/li&gt;
&lt;li&gt;if I &lt;em&gt;were&lt;/em&gt; to use serde, how do I represent &lt;code&gt;SequencedAction&lt;/code&gt;?&lt;/li&gt;
&lt;li&gt;in a fighting game, the input’s relation to a frame’s data changes as a result of game state
(a player is player 2, after all). How do I track that in this system?&lt;sup class=&quot;footnote-reference&quot; id=&quot;fr-10-1&quot;&gt;&lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fn-10&quot;&gt;[9]&lt;/a&gt;&lt;/sup&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;but I support &lt;em&gt;trait objects&lt;/em&gt; for &lt;code&gt;C&lt;/code&gt;! There has to be a better way, there &lt;em&gt;has&lt;/em&gt; to be…&lt;/p&gt;
&lt;div style=&quot;font-weight:bold;letter-spacing:100%;font-size:2rem;text-align:center;&quot;&gt;S T R I N G&lt;/div&gt;
&lt;h2 id=&quot;lexing-a-string&quot;&gt;&lt;a class=&quot;zola-anchor&quot; href=&quot;#lexing-a-string&quot; aria-label=&quot;Anchor link for: lexing-a-string&quot;&gt;Lexing a String&lt;/a&gt;&lt;/h2&gt;
&lt;p&gt;At the end of the day, serde is just a parser for a string&lt;sup class=&quot;footnote-reference&quot; id=&quot;fr-11-1&quot;&gt;&lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fn-11&quot;&gt;[10]&lt;/a&gt;&lt;/sup&gt;.&lt;/p&gt;
&lt;p&gt;A parser is just a way to convert an input format into an output format.&lt;/p&gt;
&lt;p&gt;&lt;a class=&quot;external-link&quot; rel=&quot;noreferrer external&quot; href=&quot;https://docs.rs/unscanny/latest/unscanny/&quot;&gt;unscanny&lt;/a&gt; exists.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;Why don’t &lt;em&gt;I&lt;/em&gt; make the string parser?&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;I’ve done it so many times before for fun, this won’t be too bad, and to my surprise, it &lt;em&gt;wasn’t&lt;/em&gt;.&lt;/p&gt;
&lt;p&gt;The interface would look like this:&lt;/p&gt;
&lt;pre class=&quot;giallo&quot; style=&quot;color: #CDD6F4; background-color: #1E1E2E;&quot; &gt;&lt;code data-lang=&quot;rust&quot;&gt;&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;pub fn&lt;/span&gt;&lt;span style=&quot;color: #89B4FA;font-style: italic;&quot;&gt; buffer_matches_input&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt;const&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; N&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;:&lt;/span&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt; usize&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;(&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #EBA0AC;&quot;&gt;    buffer&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;: &amp;amp;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;&quot;&gt;input&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;::&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;InputBuffer&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;N&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; InputFrame&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #EBA0AC;&quot;&gt;    input&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt;:&lt;/span&gt;&lt;span style=&quot;color: #CBA6F7;&quot;&gt; impl&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; AsRef&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;str&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;,&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;)&lt;/span&gt;&lt;span style=&quot;color: #94E2D5;&quot;&gt; -&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt; Option&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;lt;&lt;/span&gt;&lt;span style=&quot;color: #F9E2AF;font-style: italic;&quot;&gt;bool&lt;/span&gt;&lt;span style=&quot;color: #89DCEB;&quot;&gt;&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt; {&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;font-style: italic;&quot;&gt;  // magic code that&amp;#39;s for me, not for you...&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span style=&quot;color: #9399B2;&quot;&gt;}&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;&lt;a class=&quot;external-link&quot; rel=&quot;noreferrer external&quot; href=&quot;https://docs.rs/bumpalo/latest/bumpalo/&quot;&gt;bumpalo&lt;/a&gt; exists, so I can create an arena to allocate &lt;code&gt;Numpad&lt;/code&gt; and &lt;code&gt;Button&lt;/code&gt; and get a bunch of
&lt;code&gt;&amp;amp;dyn InputMatcher&amp;lt;InputFrame&amp;gt;&lt;/code&gt;, then use those references as arguments to the matcher system, with
other characters representing the way that the next input should be sequenced.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;None&lt;/code&gt; means the input string’s bad, either:
&lt;ul&gt;
&lt;li&gt;an input isn’t seen where it should be (after a sequencer character)&lt;/li&gt;
&lt;li&gt;there is no initial input, which is required&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;code&gt;Some(found)&lt;/code&gt; means the input string was successfully understood, and returns the buffer’s answer&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;A bit of lexer writing later, and I had to take a moment when I tested the first input string &lt;code&gt;2&amp;gt;3&amp;gt;6&lt;/code&gt;&lt;sup class=&quot;footnote-reference&quot; id=&quot;fr-23-1&quot;&gt;&lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fn-23&quot;&gt;[11]&lt;/a&gt;&lt;/sup&gt;.&lt;/p&gt;
&lt;p&gt;Taking the arena as a parameter (to enable reuse) also had me adding a flag to flip inputs,
and with no change on the lexing side, all of a sudden, the string format worked for both player 1
&lt;em&gt;and&lt;/em&gt; player 2 as expected.&lt;/p&gt;
&lt;h2 id=&quot;the-upshot&quot;&gt;&lt;a class=&quot;zola-anchor&quot; href=&quot;#the-upshot&quot; aria-label=&quot;Anchor link for: the-upshot&quot;&gt;The Upshot&lt;/a&gt;&lt;/h2&gt;
&lt;p&gt;In combination with loading assets in Bevy with hot-reload enabled, I felt like crying tears of joy when I could
experiment with
different inputs &lt;em&gt;without even restarting the game&lt;/em&gt;&lt;sup class=&quot;footnote-reference&quot; id=&quot;fr-16-1&quot;&gt;&lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fn-16&quot;&gt;[12]&lt;/a&gt;&lt;/sup&gt;.&lt;/p&gt;
&lt;p&gt;Here I was, feeling that I’ve been struggling against a
language and engine when this system just randomly fell into my lap, making me realize:
oh, when it works, &lt;em&gt;it works&lt;/em&gt;.&lt;/p&gt;
&lt;p&gt;I would eventually:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;add new inputs&lt;/li&gt;
&lt;li&gt;add a couple new sequences&lt;/li&gt;
&lt;li&gt;add a way to request only matching on a subslice of the buffer&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;and the rest of the code didn’t change much. No need to add and handle new variants, figure out
how to recombined data. It just wa really easy to update&lt;sup class=&quot;footnote-reference&quot; id=&quot;fr-17-1&quot;&gt;&lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fn-17&quot;&gt;[13]&lt;/a&gt;&lt;/sup&gt;.&lt;/p&gt;
&lt;p&gt;This was a story about me taking a reified input system, and somehow rolling myself into simplicity.&lt;/p&gt;
&lt;p&gt;The naive input frame solution would have looked something like:&lt;/p&gt;
&lt;pre class=&quot;giallo&quot; style=&quot;color: #CDD6F4; background-color: #1E1E2E;&quot; &gt;&lt;code data-lang=&quot;plain&quot;&gt;&lt;span class=&quot;giallo-l&quot;&gt;&lt;span&gt;{&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span&gt;  first_input: Numpad(Num2),&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span&gt;  sequence: [&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span&gt;    Next {&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span&gt;      input: Numpad(Num3),&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span&gt;      range: [0, 3],&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span&gt;    },&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span&gt;    Next {&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span&gt;      input: Numpad(Num6),&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span&gt;    },&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span&gt;  ]&lt;/span&gt;&lt;/span&gt;
&lt;span class=&quot;giallo-l&quot;&gt;&lt;span&gt;}&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;where with this system, I can just write &lt;code&gt;2&amp;gt;(..3)3&amp;gt;6&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;This isn’t impossible in other languagesby far, I just think it kinda funny that I just kinda fell onto this
solution because it was “easy”&lt;sup class=&quot;footnote-reference&quot; id=&quot;fr-18-1&quot;&gt;&lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fn-18&quot;&gt;[14]&lt;/a&gt;&lt;/sup&gt;.&lt;/p&gt;
&lt;p&gt;My favorite thing about this situation is that now that I’ve figured out how to do this, I can
just copy-paste it, tweak it a bit, switch out the input frame type, and it’s ready to go for a different game.
And this all happened in one day 🤣.&lt;/p&gt;
&lt;section class=&quot;footnotes&quot;&gt;
&lt;ol class=&quot;footnotes-list&quot;&gt;
&lt;li id=&quot;fn-1&quot;&gt;
&lt;p&gt;as one does… &lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fr-1-1&quot;&gt;↩&lt;/a&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li id=&quot;fn-2&quot;&gt;
&lt;p&gt;if job have, pls contact me &lt;a href=&quot;mailto:sad.dust8020@fastmail.com&quot;&gt;here&lt;/a&gt; &lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fr-2-1&quot;&gt;↩&lt;/a&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li id=&quot;fn-3&quot;&gt;
&lt;p&gt;there’s code to ensure that N isn’t 0 in the constructor function &lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fr-3-1&quot;&gt;↩&lt;/a&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li id=&quot;fn-5&quot;&gt;
&lt;p&gt;the code that I use for controlling the camera is a result of this process: I isolated a pattern I liked and
stuck it in a module to never have to write the initial code for it again. &lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fr-5-1&quot;&gt;↩&lt;/a&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li id=&quot;fn-21&quot;&gt;
&lt;p&gt;&lt;a class=&quot;external-link&quot; rel=&quot;noreferrer external&quot; href=&quot;https://gameprogrammingpatterns.com/command.html&quot;&gt;Here&lt;/a&gt; is a good explanation. I know of the book, have the book, and
have read bits and pieces of the book except for the bytecode chapter. I have read that one chapter back to
front, and think about it a lot. &lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fr-21-1&quot;&gt;↩&lt;/a&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li id=&quot;fn-8&quot;&gt;
&lt;p&gt;generally, see &lt;a class=&quot;external-link&quot; rel=&quot;noreferrer external&quot; href=&quot;https://doc.rust-lang.org/std/marker/trait.Sized.html&quot;&gt;the docs&lt;/a&gt; for more info &lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fr-8-1&quot;&gt;↩&lt;/a&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li id=&quot;fn-22&quot;&gt;
&lt;p&gt;following the “do I need to own it? no. do I need to mutate it? no.” flow of logic when selecting parameter types
in Rust &lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fr-22-1&quot;&gt;↩&lt;/a&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li id=&quot;fn-9&quot;&gt;
&lt;p&gt;having a unit testing solution just built into language packaging is still really cool, helps me with choice
paralysis by not having to think about it, and provides me with one less reason to not test things when I can. &lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fr-9-1&quot;&gt;↩&lt;/a&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li id=&quot;fn-10&quot;&gt;
&lt;p&gt;I thought it was a Good Idea™️ at one point to use an atomic bool to store the current
facing state in… &lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fr-10-1&quot;&gt;↩&lt;/a&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li id=&quot;fn-11&quot;&gt;
&lt;p&gt;we are using the definition of “a fixed size array of UTF-8” for string because we snarf it from Rust &lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fr-11-1&quot;&gt;↩&lt;/a&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li id=&quot;fn-23&quot;&gt;
&lt;p&gt;“QCF” or quarter circle forward. Very common motion input. The syntax I used was based off &lt;a class=&quot;external-link&quot; rel=&quot;noreferrer external&quot; href=&quot;https://glossary.infil.net/?t=Numpad%20Notation&quot;&gt;numpad notation&lt;/a&gt;. &lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fr-23-1&quot;&gt;↩&lt;/a&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li id=&quot;fn-16&quot;&gt;
&lt;p&gt;ig this is why hot reloading is such a big deal, b/c it is &lt;em&gt;such&lt;/em&gt; a great feeling &lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fr-16-1&quot;&gt;↩&lt;/a&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li id=&quot;fn-17&quot;&gt;
&lt;p&gt;the most effort was rewriting the code for matching numpad inputs from a bunch of separate cases into
&lt;code&gt;c @ (&#39;1&#39;..=&#39;9&#39;)&lt;/code&gt;, and indexing a const for the actual input to use, but it wasn’t even bad, like at all. &lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fr-17-1&quot;&gt;↩&lt;/a&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li id=&quot;fn-18&quot;&gt;
&lt;p&gt;a combination of “easy-for-present-me-to-make” and “easy-for-future-me-to-maintain-and-fix” &lt;a href=&quot;https://jangermad.srht.site/blog/language-of-interfaces/#fr-18-1&quot;&gt;↩&lt;/a&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;/section&gt;
</content>
        
    </entry>
</feed>
