// This is how it's done!
http://lists.debian.org/debian-user-spanish/2005/01/msg00380.html


==========================================================================
 TASKS (client)
==========================================================================

MessageBox:
 [x]	- Make it.
 [x]	- Make icons.
 [x]	- Test it.

SplashScreen:
 [ ]	- Make it.

Mainwindow:
 [x]	- Clean out mgui code.
 [x]	- Make generic gui layout code.
 [x]	- Make icons.
 [x]	- Make statusbar.
 [x]	- Make flashing record bar.
 [ ]	- Show network connection status in statusbar.
 [ ]	- Show camera connection status in statusbar.
 [x]	- Save movie messagebox (yes/no/dunno)
 [x]	- Create snapshot thumbnails from dv stream instead of the widget.
 [x]	- Make sure the same frame is shown in thumbnail as the one actually 
	    shot on the server.
 [ ]	- Test it.

CPRQueryDialog:
 [x]	- Make it!
 [x]	- Clean out unnesessary code.
 [x]	- Make cancel posibility (return code 0 should do something useful)
 [x]	- Insert timer for network connection timeout.
 [x]	- Send connection status info to mainwindow.
 [x]	- Make icon (backspace)
 [ ]	- Test it.

Encoder:
 [x]	- Send savestate signal.
 [x]	- Make all data sent before deleting network object. (flush)
 [x]	- Remove ffmpeg code.
 [x]	- Make use of 2.6 kernel (through raw1394)

Decoder:
 [ ]	- Enable sound decoding for the network stream.
 [x]	- Remove ffmpeg code.
 [x]	- Make use of 2.6 kernel (through raw1394)
 [x]	- Set flags on frame objects.

Camera:
 [x]	- Add initialize method (constructor should do nothing).
 [%]	- Add getStatus methods. (implemented through error object)

Player:
 [x]	- Remove ffmpeg code.
 [x]	- Use libdv for dv decoding

==========================================================================
 TASKS (server)
==========================================================================

ImgEncoder:
 [x]	- Make libjpeg calls work again.

MovEncoder:
 [x]	- Test Mpeg4. (no good)
 [ ]	- Remove ffmpeg code.
 [ ]	- Enable sound.

Main:
 [ ]	- Save movie signal handling.
 [x]	- Read server root folder from config.
 [x]	- Use correct filenames and paths.
 [x]	- Check for writabilty before trying to do any writing.
 [x]	- Create fallback, when unable to write the requested filename.

==========================================================================
 TASKS (common)
==========================================================================

Makesystem:
 [x]	- "Port" to automake/autoconf
 [x]	- Make LibSDL detection in configure script
 [x]	- Make LibJpeg detection in configure script
 [ ]	- Make ffmpeg detection in configure script
 [x]	- Make server standalone compilable (through flag to configure)
 [x]	- Include pixmaps and tools in distdir.
 [x]	- Make pixmaps correctly intalled.
 [x]	- Make QT link correctly on fedora core 1
 [x]	- Make libJpeg link correctly on fedora core 1
 [x]	- Make configuration files installed in $(prefix)/etc/miav

MiavConfig:
 [x]	- Integrate file parser.
 [x]	- Use error object.
 [ ]	- Make code for input validity test.
 [x]	- Initialize one global configuration object.

ErrorObject:
 [x]	- Make it.
 [x]	- Maintain error string stack, instead of appending.
 [x]	- Make it thread safe.
 [x]	- Make pushError take any number parameters and parse them on to sprintf
 [ ]	- Make it a superclass.
 [ ]	- Create a textmode version subclass (for the server).
 [ ]	- Create a QT version subclass (callback to mainwindow with messagebox).
 [ ]	- Append to log, whenever error occur.

FFMpegWrapper:
 [%]	- Make it.(FFMPEG is on its way out of the project)


==========================================================================
 SAVE THE MOVIE?
==========================================================================
When the stop button is clicked, a msg box pops up, "Save? [yes, no, dunno]"
network connection is no killed before this has been answered, and an empty 
frame has been send to the server with the answer.

On the serverside, a variable describing wether the file is to be saved (SAVE), 
deleted (DELETE), og scheduled for later descision (LATER).

It is initialized with LATER, in order to prevent errors due to a malfunction
leading to a disconnection.

If a flag is recieved, the state is overwritten.

If the state is SAVE, when the connection is terminated, the file is moved to
a folder containing permanent data store.

If the state is DELETE, the file is moved to a folder containing files scheduled
for deletion, when more space is needed (no files are removed at this point)

If the state is LATER, the file is moved to a folder containing files with this
purpose.

A cron job examines this folder regularly (test how often).
If a file has been here for more than a week, the administrator is contacted by
email.

==========================================================================
 Semphores and mutexes in the client network architechture
==========================================================================
,-----------.
| DV stream |
`-----------'
      |
      V
,-----------.
| Decoder   |
`-----------'
      |      \
      V       \
,-----------.  \
| Player    |   \
`-----------'    \
                  \  ,-----------.
                   ->| Encoder   |
                     `-----------'


==========================================================================
 This code should convert yuv to yuv422 planar
==========================================================================
int Frame::ExtractYUV420( uint8_t *yuv, uint8_t *output[ 3 ] )
{
         unsigned char *pixels[ 3 ];
         int pitches[ 3 ];
         int width = GetWidth(), height = GetHeight();
 
         pixels[ 0 ] = ( unsigned char* ) yuv;
         pitches[ 0 ] = decoder->width * 2;
 
         dv_decode_full_frame( decoder, data, e_dv_color_yuv, pixels, pitches );
 
         int w2 = width / 2;
         uint8_t *y = output[ 0 ];
         uint8_t *cb = output[ 1 ];
         uint8_t *cr = output[ 2 ];
         uint8_t *p = yuv;
 
         for ( int i = 0; i < height; i += 2 )
         {
                 /* process two scanlines (one from each field, interleaved) */
                 for ( int j = 0; j < w2; j++ )
                 {
                         /* packed YUV 422 is: Y[i] U[i] Y[i+1] V[i] */
                         *( y++ ) = *( p++ );
                         *( cb++ ) = *( p++ );
                         *( y++ ) = *( p++ );
                         *( cr++ ) = *( p++ );
                 }
                 /* process next two scanlines (one from each field, interleaved) */
                 for ( int j = 0; j < w2; j++ )
                 {
                         /* skip every second line for U and V */
                         *( y++ ) = *( p++ );
                         p++;
                         *( y++ ) = *( p++ );
                         p++;
                 }
         }
}