46
\$\begingroup\$

Background

Summer is well over in the Northern Hemisphere, and a lot of us miss the sun, the beaches, the waves of the ocean... This challenge aims at cheering them up by reminding them of the sea.

The challenge

Here is the sea :

             **              **              **              **              ** 
         ****            ****            ****            ****            ****   
      *****           *****           *****           *****           *****     
    **   **         **   **         **   **         **   **         **   **     
  **      **      **      **      **      **      **      **      **      **    
**          ******          ******          ******          ******          ****

The sea is made of 5 times this wave pattern :

            **  
        ****    
     *****      
   **   **      
 **      **     
*          *****

Note that the pattern is 16 characters long, and the sea is 5 times this pattern = 80 characters long.

Which you can print into a terminal using this command-line :

perl -e 'print "            **  \n        ****    \n     *****      \n   **   **      \n **      **     \n*          *****\n"'

Or this one :

perl -e 'print " "x12, "*"x2, " "x2, "\n", " "x8, "*"x4, " "x4, "\n", " "x5, "*"x5, " "x6, "\n", " "x3, "*"x2, " "x3, "*"x2, " "x6, "\n", " "x1, "*"x2, " "x6, "*"x2, " "x5, "\n", "*"x1, " "x10, "*"x5, "\n"'

(The second one should make it easier for you to get the exact pattern)

Your task is to display the sea in a terminal, and make look like the waves are moving toward the right : it needs to shift to the right at a speed of 1 character each 100ms (= 10 times each seconds). No character should be printed after the 80th column, but as the rightmost wave disappears, a new one appears on the left.
Here is an example of output :

time = 0.0s

             **              **              **              **              ** 
         ****            ****            ****            ****            ****   
      *****           *****           *****           *****           *****     
    **   **         **   **         **   **         **   **         **   **     
  **      **      **      **      **      **      **      **      **      **    
**          ******          ******          ******          ******          ****

time = 0.1s

              **              **              **              **              **
          ****            ****            ****            ****            ****  
       *****           *****           *****           *****           *****    
     **   **         **   **         **   **         **   **         **   **    
   **      **      **      **      **      **      **      **      **      **   
***          ******          ******          ******          ******          ***

time = 0.2s

*              **              **              **              **              *
           ****            ****            ****            ****            **** 
        *****           *****           *****           *****           *****   
      **   **         **   **         **   **         **   **         **   **   
    **      **      **      **      **      **      **      **      **      **  
****          ******          ******          ******          ******          **

time = 0.3s

**              **              **              **              **              
            ****            ****            ****            ****            ****
         *****           *****           *****           *****           *****  
       **   **         **   **         **   **         **   **         **   **  
     **      **      **      **      **      **      **      **      **      ** 
*****          ******          ******          ******          ******          *

time = 0.4s

 **              **              **              **              **             
*            ****            ****            ****            ****            ***
          *****           *****           *****           *****           ***** 
        **   **         **   **         **   **         **   **         **   ** 
      **      **      **      **      **      **      **      **      **      **
******          ******          ******          ******          ******          

Of course, each output should replace the previous one.

You can run this code into a unix terminal to see how it should look with the animation:

perl -M5.010 -MTime::HiRes=sleep -E '@arr=([($")x12,($n="*")x2,($")x3],[($")x8,($n)x4,($")x4],[($")x5,($n)x5,($")x6],[($")x3,($n)x2,($")x3,($n)x2,($")x6],[($")x1,($n)x2,($")x6,($n)x2,($")x5],[($n)x1,($")x10,($n)x5]);while(++$j){for$i(0..5){for$k(0..15) {$out[$i][16*$_+$k]=$arr[$i][($k-$j)%16]for 0..4}}say"\e[H",$/,join$/,map{join"",@$_}@out;sleep 0.1}'

(Note that this code isn't very well golfed: I just made it compact enough to be convenient to run in a terminal.)

Winning criterion

This is codegolf, so shortest code in byte wins.

\$\endgroup\$
9
  • 2
    \$\begingroup\$ Can we start the animation at any frame? \$\endgroup\$
    – Arnauld
    Commented Dec 9, 2016 at 18:44
  • 2
    \$\begingroup\$ 05ab1e.tryitonline.net/… too bad 05AB1E can't animate, that would've been short. \$\endgroup\$ Commented Dec 9, 2016 at 19:01
  • 2
    \$\begingroup\$ @Arnauld Yes, you can. \$\endgroup\$
    – Dada
    Commented Dec 9, 2016 at 19:02
  • 2
    \$\begingroup\$ Oh, you're right! These are true lambdas \$\endgroup\$
    – Luis Mendo
    Commented Dec 9, 2016 at 19:16
  • 15
    \$\begingroup\$ "Summer is well over" that's very Northern Hemisphere of you. \$\endgroup\$ Commented Dec 9, 2016 at 22:13

24 Answers 24

17
\$\begingroup\$

MATL, 41 40 bytes

`'3SJp/B@Tc`@+ara'F'* 'Za6el&Xx80:@-Z)DT

Example run:

enter image description here

Or try it at MATL Online! (the actual speed may depend on server load).

How it works

`                    % Do...while
  '3SJp/B@Tc`@+ara'  %   Compressed string (actually it's just a change of base)
  F                  %   Push false. Indicates base-95 input alphabet for decompression
  '* '               %   Push this string, which defines output alphabet
  Za                 %   Base conversion. This decompresses the string
  6e                 %   Reshape as a 6-row char array. This gives the basic pattern
  l&Xx               %   Pause 0.1 seconds and clear screen
  80:                %   Push array [1 2 ... 80] 
  @-                 %   Subtract iteration index to each element of that array. This
                     %    will produce the rotation via modular indexing
  Z)                 %   Use as column index. Indexing is modular, so this repeats
                     %   (and rotates) the pattern
  D                  %   Display
  T                  %   True. Loop condition for infinite loop
                     % Implicit end
\$\endgroup\$
17
\$\begingroup\$

JavaScript (ES6) + HTML, 151 143 + 10 = 161 153 bytes

a=[48,15,57347,6147,1542,504];setInterval("a=a.map(n=>{for(x=-1;++x<80;)s+=' *'[n>>x%16&1];s+=`\n`;return n>>>15|n<<1},s='');O.innerHTML=s",99)
<pre id=O>

\$\endgroup\$
2
  • \$\begingroup\$ What is the function of the variable a? \$\endgroup\$
    – user41805
    Commented Dec 9, 2016 at 18:55
  • \$\begingroup\$ @KritixiLithos a holds the binary-encoded wave pattern and is rotated on each frame. So, it can't be hardcoded: it needs to be stored in a variable. \$\endgroup\$
    – Arnauld
    Commented Dec 9, 2016 at 19:00
16
\$\begingroup\$

HTML + CSS, 70 + 181 175 = 245 bytes

Makes use of text-shadow, rtl text and CSS keyframe animations.

a{display:flex;overflow:hidden;width:80ch}pre{text-shadow:16ch 0,32ch 0,48ch 0,64ch 0,80ch 0;direction:rtl;animation:w steps(16)1.6s infinite}@keyframes w{0%{margin-left:-16ch
<a><pre>**
  ****
    *****
    **   **
   **      **
***          ***

\$\endgroup\$
9
\$\begingroup\$

C# 450 444 425 417 Bytes

399 without using System.Linq; but I'm sure that would be cheating...

Edit: Saved 25 Bytes thanks to @Cyoce

Golfed:

void S(){Func<string,string>r=a=>string.Concat(Enumerable.Repeat(a,5));Func<string,int,string>s=(b,i)=>(b.Substring(16-i)+b).Substring(0,80);int p=0;for(;;){Console.Clear();Console.WriteLine(string.Join("\r\n",new string[]{s(r("            **  "),p),s(r("        ****    "),p),s(r("     *****      "),p),s(r(" **      **     "),p),s(r("*          *****"),p),}));Thread.Sleep(100);p++;if(p==16)p=0;}}

Ungolfed:

public void S()
{
  Func<string, string> r = a => string.Concat(Enumerable.Repeat(a, 5));
  Func<string, int, string> s = (b, i) => (b.Substring(16 - i) + b).Substring(0, 80);

  int p = 0;
  for(;;)
  {
    Console.Clear();
    Console.WriteLine(
      string.Join("\r\n", new string[]
    {
      s(r("            **  "), p),
      s(r("        ****    "), p),
      s(r("     *****      "), p),
      s(r(" **      **     "), p),
      s(r("*          *****"), p),})
      );
    Thread.Sleep(100);
    p++;

    if (p == 16)
      p = 0;
  }
}

enter image description here

\$\endgroup\$
10
  • 1
    \$\begingroup\$ I think you can remove the parentheses in (a)=>. And while(true) can be for(;;) \$\endgroup\$
    – Cyoce
    Commented Dec 9, 2016 at 23:45
  • 1
    \$\begingroup\$ For the s lambda I think you can remove the {} and return \$\endgroup\$
    – Cyoce
    Commented Dec 9, 2016 at 23:57
  • \$\begingroup\$ Worked on both, giving me a 25 Byte saving in total, thanks! :) \$\endgroup\$
    – Pete Arden
    Commented Dec 10, 2016 at 0:10
  • \$\begingroup\$ You can make your entire function a lambda. I think you can also remove the \r from the string.Join (at least on Windows it works, didn't test it with Mono though) You can also save 1 byte by putting p++ into the for loop like this for(;;p++) \$\endgroup\$
    – Stefan
    Commented Dec 11, 2016 at 8:51
  • \$\begingroup\$ To remove the boundary check at the bottom (if (p==16)...) you can also put it into the for loop header like this for(;;p=++p%16). Save 1 more byte by declaring p in the loop (for(int p=0;;p=++p%16)) \$\endgroup\$
    – Stefan
    Commented Dec 11, 2016 at 8:56
7
\$\begingroup\$

V, 98 97 73 bytes

Thanks to @nmjcman101 for saving 24 bytes!

i¹ ³ **  
¸ ´*´ 
µ µ*¶ 
³ **³ **¶ 
 **¶ **µ 
*± µ*<ESC>{<C-v>}y4pò:sl100m
$<C-v>}x|Pò

This contains a lot of unprintables, so here's an xxd hexdump:

0000000: 69c2 b920 c2b3 202a 2a20 200a c2b8 20c2  i.. .. **  ... .
0000010: b42a c2b4 200a c2b5 20c2 b52a c2b6 200a  .*.. ... ..*.. .
0000020: c2b3 202a 2ac2 b320 2a2a c2b6 200a 202a  .. **.. **.. . *
0000030: 2ac2 b620 2a2a c2b5 200a 2ac2 b120 c2b5  *.. **.. .*.. ..
0000040: 2a1b 7b16 7d79 3470 c3b2 3a73 6c31 3030  *.{.}y4p..:sl100
0000050: 6d0a 2416 7d78 7c50 c3b2 0a              m.$.}x|P...

Edit

  1. Used y$ instead of <C-v>$y

  2. A lot of changes

    • Instead of copying each line and pasting them 4 times, I first generate the wave and then copy the whole thing and paste it 4 times
    • Used { and } to save few bytes
    • Used ò instead of registers to create the infinite loop (for some reason I have to include a ò at the end for it to work)
    • fixed the static * at the bottom

Mini-Explanation

I'm using <alt-n> to create copies of strings. For example, <alt-5>* (this looks like µ5) makes 5 copies of * in insert mode. This I found to be shorter than copying the string and using a regex to do the necessary replacements. After creating one wave, I paste it to create the other waves. Finally, I loop recursively using ò to create the infinite loop (with a delay of 100ms).

Gif

Most of the code is dedicated towards creating the wave, so I'm still trying to golf this. Note that this code will not work on TIO since TIO only outputs the output after the code has finished execution. So here's a gif (sorry for the low quality, I had to use a website to convert a .mov to a .gif, also the >_ that keeps popping up in the right is the Terminal icon on my mac's dock):

wave gif

\$\endgroup\$
4
  • \$\begingroup\$ I have very little idea about how your funky repeating numbers work, but if you make one wave, and then block copy/paste it, you can save characters (instead of copy pasting each line 4 times) Link to TryItOnline \$\endgroup\$
    – nmjcman101
    Commented Dec 12, 2016 at 20:05
  • \$\begingroup\$ Less helpfully, I think your 5j (in the context of $<C-V>5j) could just be }, and the p after the | should be a P which will fix the static * in the bottom left. \$\endgroup\$
    – nmjcman101
    Commented Dec 12, 2016 at 20:08
  • 1
    \$\begingroup\$ Finally (sorry for comment spam, apparently they're editable for 5 minutes) you can replace the qm[CODE]@mq@m at the end with just ò[CODE]. Code between ò will loop until breaking (similarly to your macro), and at the end of a program an ò is implicitly closed. \$\endgroup\$
    – nmjcman101
    Commented Dec 12, 2016 at 20:18
  • \$\begingroup\$ @nmjcman101 Thanks for all you help! (it is not comment spam if you are helping me golf a few bytes :) \$\endgroup\$
    – user41805
    Commented Dec 13, 2016 at 11:25
6
\$\begingroup\$

Batch, 424 bytes

@echo off
set f=     
set a=%f%%f%  **  
set b=%f%   ****    
set c=%f%***** %f%
set d=   **   ** %f%
set e= **%f% **%f%
set f=*%f%%f%*****
set a=%a%%a%%a%%a%%a%%b%%b%%b%%b%%b%%c%%c%%c%%c%%c%%d%%d%%d%%d%%d%%e%%e%%e%%e%%e%%f%%f%%f%%f%%f%
:l
cls
echo %a%
set a=%a:~79,1%%a:~0,79%%a:~159,1%%a:~80,79%%a:~249,1%%a:~160,79%%a:~319,1%%a:~240,79%%a:~399,1%%a:~320,79%%a:~-1%%a:~-80,79%
ping>nul 1.1 -n 1 -w 100
goto l

Some lines have trailing spaces. Requires a standard 80-column terminal. The timing isn't very accurate, but it's the best you can do in Batch.

\$\endgroup\$
6
\$\begingroup\$

Racket 395 374 373 367 364 351 bytes

Uses an external library for screen clearing
Edit: Saved 21 bytes by not defining w and inlining the function.
Edit2: Saved 1 byte by removing a space.
Edit3: Saved 6 bytes by renaming loop to p, thanks @rnso!
Edit4: Putting substring in the let saving 3 bytes.
Edit5: Remove #lang racket, which isn't needed in the interpreter.

Golfed: 351 bytes

[require[planet neil/charterm:3:0]][let p([n 1])[with-charterm[void[charterm-clear-screen]]][for([i'["            **  ""        ****    ""     *****      ""   **   **      "" **      **     ""*          *****"]])[let([g substring][x[string-join[make-list 5 i]""]])[displayln[string-append[g x[- 16 n]][g x 0[- 16 n]]]]]][sleep .1][p[modulo[+ n 1]16]]]

Scrolling (no clear): 272 bytes

[let p([n 1])[for([i'["            **  ""        ****    ""     *****      ""   **   **      "" **      **     ""*          *****"]])[let([g substring][x[string-join[make-list 5 i]""]])[displayln[string-append[g x[- 16 n]][g x 0[- 16 n]]]]]][sleep .1][p[modulo[+ n 1]16]]]

Ungolfed:

#lang racket
[require [planet neil/charterm:3:0]]
[define w
'[
"            **  "
"        ****    "
"     *****      "
"   **   **      "
" **      **     "
"*          *****"]]
[define (rotmul count)
  [for ([i w])
    [let ([x [string-join [make-list 5 i] ""]])
      [displayln [string-append [substring x count]
                                [substring x 0 count]]]]]]

[let loop ([n 1])
  [with-charterm
   [void [charterm-clear-screen]]]
  [rotmul [- 16 n]]
  [sleep .1]
  [loop [modulo [+ n 1] 16]]]

Waves

\$\endgroup\$
5
  • \$\begingroup\$ Renaming names to shorter ones (like p instead of loop) can be done to reduce bytes. What software did you use to capture video to gif file? \$\endgroup\$
    – rnso
    Commented Dec 11, 2016 at 16:05
  • \$\begingroup\$ @rnso: Oh you're right! Didn't think of that one. I used simplescreenrecorder with avconv to convert mp4 to gif. \$\endgroup\$
    – user63250
    Commented Dec 11, 2016 at 16:53
  • \$\begingroup\$ You can put (g substring) in let so that you can use g in place of 2 substring keywords later in code. That should save you another 5 bytes. Also what is 'lst' doing in your ungolfed version? \$\endgroup\$
    – rnso
    Commented Dec 11, 2016 at 17:15
  • \$\begingroup\$ @rnso: Removed it, was a remnant of when rotmul actually took in w as a parameter. \$\endgroup\$
    – user63250
    Commented Dec 11, 2016 at 17:37
  • \$\begingroup\$ You can also remove "#lang racket" from golfed version. Most Racket code on this site is not including it while counting bytes. \$\endgroup\$
    – rnso
    Commented Dec 12, 2016 at 0:39
4
\$\begingroup\$

PowerShell 3.0, 183 182 173 bytes

Requires PS 3.0 for binary shift operators. Slimmed to 173 bytes with AdmBorkBork's help!

$w=12,240,1984,6336,24672,32799
for(){0..5|%{'{0:D16}'-f+[Convert]::ToString(([uint16]$o=$w[$_]),2)*5-replace0,' '-replace1,'*'
$w[$_]=$o-shr1-bor$o-shl15}
sleep -m 100
cls}

PoshWaves

\$\endgroup\$
4
  • \$\begingroup\$ Nice answer! Some golfs -- using the decimal format specifier instead of .PadLeft, move the $o declaration into the [convert] call, and eliminate the quotes around the numbers in the -replace ops. Gets you down to 175 -- for(){0..5|%{("{0:D16}"-f+[Convert]::ToString(([uint16]$o=$w[$_]),2))*5-replace0,' '-replace1,'*' \$\endgroup\$ Commented Dec 16, 2016 at 14:12
  • \$\begingroup\$ @AdmBorkBork Thanks! Sorry that it took me quite a time to update the answer. Could you explain + in the "{0:D16}"-f+[Convert]? It doesn't work without it, but I can't grok what it does. \$\endgroup\$ Commented Feb 7, 2017 at 22:31
  • \$\begingroup\$ The [convert]::ToString() returns a string. The + forces a cast to an [int] so that -f picks up the correct parameter type for the D16 to work. \$\endgroup\$ Commented Feb 8, 2017 at 13:22
  • 1
    \$\begingroup\$ @AdmBorkBork You mean that PS treats +'1' like a valid arithmetical operation without first summand, casts string to int and returns result? Great Scott! \$\endgroup\$ Commented Feb 8, 2017 at 17:29
3
\$\begingroup\$

Bash+coreutils, 172 148 bytes

24 bytes saved thanks to @zeppelin, many thanks

while :
do clear
cut -c$[i=i%16+1]-$[79+i] <(base64 -d<<<4AJFACddABVgf2dnw+CvmeyOkhIoUJOPLK6oKkljh0+Peqi5BfrbbnDyuVkr+AA==|xz -qdFraw)
sleep .1
done

The first line decompresses the following pattern made of 6 consecutive waves:

**              **              **              **              **              **              
            ****            ****            ****            ****            ****            ****
         *****           *****           *****           *****           *****           *****  
       **   **         **   **         **   **         **   **         **   **         **   **  
     **      **      **      **      **      **      **      **      **      **      **      ** 
*****          ******          ******          ******          ******          ******          *

Then, the loop slides an 80-bytes-wide window through that pattern.

\$\endgroup\$
7
  • \$\begingroup\$ Coreutils base64 utility does not support -D flag (should be -d, lowercase instead). \$\endgroup\$
    – zeppelin
    Commented Dec 11, 2016 at 10:27
  • \$\begingroup\$ You can save ~10 bytes by using raw LZMA (xz), instead of gzip (compress with lzma -Fraw, decompress with xz -qdFraw). \$\endgroup\$
    – zeppelin
    Commented Dec 11, 2016 at 10:39
  • \$\begingroup\$ You can also use an older arithmetic expansion syntax $[], instead of $(()), to save 4 more bytes \$\endgroup\$
    – zeppelin
    Commented Dec 11, 2016 at 10:44
  • \$\begingroup\$ A leading zero can be omitted in sleep command, i.e. sleep .1 should work just fine \$\endgroup\$
    – zeppelin
    Commented Dec 11, 2016 at 10:50
  • \$\begingroup\$ You can also get rid of explicit i=0 declaration \$\endgroup\$
    – zeppelin
    Commented Dec 11, 2016 at 10:54
3
\$\begingroup\$

*><>, 251 250 251 bytes (non-competing)

" **             "e1C0["   ****         "e1C0["     *****      "e1C0["     **   **    "e1C0["    **      **  "e1C0["****          **"e1C0[06.
52Cl2,[52C52C]R
<v0&:l
$>:@=?v1+{:}&l1-[:&$@
?!v]1->:
~R>
vDDDDDD"H;0["ooooo
>l?u1S06.O{52Cl2,[a}48C]I
ol?!R

Note: "H;0[" is supposed to have ascii 27 after [.

Try it here! (set delay to 0ms)

I can't believe I ended up sucessfully making this. This uses the I and D instructions, which increments or decrements the selected stack. This is demonstrates that it's probably possible to do this in pure ><> (minus the sleep) or a competetive *><> answer, though probably a lot harder to do.

The online interpreter version is different simply to clear the output using a carriage return.

This is non-competing because the I, D, C, and R instructions are younger than the challenge. This is probably possible to do without those instructions, but it'd be very hard/long.

Edit: I actually managed to remove a byte, but I also noticed I measured the size wrong, so I actually gained a byte.


I'll do my best to break down the steps and explain what's happening here...

Explanation

" **             "e2C0["   ****         "e2C0["     *****      "e2C0["     **   **    "e2C0["    **      **  "e2C0["****          **"e2C0[09.
# Copy current stack 4 times
54Cl2,[54C54C]R
# Copy stack
<v0&:l
$>:@=?v1+{:}&l1-[:&$@
?!v]1->:
~R>
# Main loop
vDDDDDD"H;0["ooooo
>l?u1S09.O{54Cl2,[a}4cC]I
# Output stack
ol?!R

Table of Contents

Line 1 - Initialization
e2C    - Call "copy current stack 4 times"
54C    - Call "copy stack"
09.    - Jump to "main loop"
4cC    - Call "output stack" (not explained, is very simple)

Initialization

Here we build the 6 lines which construct the waves. We need to repeat each string 5 times to be the correct length.

We start with 6 of these, one for each line of the wave:

 " **             "       push " **             " to the stack
                   e2C    call "copy current stack 4 times"
                      0[  create a new stack

And we enter the main loop after initialization through 09..

Copy Current Stack 4 Times

This is a simple function which simply takes the current stack, and copies it 4 times. So "a" would become "aaaaa".

54C              call "copy stack"
   l2,[          copy half the current stack to a new stack
       54C54C    call "copy stack" twice
             ]   close the current stack, moving values to the one below
              R  return from the function

Copy Stack

This copies the current stack, appending the copy to the current stack.

Setup

Going to skip the initial < and invert the first line to become l:&0v as that's the order it gets executed in after the < changes the IP's direction.

l      push the stack length to the stack
 :&    copy the length to the register
   0   push 0 to the stack
    v  move the IP downwards, entering the loop

From here on out the length will be referred to as n and the 0 as i.

Loop

>                        move the IP to the right
 :                       copy i
  @=?v                   pop i from the stack, if n == i, proceed to cleanup
      1+                 add 1 to i
        {:}              copy the first value of the stack to the end of the stack
           &             place n on the stack
            l1-[         open a new stack moving all values but index 0 to the new one
                :&       copy n and place it on the register
                  $@     swap i with the value on its right
                     $   swap i with n

Cleanup

>                        move the IP to the right
 :?!v                    if i == 0 then ...
  ~R>                      remove i from the stack and return
     ]                   close the stack, appending all values to the stack below
      1-                 subtract 1 from i

Main Loop

Here is where the code runs forever, constantly redrawing the waves in-between 100ms sleeps.

Setup

DDDDDD                 select the 6th stack down
      "H;0[x"ooooo     move the cursor to the top-left of the term (x == ascii 27)
                  v    move the IP downwards, entering the loop 

Loop

>                          move the IP to the right
 l?u     O                 if the stack is empty ...
    1S                       sleep for 100ms
      09.                    jump to main loop initialisation
          {                shift the stack left
           54Cl2,[         copy the current stack to a new stack
                  a        append a newline to the stack
                   }       shift the stack to the right
                    4cC    call "output stack"
                       ]   close the stack
                        I  select one stack higher
\$\endgroup\$
2
\$\begingroup\$

PHP, 128 bytes

for($a=[3,60,496,1584,6168,57351];;usleep(1e5))foreach($a as&$x)for($x=$x/2|$x%2<<15,$i=80;$i--;)echo" *"[$x>>$i%16&1],"\n"[$i];

Cannot animate more than one line, but it scrolls.
Add ,0 to the array for an empty line between iterations. Run with -r.

\$\endgroup\$
2
\$\begingroup\$

Mathematica, 213 bytes

i=0;RunScheduledTask[i++,0.1];Dynamic[RotateRight[#,i]&/@Characters/@(StringRepeat[#,5]&)/@{"            **  ","        ****    ","     *****      ","   **   **      "," **      **     ","*          *****"}//Grid]

I don't see any way of golfing the wave pattern in Mathematica other than just starting with a list of strings for each line. I initialize i to be 0 and schedule a task to increment it every 0.1 seconds. I Dynamically display the result of the following:

  1. StringRepeat each line 5 times.
  2. Convert each line into a list of its Characters.
  3. RotateRight each list of characters by i.
  4. Display the resulting array of characters as a Grid.

enter image description here

\$\endgroup\$
2
  • \$\begingroup\$ What software did you use to create capture and create gif file? \$\endgroup\$
    – rnso
    Commented Dec 11, 2016 at 17:16
  • \$\begingroup\$ I used ScreenToGif. \$\endgroup\$
    – user61980
    Commented Dec 11, 2016 at 19:54
2
\$\begingroup\$

C (unix), 231 191 bytes

This will only work on unix environments. Also, please excuse the fact that sleep accepts only integers... so it actually delays 1second between frames.

Ungolfed version:

#include <stdio.h>
int main() {
    int x=0,l,i,a[6]={32799,24672,6336,1984,240,12};
    while(l=6,++x) {
        printf("\033[2J");
        while(i=128,l--) {
            while(i--) putchar(a[l]&1<<(i+x)%16 ? 42 :32);
            puts("");
        }
        sleep(1);
    }
}

Golfed version:

#include <stdio.h>
int main(){int x=0,l,i,a[6]={32799,24672,6336,1984,240,12};while(l=6,++x){printf("\033[2J");while(i=128,l--){while(i--)putchar(a[l]&1<<(i+x)%16?42:32);puts("");}sleep(1);}}
\$\endgroup\$
1
  • 1
    \$\begingroup\$ That's the C in your terminal. \$\endgroup\$ Commented Dec 17, 2016 at 7:19
2
\$\begingroup\$

Ruby 269 217 189 185 Bytes

-28 Bytes thanks to @manatwork

-5 Bytes thanks to @ropata

Normal

p=0
loop do
  system 'clear'
  [' '*12+'**  ', ' '*8+'****    ','     *****      ','   **   **      ',' **      **     ','*          *****'].each {|i| puts ((i*5)[16-p..-1]+i)[0..79]}
  p=-~p%16
  sleep 0.1
end

Golfed

p=0
b=' '
loop{system'clear'
[b*12+'**  ',b*8+'****    ',b*5+'*****'+b*6,'   **   **'+b*6,' **      **     ',"*#{b*10}*****"].map{|i|puts ((i*5)[16-p..-1]+i)[0,79]}
p=-~p%16
sleep 0.1}
\$\endgroup\$
4
  • \$\begingroup\$ Although your code works fine please note that according to site rules it is not a valid solution yet: “All solutions to challenges should: (…) Be a serious contender for the winning criteria in use. For example, an entry to a code golf contest needs to be golfed, (…)” – help center See Tips for golfing in Ruby for some tips. \$\endgroup\$
    – manatwork
    Commented Dec 12, 2016 at 11:04
  • \$\begingroup\$ Anyway, a brief list: remove indentation; do … end{ … } and remove the newlines after { and before }; remove the space between system and its parameter; remove the , after array literal's last element; .each.map and remove the space between it and its code block; remove the space in front of puts; 0..800,80 (this is also a bug as you expression results 81 characters long string); p=p+1==16?0: p+1p=-~p%16. \$\endgroup\$
    – manatwork
    Commented Dec 12, 2016 at 11:08
  • \$\begingroup\$ Yepp, manatwork's dumb explanation strikes again. Even changing do … end{ … }, there is still need for the loop keyword. This is the shortest I get: pastebin.com/cg3gxnm4 \$\endgroup\$
    – manatwork
    Commented Dec 12, 2016 at 19:12
  • \$\begingroup\$ Can save 5 or 6 bytes by setting b=' ' (5 blank spaces) at the top then changing the output expression to ' '*12+'** ', ' '*8+'**** ',b+'***** '+b,' ** ** '+b,' ** **'+b,'*'+b+b+'*****' ... (but SE isn't showing repeated spaces properly in this comment!) \$\endgroup\$
    – roblogic
    Commented Dec 15, 2016 at 2:05
2
\$\begingroup\$

Javascript (ES6), 152 147 145 bytes

x=0,c=console;setInterval(a=>{for(c.clear();f="",i=128,++x,a--;c.log(f))for(;i--;)f+=" *"[[32799,24672,6336,1984,240,12][a]>>(i+x)%16&1]},100,6);
\$\endgroup\$
2
  • \$\begingroup\$ You can also save 2 bytes with setInterval(a=>{...},100,6), and 4 more with f+=" *"[[...][a]&1<<(i+x)%16]. \$\endgroup\$ Commented Dec 14, 2016 at 23:19
  • \$\begingroup\$ Thanks for the suggestions! But are you certain you can get your second suggestion to work? You'll still have to coerce that value to a boolean to retrieve array index 0-1. I was thinking of further bitmapping the wave ascii into a single hex value: 0x801F606018C007C000F0000C but Javascript can only bitwise shift a maximum of 31 bits in either direction! You learn something every day! \$\endgroup\$
    – ajxs
    Commented Dec 15, 2016 at 12:15
2
\$\begingroup\$

Perl 6, 140 138 137 123 120 bytes

for ^Inf ->\i{print "\e[H";for 12,240,1984,6336,24672,32799 ->\j{say [~] map {j+>((i-$_)%16)%2??'*'!!' '},^80};sleep .1}

Old solutions:

for ^Inf ->\i {print "\e[H";for 12,240,1984,6336,24672,32799 ->\j {say [~] map {j+>((i-$_)%16)%2??'*'!!' '},^80};sleep .1;}
my @a=12,240,1984,6336,24672,32799;for ^Inf ->\i {print "\e[H";for @a ->\j {for ^80 {print j+>((i-$_)%16)%2??'*'!!' '};say ""};sleep .1;}
my @a=12,240,1984,6336,24672,32799;for ^Inf {print "\e[H";for @a ->\j {for ^80 ->\k {print j+>(($_- k)%16)%2??'*'!!' '};say ""};sleep .1;}
my @a=12,240,1984,6336,24672,32799;for ^Inf {print "\e[H";for @a ->\j {for ^80 ->\k {print j+>(($_+15*k)%16)%2??'*'!!' '};say ""};sleep .1;}
\$\endgroup\$
0
1
\$\begingroup\$

Python 3, 240 239 230 bytes

-1 byte thanks to @redstarcoder

-9 bytes thanks to @PascalvKooten

import time
def p():print("\x1b[0;H")
i=0;p();s=[' '*13+'**',' '*9+'****  ','      *****    ','    **   **    ','  **      **   ','**          ***']
while True:
 for x in s:x*=5;c=i%80;print(x[-c:]+x[:-c])
 i+=1;p();time.sleep(.1)
\$\endgroup\$
3
  • \$\begingroup\$ print("\x1b[0;H") also works for me for -1 byte. \$\endgroup\$ Commented Dec 10, 2016 at 18:11
  • \$\begingroup\$ You can replace ' **' with ' '*13+'**' and you can have 1 character indents in the while, no need for it to be 4 characters. \$\endgroup\$ Commented Dec 11, 2016 at 22:09
  • \$\begingroup\$ @PascalvKooten thanks. The indents were transformed into spaces from tab characters during pasting. I will make sure to watch out for that. \$\endgroup\$
    – dfernan
    Commented Dec 11, 2016 at 22:36
1
\$\begingroup\$

Racket 295 bytes

(let*((g string-append)(h substring)(d displayln)(j(λ(l)(map(λ(x)(g(h x 1)(h x 0 1)))l))))(let p((l(map(λ(x)(apply g(for/list((i 5))x)))'("            **  ""         ****   ""      *****     ""    **   **     ""  **      **    ""*          *****"))))(for((i l))(d i))(d"")(sleep .1)(p(j l))))

Ungolfed:

(define(f)
 (define (lf l)
    (map (λ (x) (string-append (substring x 1) (substring x 0 1)))
         l))
  (let loop ((l (map (λ (x) (apply string-append (for/list ((i 5)) x)) )
                     (list 
                      "            **  "
                      "         ****   "
                      "      *****     "
                      "    **   **     "
                      "  **      **    "
                      "*          *****"))))
    (for ((i l))
      (displayln i))
    (displayln "")
    (sleep 0.1)
    (loop (lf l))))

Testing:

(f)

Output:

enter image description here

(This gif file display is slower than actual output).

\$\endgroup\$
1
\$\begingroup\$

Python 2, 207 202 bytes

Usually I'm a C# developer, so this might not be completely golfed yet...

import time;i=0
while 5:
    print"\033[;H"
    for l in[" "*12+"**  "," "*8+"*"*4+" "*4," "*5+"*"*5+" "*6,"   **   **"+" "*6," **     "*2,"*"+" "*10+"*"*5]:print(l[16-i:]+l*5)[:80]
    time.sleep(.1);i=(i+1)%16
\$\endgroup\$
1
\$\begingroup\$

C#, 327 bytes

More or less a ported version of my solution in Python...

_=>{Func<string,int,string>t=(s,j)=>(s.Substring(16-j)+string.Concat(Enumerable.Repeat(s,5))).Substring(0,80);for(var i=0;;i=++i%16){Console.Clear();foreach(var q in "            **  ,        ****    ,     *****      ,   **   **      , **      **     ,*          *****".Split(','))Console.WriteLine(t(q,i));Thread.Sleep(100);}}
\$\endgroup\$
1
\$\begingroup\$

Perl, 110 bytes

Requires -E at no extra cost. This contains unprintable characters.

$_=unpack"B*","x?`00?";s!.{16}!$&x5 .$/!ge;y/01/ */;{say"\ec$_";select!s/(.+)(.)$/$2$1/mg,$a,$a,.1;redo}"

Create the above data using the below reversible hexdump. Run xxd -d > sea.pl in a linux or compatible terminal, paste the below and press Ctrl+d, then run perl -E "$(cat sea.pl)".

0000000: 245f 3d75 6e70 6163 6b22 422a 222c 2200  $_=unpack"B*",".
0000010: 0600 7803 e00c 6030 30c0 0f22 3b73 212e  ..x...`00..";s!.
0000020: 7b31 367d 2124 2678 3520 2e24 2f21 6765  {16}!$&x5 .$/!ge
0000030: 3b79 2f30 312f 202a 2f3b 7b73 6179 225c  ;y/01/ */;{say"\
0000040: 6563 245f 223b 7365 6c65 6374 2173 2f28  ec$_";select!s/(
0000050: 2e2b 2928 2e29 242f 2432 2431 2f6d 672c  .+)(.)$/$2$1/mg,
0000060: 2461 2c24 612c 2e31 3b72 6564 6f7d       $a,$a,.1;redo}

Usage

For easy copy/pasting, please use the below:

perl -E '$_=unpack"B*","\x00\x06\x00\x78\x03\xe0\x0c\x60\x30\x30\xc0\x0f";s!.{16}!$&x5 .$/!ge;y/01/ */;{say"\ec$_";select!s/(.+)(.)$/$2$1/mg,$a,$a,.1;redo}'

Explanation

A fairly straightforward solution that stores the wave as a string at the beginning, which is unpacked to binary, each section is quintuplicated, 0s are converted to spaces and 1s are converted to *s. Now we have the whole string so we enter a redo loop which prints out the whole string, then we wait for .1 seconds and for each line in the string, we move the last character to the beginning of the string.

\$\endgroup\$
1
\$\begingroup\$

Mathematica 171 Bytes

The wave itself is data, so I'm storing a compressed version of the whole wave in my code. I can store a single wave much more compactly as \fð߀ᣀ恠耟 using it's binary representation, but the character count overhead of uncompressing is too high*.

Here is the code:

w=Uncompress@"1:eJxTTMoPSmNjYGAoZgESPpnFJcEBQIYCEtDSUlCglI9iqJYWqhJy+QhDtdCUUMCHGQrmIymiiA8xFMajEg02FMkXWmi+IosPAJNuSHg=";
Dynamic[Pause[.1];Column[w=StringRotateRight/@w]]   

Here is the code I used to create the compressed version of the wave data:

s={"            **  ","        ****    ","     *****      ","   **   **      "," **      **     ","*          *****"};
s//TableForm
StringRepeat[#,5]&/@s
Compress[%]

Here is the code I would have preferred to use to store compressed repeating binary data like this wave:

StringJoin /@ (PadLeft[(IntegerDigits[#1, 2] & ) /@ ToCharacterCode["\fð߀ᣀ恠耟"]] /. {0 -> " ", 1 -> "*"})

As you can see, the overhead to turn the compressed data back into a string is too expensive for this particular problem, although a single wave can be stored this way with 7 UTF characters and 15 bytes.

Here was the code to determine the UTF character sequence to store a single wave (s as above).

StringReplace[#,{" "->"0","*"->"1"}]&/@s
ToExpression/@%
IntegerDigits/@%
FromDigits[#,2]&/@%
FromCharacterCode/@%
StringJoin@%
\$\endgroup\$
1
\$\begingroup\$

Stax, 38 bytes

ç²kτ,e7rà♠ǃ╜?║í▬u╬wπ■&Jµⁿj↨▄!=╢╡═+ZWu

Run and debug it

Took some shuffling around and :B to beat the MATL score.

Explanation

. *9*"!1$'YKaK968"%13|E:B16/WcM|)Ms{|,}6*|:m5* 
. *                                            " *"
   9*                                          repeat 9 times
     "!1$'YKaK968"%13|E                        compressed run lengths of wave
                       :B                      run length decode using the two arrays
                         16/                   split in groups of 16
                            W                  loop forever
                             c                 copy the wave
                              M|)M             shift right
                                  s            swap
                                   {|,}6*      wait 6 frames(0.1s at 60fps)
                                         m5*   pop, repeat each line 5 times and display  
\$\endgroup\$
0
\$\begingroup\$

HTML + JS + jQuery, 10 + 233 = 243 bytes

b="            **  q        ****    q     *****      q   **   **      q **      **     q*          *****".split`q`.map(x=>x.repeat(5).split``)
setInterval(a=>$("#a").text(b.map(f=>f.join``).join`\n`)+b.map(e=>e.unshift(e.pop())),100)
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>

<!-- start -->
<pre id=a>

The JavaScript just shifts each row by 1 and changes the text every 100 ms.

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.