1

Тема: Spiral demo

Возможно, кто-то уже знаком с анимированной демкой, в которой спираль рисуется методом черепашьей графики(turtle graphics).
На данный момент она является скринсейвером по умолчанию и в дистрибутиве KolibriOS находится тут '/sys/demos/spiral'.
Я хотел переделать, чтобы линии были сглаженные(smooth lines), однако, ядро рисует только обычные, несглаженные линии.
В библиотеке Buf2D имеется функция для рисования таких линий, я решил её использовать.
То есть, рисование происходит в буфере с помощью библиотеки Buf2D, а затем выводиться на экран.
Также сделал небольшое изменение: теперь размер изображения изменяется со временем(увеличивается, потом уменьшается и наоборот).misc.php?action=pun_attachment&item=97&download=0

К сожалению, есть некоторые проблемы со сглаженными линиями в библиотеке Buf2D

Одна из проблем в том, что некоторые линии, с углом наклона примерно 45 градусов, рисуются неправильным цветом, нецветные, тёмные, на чёрном фоне их даже незаметно, но заметно "незакрашенное" место(просвет), там, где должна была рисоваться линия.misc.php?action=pun_attachment&item=98&download=0
  Иногда такие линии рисуются только частично не на всю длину, либо их середина не прорисовывается.
  Очень похоже, что это баг в библиотеке Buf2D, потому что код, рисующий обычные линии работает верно:

  buf2d_line(Buf2DBuffer, X1, Y1, X2, Y2, Color);

проблема только со сглаженными линиями:

  buf2d_line_sm(Buf2DBuffer, X1, Y1, X2, Y2, Color);

Горизонтальные сглаженные линии в Buf2D рисуются толщиной в 1 пиксель, а вертикальные 2 пикселя.
  Тут, по логике, надо в обоих случаях рисовать одинаково: либо и там, и там — 1 пиксель, либо и там, и там — 2 пикселя
  Даже, наверное, правильнее именно 1 пиксель, так же, как рисуются и линии под углом 45 градусов.

И, кстати, некоторая проблема с цветом имеется при выводе шрифта

в приложении "Файловый навигатор" с помощью функции buf2d_draw_text: интенсивность правильного цвета и выводимого через Buf2D отличается, хотя и очень незначительно(например, вместо RGB(253, 253, 253) выводится RGB(252, 252, 252)).
  Сравнивать правильность можно с цветом в файле шрифта FNT.PNG — по сути это чёрный($00000000) текст на белом($00FFFFFF) фоне.

Приложение собирается с помощью SDK, скачайте его релиз.
Архив с исходником распакуйте в папку "My" и собирайте, запустив build.bat — в папке "bin" создастся приложение "kex".
Также прикладываю уже готовое приложение Buf2dSpiral.kex.

Post's attachments

Иконка вложений Buf2dSpiral.7z 3 Кб, 78 скачиваний с 2021-12-06 

Иконка вложений Buf2dSpiral.kex 1.54 Кб, 76 скачиваний с 2021-12-06 

Иконка вложений Spiral_buf2d_incorrect.png 534.7 Кб, 45 скачиваний с 2021-12-06 

Иконка вложений Spiral_buf2d.PNG 526.19 Кб, 52 скачиваний с 2021-12-06 

2

Re: Spiral demo

0CodErr пишет:

На данный момент она является скринсейвером по умолчанию и в дистрибутиве KolibriOS находится тут '/sys/demos/spiral'

Этот скринсейвер всегда вызывал у меня вопрос с точки зрения процедуры сохранения пикселей экрана. По логике, меняющееся изображения должно попеременно захватывать все пиксели, а не выжигать дырку посередине.

3

Re: Spiral demo

Freeman пишет:

с точки зрения процедуры сохранения пикселей экрана

Да, современные скринсейверы похоже утратили своё первоначальное предназначение.
Однако, теперь этот скринсейвер работает чуть по-другому

0CodErr пишет:

сделал небольшое изменение: теперь размер изображения изменяется со временем

4

Re: Spiral demo

Красиво)

Добавлено 2021-12-26 в 23:42

Можно ли добавить поддержку @SS как в оригинале?

5

Re: Spiral demo

Leency пишет:

Можно ли добавить поддержку @SS как в оригинале?

Можно.
Но ещё желательно пофиксить функцию рисования сглаженных линий buf2d_line_sm из библиотеки buf2d(в первом сообщении под спойлером описана суть проблемы со скриншотом, иногда линии не прорисовываются).

Я бы вообще саму логику работы @SS изменил.
Сейчас, насколько понимаю из исходника, логика такая:
если время истекло, то запустить приложение-ScreenSaver(в данный момент это Spiral), а самому @SS завершиться.
Теперь приложение Spiral ждёт события, если оно произошло, то запускает снова @SS, а само завершается.
Ну разве это не забавно!? smile

А теперь, как было бы логичнее сделать:
если время истекло, то запустить приложение-ScreenSaver(в данный момент это Spiral), запомнив его идентификатор, и ждать события, если оно произошло, то послать сообщение приложению-ScreenSaver(в данный момент это Spiral) о нажатии кнопки закрытия окна — приложение-ScreenSaver завершится.

Есть ещё один вариант, может и не совсем идеологически верный, но можно было бы просто прибить процесс с помощью TerminateThreadById(SysFn18.18) — мы ведь всё равно ничего не теряем, скринсейверы же просто графику рисуют.

Но тут ещё похоже нужно фиктивное окно, чтобы принимать события клавиатуры, ну окей, нарисуем окошко нулевого размера, чтобы не загораживало приложение-ScreenSaver.


Кстати, насчёт "оригинала", который уже не оригинал — привет тому умнику, который заменил инструкцию fcomip, аргументируя это тем, что она появилась в семействе процессоров P6, однако, он сам при этом использует инструкцию cmovz.
Пусть почитает, например, это на странице 253

The CMOVcc  instructions were introduced in P6 family processors; however, these instructions may not be supported by all IA-32 processors.
Software can determine if the CMOVcc instructions are supported by checking the processor’s feature information with the CPUID instruction (see “CPUID—CPU Identification” in this chapter).

и который заменил человекочитаемые имена функций, такие как DrawWindow, SetEventMask, GetTickCount, CheckEvent на макросы mcall: mcall   0, mcall   40, mcall   26, 9, mcall   11 — ну тогда бы сразу в двоичном коде писал для пущей важности smile
Проще говоря, это пример, как делать не надо было!


Что касается текущего варианта поддержки @SS, то можно сделать так:

var
  IsScreenSaver: Boolean = False;
  ThreadInfo: TThreadInfo;
  MySlot: LongWord;

if StrCmp(CmdLine, '@ss') = True then
begin
  IsScreenSaver := True;
  GetThreadInfo($FFFFFFFF, ThreadInfo)
  MySlot := GetSlotById(ThreadInfo.Identifier);
end;

а во время отрисовки  проверяем

if IsScreenSaver then
  if GetActiveWindow <> MySlot then
  begin
    RunFile('/sys/@SS', '');
    (* завершаем программу *)
  end;

6

Re: Spiral demo

Вроде как первое fixed:
http://board.kolibrios.org/viewtopic.php?p=77777#p77777