Круговий блюз


21

Напишіть програму або функцію, яка приймає додатне ціле число N і відтворює цю схему кіл, масштабовану під розмір зображення N × N пікселів:

ошатні кола

Це зображення є дійсним прикладом виводу для N = 946.

Якщо це не зрозуміло, всі маленькі світло-сині кола мають однаковий радіус і розташовуються в чотирьох темно-синіх колах однаково. Темно-сині кола мають подвійний радіус і аналогічно розташовані у великому світло-синьому колі.

  • Замість двох відтінків синього можна використовувати будь-які два візуально чіткі кольори.

  • Фоновий квадрат потрібно пофарбувати.

  • Згладжування не є обов'язковим.

  • Збережіть зображення у файлі, покажіть його або передайте необроблені дані зображення в stdout.

  • Дозволений будь-який загальний формат файлу зображень.

Виграє найкоротший код у байтах.

Брауні вказує, якщо розширити рекурсивні аспекти цього шаблону кола на подальші рівні. (Залишайте це відмінним від запису на запитання.)


Що ви маєте на увазі під "Квадрат фона потрібно кольоровим"? Якщо фон має певний колір за замовчуванням, чи можу я просто використовувати його як один із двох кольорів без явного заповнення?
aditsu

Я маю на увазі, що bg не може бути третього іншого кольору
Calvin's Hobbies

Відповіді:


5

CJam, 83 байти

"P1"li___,.5f+2.@/f*1fm2m*{[3{_~mh1<[[VX][ZmqV]]_Wff*+@2f*f.+{~mh}$0=}*;0]0#2%}%]S*

Спробуйте в Інтернеті

CJam не має функціоналу виділеного зображення. Мій код генерує зображення в PBM ASCII. Для публікації я перетворив це зображення в PNG за допомогою GIMP.

Зауважте, що жоден функціонал малювання кола чи щось подібне він не використовував. Зображення обчислюється пікселем за пікселем.

Вибірка зразка

Вищі ступені підрозділу можна легко створити, збільшивши константу 3навколо середини коду.

Зображення ступеня 4 і 5 виглядають приблизно так:

Ступінь 45 ступінь

Загальна послідовність коду:

  1. Створити координати всіх пікселів, нормалізованих до діапазону [-1.0, 1.0].
  2. Цикл на всіх пікселях.
  3. Переведіть петлі на ступені підрозділу.
  4. Для кожного підрозділу перевірте, чи знаходиться піксель всередині / зовні, і збережіть результат. Шкала / переклад піксельних координат до систем координат, орієнтованих на одному з 4 підколів. Виберіть ту, де перетворені координати найближчі до центру.
  5. З двійкових внутрішніх та зовнішніх результатів кожного ступеня знайдіть перший 0, що відповідає першому ступені, де піксель знаходився зовні, і візьміть його модуль 2 для визначення кольору пікселя.

Пояснення:

"P1"    Start of header for PBM ASCII file.
li      Get input n.
__      Two copies for the width/height of the image in the PBM header.
_,      Generate [0 .. n - 1].
.5f+    Add 0.5 to each list entry, since we want to test the pixel centers.
2.@/    Calculate 2.0 / n, which is the distance between two pixels.
f*      Multiply the unscaled pixel coordinates with the pixel distance.
        We now have coordinates in the range [0.0, 2.0].
1fm     Subtract one from each, giving coordinates in range [-1.0, 1.0].
2m*     Cartesian power to calculate all y/x pairs.
{       Start loop over all pixel coordinates.
  [       Start wrapping the inside/outside results for all degrees.
  3{      Start loop over degrees.
    _~mh    Calculate distance from center.
    1<      Compare with 1. This gives inside/outside result for degree.
    [       Start building list of centers for 4 sub-circles.
    [VX]    One is at [0 1]. Note that coordinate order is y/x.
    [ZmqV]  Next one is at [sqrt(3) 0].
    ]       Wrap these two...
    _       ... and copy them.
    Wff*    Mirror all coordinates by multiplying with -1.
    +       Concatenate, giving the centers of all 4 sub-circles.
    @       Get current coordinates to top.
    2f*     Multiply them by 2. Note that the coordinates need to be scaled up by
            a factor 2 to give a circle with half the radius when we test the distance
            to the origin against 1.0.
    f.+     Add the current coordinates to the centers of all 4 sub-circles.
            For each sub-circle, this puts the current coordinates in a coordinate
            space with the origin at the center, and with a radius of 1.0
    {~mh}$  Sort them by distance to the origin...
    0=      ... and take the first one. This picks the sub-circle which has its
            center closest to the current coordinates.
            We now have one coordinate pair, for the closest sub-circle, and are
            ready for the next loop iteration, which tests the next degree of the
            subdivision.
  }*      End loop over degrees.
  ;       Have remaining coordinate pair on stack, pop it.
  0       Add a sentinel for find operation before, so that a 0 is always found.
  ]       End wrapping the inside/outside results for all degrees.
  0#      Find the first 0 (outside) degree.
  2%      Modulo 2 to determine color.
}%      End loop over all pixel coordinates.
]       Wrap the pieces of the PBM header and the pixel list.
S*      Join them with spaces, to produce the necessary spaces for the header.

17

Python 2 + PIL, 262 байти

введіть тут опис зображення

Цей підхід визначає колір кожної окремої піксельної координати за допомогою рекурсивної функції c. c(x,y,0)робить коло; c(x,y,1)робить коло з вирізаними з нього чотирма колами; c(x,y,2)надає зображення в ОП. Все, що перевищує 2, заробляє мені очки брауні

import PIL.Image as I
d=3**.5/2
c=lambda x,y,l=0:c(x,y)&~any(c((x+i)*2,(y+j)*2,l-1)for i,j in[(.5,0),(-.5,0),(0,d),(0,-d)])if l else x*x+y*y<1
z=input()
f=lambda s:2.*s/z-1
I.frombytes("L",(z,z),"".join(" ~"[c(f(i%z),f(i/z),2)]for i in range(z*z))).save("p.png")

Версія без гольфу:

from PIL import Image
import math
def in_shape(x,y, level=0):
    d = math.sqrt(3)/2
    if level == 0:
        return x**2 + y**2 <= 1
    else:
        t = True
        for dx,dy in [(0.5, 0), (-0.5, 0), (0, d), (0,-d)]:
            if in_shape((x+dx)*2, (y+dy)*2, level-1):
                t = False
        return in_shape(x,y) and t

f = lambda s: ((2*s / float(size))-1)

size = input()
img = Image.new("RGB", (size, size))
pix = img.load()
for i in range(size):
    for j in range(size):
        if in_shape(f(i), f(j), 2):
            pix[i,j] = (0,0,0)
        else:
            pix[i,j] = (255,255,255)
img.save("output.png")

Бонусне надрекурсивне зображення:

введіть тут опис зображення


Замість .save("p.png")просто використовувати.show()
Альберт Реншо

7

PostScript, 335 байт.

%!
/D{def}def/B{bind D}D/E{exch}B/A{add}D/c{3 copy 3 -1 roll A E moveto 0 360 arc}B/f{5 dict begin/d E D/r E D/y E D/x E D gsave x y r c clip d 2 mod setgray x y r c fill d 0 gt{/h 3 sqrt 2 div r mul D/r r 2 div D/d d 1 sub D x r A y r d f x r sub y r d f x y h A r d f x y h sub r d f}if grestore end}B 512 2 div dup dup 2 f showpage

PostScript - це не просто формат графічного файлу, що має як векторні, так і растрові можливості, це фактично об'єктна мова програмування Turing. Код, наведений вище, є досить прямою рекурсивною реалізацією функції. Усі оператори PostScript - це функції, і звичайно переосмислювати їх для згущення коду. Зауважте, що PostScript використовує зворотні польські позначення (також нотації постфікса).

Інтерпретатори PostScript, як правило, читають метадані (наприклад, розмір сторінки та заголовок) із спеціальних коментарів на початку файлу; Очевидно, я видалив усі %!мої коментарі, окрім гострого необхідного підпису PostScript , але він все одно повинен відображатись нормально у будь-якому стандартному інтерпретаторі PostScript, наприклад, GhostScript або Okular. Його також можна переглядати за допомогою утиліти відображення , яка постачається разом із ImageMagick / GraphicsMagick.

Зауважте, що файл повинен закінчуватися новим рядком (який я включив у свій байт), інакше перекладач може засмутитися.

Параметр розміру Nдля цього коду - 512; він ділиться на 2 і дублюється двічі, щоб створити параметри для початкового виклику рекурсивної функції f. Глибина рекурсії дорівнює 2, що задається безпосередньо перед fв 512 2 div dup dup 2 f. Щоб розмір був невеликим, вихід - чорно-білий. Хоча ви можете встановити будь-яку розумну невід’ємну цілу глибину рекурсії, ця версія добре виглядає лише з рівними глибинами.

Це зображення є векторною графікою, тому може відображатися у будь-якій роздільній здатності без пікселізації, залежно від якості та налаштувань використовуваного інтерпретатора / принтера PostScript. (FWIW, PostScript використовує кубічні криві Безьє для малювання кругових дуг з достатньою сплайною, яка використовується для того, щоб помилка завжди була менше одного пікселя в просторі пристрою). Щоб переглянути його за допомогою дисплея ImageMagick у досить високій якості, ви можете:

display -density 300 -geometry 512x512 -page 512x512

ті ж параметри також хороші, якщо ви хочете використовувати ImageMagick's convertдля перетворення його в інший формат. Наприклад, ось версія 640x640 вищезгаданого коду PostScript, перетвореного на PNG:

Фрактал кола 640x640 B&W


Ось дещо більша версія, яка обробляє RGB ​​кольори та непарні глибини рекурсії:

%!PS-Adobe-3.0
/D{def}def/N 512 D/d 2 D/B{bind D}D/E{exch}B/A{add}D/c{3 copy 3 -1 roll A E moveto 0 360 arc}B/k{2 mod 0 eq{.3 .6 .9}{0 .2 .5}ifelse setrgbcolor}B d 1 A k 0 0 N N rectfill/f{5 dict begin/d E D/r E D/y E D/x E D gsave x y r c clip d k x y r c fill d 0 gt{/h 3 sqrt 2 div r mul D/r r 2 div D/d d 1 sub D x r A y r d f x r sub y r d f x y h A r d f x y h sub r d f}if grestore end}B N 2 div dup dup d f showpage

Це також дозволяє встановити параметр розміру Nта глибину рекурсії dбіля верхньої частини сценарію.

640x640 кольорове коло фрактал, глибина == 2


Нарешті, ось більш читабельна форма коду. (На жаль, виділення синтаксису, що використовується тут для PostScript, залишає бажати кращого, але, мабуть, це краще, ніж нічого ...). Інтелектуальні інтерпретатори PostScript прочитають геометрію сторінки із %%BoundingBox:спеціального коментаря.

%!PS-Adobe-3.0
%%BoundingBox: 0 0 640 640
%%Title: Circle fractal
%%Creator: PM 2Ring
%%Creationdate: (Oct 29 2015)
%%Pages: 1 1
%%EndComments

% for http://codegolf.stackexchange.com/questions/61989/circular-blues

% ----------------------------------------------------------------------

16 dict begin

%Total image width & height in points / pixels
/N 640 def

%Maximum recursion depth
/Depth 4 def

% ----------------------------------------------------------------------

%Draw a circle centred at (x,y), radius r. x y r circle -
/circle{
    3 copy      % x y r  x y r
    3 -1 roll   % x y r  y r x
    add exch    % x y r  x+r y
    moveto
    0 360 arc 
}bind def

% ----------------------------------------------------------------------

%Select 1st color if n is even, select 2nd color if n is odd. n color -
/color{
    2 mod 0 eq
    {.36 .6 .9}
    {0 .25 .5}
    ifelse
    setrgbcolor
}bind def

%Do background square
Depth 1 add color
0 0 N N rectfill

/Q 3 sqrt 2 div def

%Recursive circle pattern. x y r Depth cfrac -
/cfrac{
    5 dict begin
    /Depth exch def
    /r exch def
    /y exch def
    /x exch def

    gsave
    x y r circle clip
    Depth color
    x y r circle fill

    Depth 0 gt
    {
        /dy Q r mul def
        /r r 2 div def
        /Depth Depth 1 sub def 

        x r add y r Depth cfrac
        x r sub y r Depth cfrac
        x y dy add r Depth cfrac
        x y dy sub r Depth cfrac
    }if
    grestore
    end
}bind def

%Call it!
N 2 div dup dup Depth cfrac

showpage

% ----------------------------------------------------------------------

%%Trailer
end
%%EOF

А ось вивід глибини == 4 у форматі PNG, знову створений за допомогою перетворення (та оптимізованого optipng ):

640x640 кольорове коло фрактал, глибина == 4


6

Python 2 + PIL, 361 байт

import PIL.Image as p,PIL.ImageDraw as d
W=input()
q=W/4
h=2*q
t=3*q
e=W/8
o=int(q*3**.5)
I,J=[p.new("1",(s,s),s>h)for s in[W,h]]
Q=lambda i,x,y,s=q,c=0:d.Draw(i).ellipse((x,y,x+s,y+s),fill=c)
Q(I,0,0,W)
Q(J,0,0,h,1)
[Q(J,k,e)for k in[0,q]]
[Q(J,e,e+k/2)for k in[-o,o]]
[I.paste(1,k,J)for k in[(0,q,h,t),(h,q,4*q,t),(q,q-o,t,t-o),(q,q+o,t,t+o)]]
I.save("c.png")

Зберігає зображення у чорно-білому кольорі у файлі c.png:

Приклад виведення

Я в основному генерую одне з піврозмірних кіл на зображенні J. Потім я використовую себе як маску для малювання фігури на зображенні I, на якому є основне коло.

Це можна скоротити, використовуючи I.show()в кінці замість I.save("c.png"), але я не змусив його працювати над Python 2. Якщо хтось може підтвердити, що він працює на Python 2, я зміню це.

Наступна програма генерує зображення, як у запитанні (419 байт):

import PIL.Image as p,PIL.ImageDraw as d
W=int(input())
q=W/4
h=2*q
t=3*q
e=W/8
o=int(q*3**.5)
I,J=[p.new(["1","RGB"][s>h],(s,s),s>h and"rgb(13,55,125)")for s in[W,h]]
Q=lambda i,x,y,s=q,c=0:d.Draw(i).ellipse((x,y,x+s,y+s),fill=c)
Q(I,0,0,W,"rgb(97,140,224)")
Q(J,0,0,h,1)
[Q(J,k,e)for k in[0,q]]
[Q(J,e,e+k/2)for k in[-o,o]]
[I.paste("rgb(13,55,125)",k,J)for k in[(0,q,h,t),(h,q,4*q,t),(q,q-o,t,t-o),(q,q+o,t,t+o)]]
I.save("c.png")

-1 не такий гарний, як образ Кальвіна;)
бета-розпад

Я можу підтвердити, що .show () працює
Альберт Реншо

Добре, дякую, я використаю це замість save.
Кевін

3

SVG (1249 символів)

Так, багато персонажів. Але він статичний і надає будь-якого розміру, так що це дає йому певний бонус.

<svg xmlns="http://www.w3.org/2000/svg"><path d="M15,33c-2.5,0-4.6,1.9-4.9,4.3c2.8,1.6,6.1,2.6,9.5,2.6c0.3-0.6,0.4-1.3,0.4-2C20,35.2,17.8,33,15,33zM15,7c2.8,0,5-2.2,5-5c0-0.7-0.1-1.4-0.4-2c-3.5,0.1-6.7,1-9.5,2.6C10.4,5.1,12.5,7,15,7zM25,33c-2.8,0-5,2.2-5,5c0,0.7,0.1,1.4,0.4,2c3.5-0.1,6.7-1,9.5-2.6C29.6,34.9,27.5,33,25,33zM25,7c2.5,0,4.6-1.9,4.9-4.3C27.1,1,23.9,0.1,20.4,0C20.1,0.6,20,1.3,20,2C20,4.7,22.2,7,25,7zM35,28.7C34.8,26,32.6,24,30,24s-4.8,2.1-5,4.7c-3-1.7-5-5-5-8.7c0,3.7-2,6.9-5,8.7C14.8,26,12.6,24,10,24S5.2,26,5,28.7c-3-1.7-5-5-5-8.7c0,7.4,4,13.9,10,17.3c0.1-1.2,0.4-2.4,0.8-3.4c0.9-1.9,2.3-3.5,4.1-4.5c0,0,0,0,0.1,0c0.2,2.6,2.3,4.7,5,4.7s4.8-2.1,5-4.7c0,0,0,0,0.1,0c1.8,1,3.2,2.6,4.1,4.5c0.5,1.1,0.8,2.2,0.8,3.4c6-3.5,10-9.9,10-17.3C40,23.7,38,26.9,35,28.7zM5,11.3c0.2,2.6,2.3,4.7,5,4.7s4.8-2.1,5-4.7c3,1.7,5,5,5,8.7c0-3.7,2-6.9,5-8.7c0.2,2.6,2.3,4.7,5,4.7s4.8-2.1,5-4.7c3,1.7,5,5,5,8.7c0-7.4-4-13.9-10-17.3c-0.1,1.2-0.4,2.4-0.8,3.4C28.3,8,26.8,9.6,25,10.6c0,0,0,0-0.1,0C24.8,8,22.6,6,20,6s-4.8,2.1-5,4.7c0,0,0,0-0.1,0c-1.8-1-3.2-2.6-4.1-4.5C10.4,5,10.1,3.9,10,2.6C4,6.1,0,12.6,0,20C0,16.3,2,13,5,11.3z"/><circle cx="15" cy="20" r="5"/><circle cx="5" cy="20" r="5"/><circle cx="35" cy="20" r="5"/><circle cx="25" cy="20" r="5"/></svg>

Видимий фрагмент:

svg { fill: #9FD7FF; background: #2176AA; }
<svg xmlns="http://www.w3.org/2000/svg" width="400" height="400" viewBox="0 0 40 40">
  <path d="M15,33c-2.5,0-4.6,1.9-4.9,4.3c2.8,1.6,6.1,2.6,9.5,2.6c0.3-0.6,0.4-1.3,0.4-2C20,35.2,17.8,33,15,33zM15,7c2.8,0,5-2.2,5-5c0-0.7-0.1-1.4-0.4-2c-3.5,0.1-6.7,1-9.5,2.6C10.4,5.1,12.5,7,15,7zM25,33c-2.8,0-5,2.2-5,5c0,0.7,0.1,1.4,0.4,2c3.5-0.1,6.7-1,9.5-2.6C29.6,34.9,27.5,33,25,33zM25,7c2.5,0,4.6-1.9,4.9-4.3C27.1,1,23.9,0.1,20.4,0C20.1,0.6,20,1.3,20,2C20,4.7,22.2,7,25,7zM35,28.7C34.8,26,32.6,24,30,24s-4.8,2.1-5,4.7c-3-1.7-5-5-5-8.7c0,3.7-2,6.9-5,8.7C14.8,26,12.6,24,10,24S5.2,26,5,28.7c-3-1.7-5-5-5-8.7c0,7.4,4,13.9,10,17.3c0.1-1.2,0.4-2.4,0.8-3.4c0.9-1.9,2.3-3.5,4.1-4.5c0,0,0,0,0.1,0c0.2,2.6,2.3,4.7,5,4.7s4.8-2.1,5-4.7c0,0,0,0,0.1,0c1.8,1,3.2,2.6,4.1,4.5c0.5,1.1,0.8,2.2,0.8,3.4c6-3.5,10-9.9,10-17.3C40,23.7,38,26.9,35,28.7zM5,11.3c0.2,2.6,2.3,4.7,5,4.7s4.8-2.1,5-4.7c3,1.7,5,5,5,8.7c0-3.7,2-6.9,5-8.7c0.2,2.6,2.3,4.7,5,4.7s4.8-2.1,5-4.7c3,1.7,5,5,5,8.7c0-7.4-4-13.9-10-17.3c-0.1,1.2-0.4,2.4-0.8,3.4C28.3,8,26.8,9.6,25,10.6c0,0,0,0-0.1,0C24.8,8,22.6,6,20,6s-4.8,2.1-5,4.7c0,0,0,0-0.1,0c-1.8-1-3.2-2.6-4.1-4.5C10.4,5,10.1,3.9,10,2.6C4,6.1,0,12.6,0,20C0,16.3,2,13,5,11.3z"/>
  <circle cx="15" cy="20" r="5"/>
  <circle cx="5" cy="20" r="5"/>
  <circle cx="35" cy="20" r="5"/>
  <circle cx="25" cy="20" r="5"/>
</svg>


Зауважте, що, як сказав Мего, SVG не відповідає нашим критеріям, щоб кваліфікуватись як мова програмування . Однак ОП може вирішити дозволити цю відповідь у будь-якому випадку; це до нього.
Алекс А.

SVG в цьому випадку добре.
Захоплення Кальвіна

Чи можете ви пропустити провідні 0константи з плаваючою точкою? Наприклад, замінити 0.4на .4? Для більшості мов це справедливо. І дуже швидкий погляд на специфікацію SVG говорить про те, що він, ймовірно, повинен працювати і їх.
Рето Коради

@RetoKoradi Так, і ви, ймовірно, можете розчавити ще декілька цифр шляхом ефективного округлення або змінивши розмір таким чином, що вам потрібно менше десяткових знаків, але тбг. отримані шляхи просто занадто складні для цього, щоб зробити величезну зміну. Але я можу спробувати інше рішення за допомогою масок пізніше.
ткнути

2

Mathematica 336 359 байт

Основними об’єктами графіки є регіони, визначені за допомогою логічних комбінацій рівнянь.

r=Red;i=ImplicitRegion;m=i[-2<x<2&&-2<y<2,{x,y}];n=Input[];
t[a_,b_,c_]:=i[(x+a)^2+(y+b)^2<=c,{x,y}];
a_~f~b_:={t[a,b,1],t[-.5+a,b,1/4],t[.5+a,b,1/4],t[a,b-.865,1/4],t[a,b+.865, 1/4]}
g@d_:=RegionIntersection[m,BooleanRegion[#1&&!#2&&!#3&&!#4&&!#5&,d]]
RegionPlot[{m,t[0,0,4],g@f[1,0],g@f[-1,0],g@f[0,1.75], 
g@f[0, -1.75]},ImageSize->n,PlotStyle->{r,Blue,r,r,r,r}]

рис


1

Ява, 550

import javafx.application.*;import javafx.scene.*;import javafx.scene.layout.*;import javafx.scene.shape.*;import javafx.stage.*;public
class C extends Application{static long n;Shape d(float m,float k,float x,float y){float h=m/2;Shape
s=new Circle(x+h,y+h,h);return k>0?s.subtract(s,s.union(s.union(s.union(d(h,k-1,x,y+m/4),d(h,k-1,x+h,y+m/4)),d(h,k-1,x+m/4,y-m*.183f)),d(h,k-1,x+m/4,y+m*.683f))):s;}public
void start(Stage s){s.setScene(new Scene(new Pane(d(n,2,0,0))));s.show();}public
static void main(String[]a){n=Long.valueOf(a[0]);launch();}}

В основному просто експериментують з JavaFX.

Знімок екрана:

скріншот

Для точок брауні змініть 2код ( d(n,2,0,0)) на інше число.

Стара версія, 810 рік

import javafx.application.*;import javafx.scene.*;import javafx.scene.canvas.*;import javafx.scene.effect.*;import javafx.scene.layout.*;import javafx.scene.paint.*;import javafx.stage.*;public
class C extends Application{static long n;Canvas c;GraphicsContext g;void
d(float m,float k,float x,float y){if(k>0){float
h=m/2;g.save();g.beginPath();g.arc(x+h,y+h,h,h,0,360);g.clip();g.fillRect(x,y,m,m);d(h,k-1,x,y+m/4);d(h,k-1,x+h,y+m/4);d(h,k-1,x+m/4,y-m*.183f);d(h,k-1,x+m/4,y+m*.683f);g.restore();}}public
void start(Stage s){c=new Canvas(n,n);g=c.getGraphicsContext2D();g.setGlobalBlendMode(BlendMode.DIFFERENCE);g.setFill(Color.TAN);g.fillRect(0,0,n,n);d(n,3,0,0);Pane
p=new Pane();p.getChildren().add(c);s.setScene(new Scene(p));s.show();}public
static void main(String[]a){n=Long.valueOf(a[0]);launch();}}

Це залишає небажані краї, як ви можете бачити на цьому скріншоті .


0

JavaScript (ES6), 279

Рекурсивно створюйте полотна та додайте дитині полотно чотири рази до батьківського полотна. На нижньому шарі полотна - це єдине коло; це полотно чотири рази відбивається на батьківському полотні, а потім це полотно чотири рази на остаточне головне полотно.

(n,o=0)=>(r=o-2&&f(n/2,o+1),c=document.createElement`canvas`,X=c.getContext`2d`,d=(x,Q)=>(X.drawImage(r,x,k+Q*k*Math.sqrt(3)),d),c.width=c.height=n,m=n/2,k=n/4,X.fillStyle=o%2||"red",X.fill(X.clip(X.arc(m,m,m,0,7))),r&&d(0,0)(m,0)(k,-1)(k,1),o?c:location=c.toDataURL`image/jpeg`)

зображення подання

Демонстраційна демонстрація:

З пробілом, коментарями і м'яко не враженими:

f=(n,o=0)=>(
    // recursively create another canvas if we're not at the deepest layer
    var r;
    if(o < 2) { r = f(n/2,o+1); }

    // create this canvas
    c=document.createElement("canvas"),
    c.width=c.height=n,
    X=c.getContext("2d"),

    // helpful postions
    m=n/2, k=n/4, q=k*Math.sqrt(3),

    // draw a circle and clip future draws within this circle
    // either fills red (the shortest color name) or a non-color that defaults to black
    X.fillStyle= o%2 || "red",
    X.arc(m,m,m,0,7),
    X.clip(),
    X.fill(),

    // define a chainable `drawImage` alias (the `d` function returns itself)
    d=(x,y)=>(X.drawImage(r,x,y),d)

    // if we have a recursive canvas, draw it four times by chaining `d`
    if(r) { d(0,k)(m,k)(k,k-q)(k,k+q); }

    // if this is the top-layer (o==0), show the final jpeg
    if(o == 0) { location = c.toDataURL("image/jpeg"); }

    // return this canvas, to be used recursively
    c
)

Це може легко створити більш глибокі шари рекурсії, змінивши початкове o-2або будь-яке велике o-zзначення.

Зауважте, що це подання буде виконуватися лише у Firefox, завдяки використанню функцій ES6 та неузгодженості в API для аргументів fillта clipаргументів.

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.