Scenergy #01
31 мая 1999

Coding - sync with the music in demah.

<b>Coding</b> - sync with the music in demah.
     Synchronizing with music demah.

 After watching the huge pile of dem (as
outside and looking at their code)
after conversations with many people at
Spectrum demoscene is my regret
come to a disappointing conclusion. The point
that our brave coders
the miracles of ingenuity in the writing
various effects, like virtually all
a forgotten such an important thing as
synchronization of images on the screen
music. More precisely all the methods of work,
concerning the degree of synchronization
development are just in their infancy
state. And what is more sad - not
noticeably particular attempt to move from
deadlock in this regard.
 Of course we can not say that all teams
suffer from this - there are quite a successful
methods of organizing synchronization. But in
most cases, one of the 2
the most popular methods of synchronization:
 1) Sync on end pattern'a
music. Surely, this method appeared
first because it is the simplest and most
wretched in their capabilities. Its essence
that of the music player to any
manner accrue to the data that
over the current pattern in music. By
this signal a change of effect.
 2) Counter interrupt. The method consists in
that hangs on the interrupt counter
which is increased incrementally
a memory cell. Thus,
in this cell will always be
number of interrupts since the
Launch of music. And since music player, too
depends on interrupts, we can establish
correspondence specific notes
music and a constant, which
appears in this counter at the moment
play that note.
 In order to synchronize
any point in a certain Deme
a note in music - in the appropriate place in
code is inserted into a piece about
read:


        LD DE, 
LOOP HALT

        LD HL, (NOTE_COUNTER)

        OR A

        SBC HL, DE

        JR NZ, LOOP

 And like everything is normal, you can
synchronize any event for any
note, but there are still 2 very unpleasant
moment:
 1) Synchronization is obtained by a linear one.
Ie using this method you can specify
synchronization only for a few
sequence of events. When
Moreover, if this sequence
change - will have to edit the code.
Organize the same in this method work
multiple parallel mini-effects
(As in credits to Forever final
release) and asynchronously
is the task if not
impossible, then at least very
difficult. But even with this in principle
can tolerate, if not for 2-I am the cause.
 2) If necessary, move
any time synchronization
have to edit code! A code change
entails at least an additional
recompiling, downloading an object code
to repackage and re-linking demos.
IMHO fairly high price for a change
2 bytes! And if you approach the process
Fix demos to the music rather
responsibility - the need for shifting
synchronization will occur continuously. A
then there's a global shortage of time due to
that party on the nose ...
Generally, if you ever wrote demos,
You will understand what I mean:)

 Thus, as shown by a more in-depth analysis -
none of these methods can not
allow normal
synchronization.
 So, having learned from bitter experience, build
Binary Love, when I decided to write Forever
approach to the organization of the mechanism
sync with the music from the other side.
 As a result, a system was developed
synchronization is quite different from
all I could see in the earlier demah
(Or, if someone did before me -
nothing did not tell anyone:)).
Subsequently, when writing CC999
invitation dentro, this system has undergone
further processing and as a result of
at the moment I have the system
synchronization, which is devoid of all
deficiencies described above, methods, and
In addition there are several additional
attractive opportunities.
 The proximity of CC999, and output of the first
rates so long awaited by all
Scenergy prompted me to write this
articles describing my system. Except
addition, the annex you will find complete
source of CC999 invitation intro
dentro. This is an excellent example of how
used this system synchronization
as in the intro, I used every opportunity
this system. And in addition, intro is very
simple to code and nobody will be working
or tail of it.
 Thus, the main tasks in developing
this system were:
 - Abstracting the synchronization of the code.

   Ie I wanted to create a system so that

   it allowed me to build after all

   demos to a bunch of deal only with its

   sync with the music, it is not

   touching the code.
 - Ability to synchronize asynchronous.

   Sounds a bit unusual, but just

   expresses the essence. It was necessary to

   organize everything so that I could

   synchronize with the music work

   several components of the effect

   working independently. For example in the intro

   by CC999 invitation dentro parallel

   work:

   - Output of credits.

   - Output of the inscription "CC'999".

   - Blinking screen.

   And their sequence does not

   defined in the code!
 After careful study of the question I
concluded that the best solution
will create some kind of psevdoprogrammy
synchronization. Therefore, the overall scheme of work
synchronization system is approximately as follows:
 - For each effect, additional
written in his own little psevdoprogrammka
describing when and what to do with this
effect. Of course, the term "psevdoprogramma"
probably too loud sounds - in fact
really just a table. But after their own
functions, it reminds me much more
aaplet:) Read more about it - below.
 - Interrupt-in addition to
standard interrupt handler hangs
resident performing the following functions:

   - Border management

   - Play music

   - Management of synchronization events
 This resident is just and deals
interpretation of "program" synchronization.
And here the situation is quite different
by the method described above with a counter. In
It was the main effect and the counter -
subordinates. Here, the opposite is true: the effect of
plays a subordinate role, as a resident -
the role of manager.

 Before considering the principle of
of residents - need to consider
detail the structure of the table synchronization.
 Each table consists of 2 x
Fields:
[Word] - The counter value at which

         will be generated messages

         sinhronizizatsii.
[Byte] - The code is generated posts.

 There can be three types of messages:
 - Timing (M_SYNC). They
designed so that at
necessary, could wait for the arrival of
certain notes. To do this in code
inserted into the procedure call
WAIT_FOR_MARKER. You can also continue
work in parallel monitors
marker - for this is the procedure
CHECK_FOR_MARKER. Incidentally, I note that
synchronizing tokens accumulate,
ie if the mark has come, but was not
processed - it is saved and is given by
the first call to clock
procedures. Thus preventing loss
markers on slower machines, and how
result - removed circularity in
procedure WAIT_FOR_MARKER.
 - "Attack" (M_BEAT). These messages
handled by the resident and
designed to blink
screen beneath the striker:) When you start the effect
this handler is initialized, it
a pointer to the beginning of handlers
and the end of the flashing speed of blinking and color
border by default and is blinking. When
arrival token handler is called
start blinking (in this Annex
intro is _START_FLASH), and then, after
specified number of interruptions caused by
procedure handler end flashing (in
intro is _END_FLASH). All actions
provide flashing assume these
procedures, and they are different for each
effect. The only thing that the resident does
themselves - sets the color
curb. This is a unified management
border to avoid any
INT'ov on the curb.
 - Custom. This is the most powerful in its
Opportunity type markers. Each
possible event is assigned a unique
ID, and the parish marker
handler is called custom markers (in
intro is a procedure ACTIONS_HANDLER),
and which performs the necessary steps in
Depending on the identity marker.

 Resident hanging on interrupts, and each
interrupt performs the following actions:
1) increments the counter interrupts.
2) Checks to see if the counter value
in the current row of the table synchronization.
3) If not equal to - go to item 5
4) It checks the message type. Further
actions depend on the type:
 - M_SYNC. Counter is incremented

   unclaimed clock

   markers. This counter is decremented

   whenever the clock

   token is given to the program, so it is

   can accumulate tokens in order

   then to give them on-demand

   program.
 - M_BEAT. Handler is called early

   flashing screen. Also occurs

   initialization of internal variables

   so that after a specified period

   Time to call the procedure handler

   the end of the flashing screen.

   In this case, the handler does not have to think about

   state border - it is automatically

   controlled by a resident.
 - Custom. Handler is invoked

   synchronizing message given

   user. A pointer to it, as

   as all the other necessary

   procedure, when a resident is transferred

   initialization effect.

   Handler is passed an identifier

   current message (in case A) and

   dependence on him, this procedure

   must decide - what to do.
 By the way, custom messages can also
accumulate, but only within
one interrupt. This enables
ask a few clock markers
triggered in a single interrupt.
 Items 2-4 are repeated until, until
there are tokens that must be processed in
This interruption.
5) to process all the accumulated
custom messages. The handler is called for
Each custom message.
6) checks a table of functions for
Pending the call (about this - below) and, if
necessary, call the appropriate
procedure.
7) Playing music.

 In addition, the resident provides another
an additional mechanism to directly
timing is not related, but
makes it much easier
implementation of certain things.
 This so-called mechanism of delayed
function calls. Its essence is that it
You can call any procedure
but not immediately, but after a certain
number of interrupts.
 As an example quote
real situation, all from the same intro.
 1) Since intro to each interrupt
there is a change of screens, at the moment
synchronizing the arrival of messages can not be
predicted in advance - what the screens
will be at this point is visible. But to
normal (no flicker) to remove such
sprite credits requires that
it included a specific screen. What
do if the screen is not the same?
Use HALT for passing interrupts
can not - will fail to work
the main effect as This procedure
located outside the main loop of the program.
Using the mechanism of the deferred call
will resolve this issue quickly and
painless:


        LD A, (PAGE); current state of port # 7FFD

        AND # 08; check what screen is on

        JR Z, ... 0; Enabled want us to screen
; Enabled not the screen that we needed to wait
, The next interruption.

        LD HL, VIEW_SPRITE; pointer to this same procedure

        LD A, 1, to skip a number INT'ov

        CALL ADD_IM2_HANDLER; Adding procedures for

        RET; deferred call and exit.
... 0; Drawing sprites

 2) Once printed sprite
another credits - he has a
some time to be erased from the screen. This
the problem is solved in an elementary -
simple process of drawing sprites at once
sets aside for a time call
function erase sprite.

 In real code, the resident is decorated in the form of
2 modules:
 RESIDENT.A - code of the resident.
 RES_EQUS.A - EQUS set for him. In
 Basically you can combine them, but I love
 all EQUS were in separate modules.

 In addition, in the intro is
special section entitled as a Demo
system environment. This section of code
is a kind of "emulator"
of the environment that will exist
collected in the Deme. This allows
subsequently moved into the finished effect
DeMouy with minimal changes (which
just turn off the conditional compilation).
 Consider the so-say "interface"
resident. I will only consider
variables and procedures that
directly related to the process
synchronization.

               Variables:

IM2_HANDLER - pointer to the handler IM2
interrupts.

BEAT_START_FLASH - pointer to the procedure
which will be called the parish
"Shock" marker. It should lead
screen in the form required for creation
visibility "Blink" screen. As a rule,
simply fill in one of the attributes
screens in white.

BEAT_END_FLASH - pointer to the procedure
which will be called to
restore the screen after "Blink".
FLASH_SPEED - Number of interruptions
allocated to one "blink" screen.
Simply put, through a number of
interrupt will be caused by the procedure
pointer which is set in a variable
BEAT_END_FLASH.

BORDER - Border color by default. As
usually black.

BEAT_BORDER - Border color for "Blink"
screen. Usually white.
MARKERS_HANDLER - pointer to the procedure
which will be called upon arrival of any
custom message. Message ID
will be transferred to it in the register A.

 Variables must be initialized before
how will first appeal to the
Resident! Actually, looking at
source intro, you'll see how
does this initialization.


                Procedure:

CHECK_FOR_MARKER - Check for existence
synchronizing token. At the exit of
This procedure CY flag will be set to
if the timing marker
was. In this case, the token is removed and considered
that he was successfully given to the program.
 Example of use:
MAINLP; main loop effect

        HALT

        

        CALL CHECK_FOR_MARKER

        JR NC, MAINLP

        ; Exit the main loop
WAIT_FOR_MARKER - Waiting for token
synchronization. The program will emerge from this
procedure only on the arrival token. If
raw markers were - a procedure
will return control of the caller
immediately.

CHECK_FOR_BEAT - The procedure returns a flag
CY = 1 if currently running
"Blink" screen.

IM2_RESIDENT - himself a resident. Calling this
procedures must be put to the most
first in your interrupt handler:

IM2 PUSH 

        CALL IM2_RESIDENT

        

        POP 

        EI

        RET
 This is necessary in order to avoid
unwanted INT'ov on the curb when you change
Border color.
ADD_IM2_HANDLER - The procedure is responsible for
deferred function calls. At the entrance to her
are given by:
 HL - Pointer to a subroutine.
 A - Number of skipped interrupts.

      Current interruption is also considered,

      therefore A = 1 means that the procedure

      will be called in the next interruption

EXIT - The procedure for withdrawal from the effect.
Restores all the necessary values ​​and
makes all efforts to ensure
correct output. To its normal
work at the beginning of your program
need to put the line:

             LD (EXIT_SP), SP
 This will allow you to leave out the effect
immediately, without waiting for completion of the cycle
constructing the next frame.

 I will not give examples here
procedures handlers, because all of them
quite elementary, so you can
to understand them yourself.
 Over the annexed
source. I already wrote in the article about bump
mapping and write it again: because of the specificity
my code (and I very often use
syntax specific to TASM'a) all my
sources normally are only compiled in
TASM v4.12 by RST7/CBS and nowhere else!
Ie to work with these
source you have to willy-nilly
use TASM. Although theoretically
can be converted into work in other
assemblers, but lost all
flexibility to configure them, which for me personally
totally unacceptable.
 However, if you use TASM'a
unacceptable (for example, for ideological
reasons:)) - you can simply
use listed here
descriptions for writing their own
synchronization system.
 All copyrights on the idea and source code
belong to me, so that when you use
these sources, or when writing
own, but based on this
description necessarily mention of this.
To use the same source no
restrictions are imposed for
except that for any
distributing the source code should
remain as is! For personal
allowed the use of any
correction source.

PS: Yes, I almost forgot! After compiling
intro my macro will swear:

ALLOCATED FAST MEMORY WILL CORRUPT SOME INCLUDED DATA!!!

 Do not be scared - everything is fine:)





Other articles:

Chars - the charts with 116 questionnaires staff meeting Scenergy.

Charts - the best: Organizer, Musician, Coder, Cracking group, Scener, Group, Demo, Mazazine, Party.

Charts - Best: Single Coder, Cracker, Graphilian, Organizer, Musician, Group, Site.

Charts - Statistics - the numbers and thinking.

Coding - Driver RAM DISK'a for ZX-Spectrum'128.

Coding - On the use of macros or TASM 4.12 - RULEZ!

Coding - the implementation of Phong Bump Mapping on the Speccy.

Coding - sync with the music in demah.

Cracking Scene - crack contest.

Cracking Scene - Illegal scene on the Speccy.

Demo Parrt - venue CC'999.

Demo Party - gloomy thoughts Random'a: "What should I do for you to believe in design Haosa'999?"

Demo Party - New demopati: Designs Haosa'999 - past and future.

Demo Party - Pro Fun Top and all-all-all ... (Belated report Serzh'a in 5 parts)

Demoscene - Chaosite - technical data on Haosaytu.

Demoscene - the history of composition and softografiya Omega Hackers Group.

Demoscene - A new group Novgorodoskaya "RaZZLeRS".

Demoscene - An Open Letter to the scene and Kano himself.

Demoscene - the composition and the contacts of the Lithuanian group zERo.

Editorial - Information section - INDEX ...

Groups - statistics about the active groups: Digital Reality

News - Codebuster track stolen from Zhenya? Fatality site has moved. Extreme leaves the Spectrum. Wait for a 4-th number Subliminal Extacy? Lithuanian group Zer0 longer suschesvuet. Phantasy returned to the stage! Problems with Complex compo. Disputes about associations.

Sceneexplorer - Conments - based on questionnaires: "What about the Sprinter and dumate GMX", "where taking the program," in which networks have addresses.

Sceneexplorer - The results of the survey.

Sceneexplorer - List of questioning.

Scenergy - How to contact us.

Scenergy - Work with Scenrgy Setup.

VIP - Interview with David Brabenom c, author of the great game Elite.

VIP - An Interview with galandskoy demo group The Lords.

VIP - An interview with the Moscow Spectrum team - Cosmic (Progress).

Warez Pack - description of the application log: Energy Trackmo, Forever: Final Release, Yes.

Warez Pack - description of the application log: First Association

Warez Pack - description of the application log: Pussy: Love from Titanic, CrossWord.

Warez Pack - description of the application log: SpriteLand v1.27

Warez Pack - description of the application log: Worms



Similar articles:
Laughter through tears - Computer idiocy.

В этот день...   1 May