Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

192 lines
6.6 KiB

  1. Using AVIFile.
  2. Initializing the AVIFile DLL:
  3. Before using any of the APIs in AVIFILE.DLL, be sure to
  4. call AVIStreamInit. After using them, call AVIStreamExit.
  5. If you don't, bad things will happen.
  6. Using AVIFile to read some kind of file:
  7. First, call AVIFileOpen with the OF_READ flag to open the file.
  8. Then, you can call AVIFileInfo to find out how many streams are in
  9. the file, and AVIFileGetStream to retrieve the streams you want.
  10. Once you have a stream, you can can AVIStreamReadFormat to get the
  11. bitmap format or wave format, and then call AVIStreamRead to actually
  12. read the data you want.
  13. AVIFile and the Component Object model:
  14. The AVIFile APIs include two interfaces, IAVIFile and IAVIStream,
  15. which work with the Component Object model which is part of OLE 2.0.
  16. Class IDs
  17. Each server or DLL that handles these interfaces needs to have a
  18. Globally Unique ID (GUID), so that it can be distinguished from all
  19. other handlers. OLE uses 16-byte identifiers for this purpose. If
  20. you're making a new handler, you can run the UUIDGEN program to make
  21. yourself a unique ID.
  22. The Registration Database
  23. The registration database is essentially just a replacement for .INI
  24. files. To look at what's going on in it, run "regedit -v".
  25. DLLs which implement the IAVIFile and IAVIStream interfaces all need
  26. to be listed in the registration database so that they can be found
  27. when necessary.
  28. Each DLL must be listed in the registration database by class ID,
  29. with entries of the form:
  30. HKEY_CLASSES_ROOT\Clsid\{00020003-0000-0000-C000-000000000046} = Wave File reader/writer
  31. HKEY_CLASSES_ROOT\Clsid\{00020003-0000-0000-C000-000000000046}\InprocServer = wavefile.dll
  32. where HKEY_CLASSES_ROOT is the root of the entire registration
  33. database. The InProcServer entry indicates that wavefile.dll can be
  34. loaded within an application to implement the class in question.
  35. The AVIFile library uses additional entries in the registration
  36. database in order to know which handler to use by default to open a
  37. given file. If the file is a RIFF file,
  38. HKEY_CLASSES_ROOT\AVIFile\Extensions\WAV = {00020003-0000-0000-C000-000000000046}
  39. HKEY_CLASSES_ROOT\AVIFile\RIFFHandlers\WAVE = {00020003-0000-0000-C000-000000000046}
  40. You get a GUID by running the uuidgen.exe program that comes
  41. with the SDK; it will spit out a 16-byte hex number for you. You then
  42. make a file with a .REG extension that looks like:
  43. REGEDIT
  44. HKEY_CLASSES_ROOT\Clsid\{5C2B8200-E2C8-1068-B1CA-6066188C6002} = JFIF (JPEG) Files
  45. HKEY_CLASSES_ROOT\Clsid\{5C2B8200-E2C8-1068-B1CA-6066188C6002}\InprocServer =jfiffile.dll
  46. HKEY_CLASSES_ROOT\AVIFile\Extensions\JPG = {5C2B8200-E2C8-1068-B1CA-6066188C6002}
  47. (Of course, use your GUID here.) Then, on a user's machine, they can run
  48. regedit -s whatever.reg and these definitions will get added to the
  49. registration database, allowing the system to find your DLL and know what
  50. sorts of files it can load.
  51. What are IAVIFile and IAVIStream?
  52. (Note: you may just want to read the OLE 2 documentation here....)
  53. These are examples of "interfaces". An interface is a collection of
  54. "methods".
  55. Implementing a handler DLL
  56. IClassFactory
  57. Obviously, it isn't enough for OLE to know the name of your DLL; some
  58. standard entry point is required to establish communications. The
  59. method through which COMPOBJ.DLL does this isn't exactly
  60. straightforward. A handler DLL must export a DllGetClassObject
  61. function; COMPOBJ calls that function to ask the DLL to return an
  62. instance of the IClassFactory interface, which it then uses to
  63. actually acquire an instance of the IAVIFile interface that we
  64. actually care about.
  65. Single-stream vs. Multi-stream
  66. AVI files obviously support more than one stream of data in each
  67. file. Wave files, for example, are much simpler, in that they only
  68. can have exactly one stream of audio. This means that we only need
  69. one stream object around, and we can make things even simpler by
  70. having the same object support both the stream and file interfaces.
  71. If you know that your handler will support, say, exactly one audio
  72. and one video stream, things are also simpler than the completely
  73. general case, because when you create your file object, you know that
  74. you will have to create exactly two stream objects.
  75. Read-only vs. Read-write
  76. A handler can be written which only supports reading or writing; you
  77. can always return an error code from any method. (One suggestion:
  78. don't return unsupported from the FindSample function, but rather
  79. just return that every frame is a key frame, every frame is non-empty, and
  80. that the only format change is frame 0)
  81. Using C++
  82. These handlers don't actually need to be implemented using C++; it
  83. was just easier that way.
  84. Installing your handler:
  85. For your handler to be found, it needs to have the appropriate
  86. entries in the registration database.
  87. Compression DLLs
  88. When you call AVIMakeCompressedStream, you pass in a PAVISTREAM and
  89. are returned another PAVISTREAM. This new stream can be used in two
  90. ways: either you can read from the stream, in which case you will
  91. read data which is compressed from the original stream, or you can
  92. write to the new stream, in which case the data you write will be
  93. compressed and written to the original stream.
  94. To use the "read" method, you would use the following sequence of
  95. calls: (extra parameters left out because I can't remember them at
  96. the moment)
  97. AVIFileOpen(&pf, "foo.avi",...)
  98. AVIFileGetStream(pf, &ps, ...)
  99. AVIMakeCompressedStream(ps, &psC, &options, ...)
  100. AVIStreamReadFormat(psC, lpFormatC, &cbFormatC) // get compressed format
  101. for (loop through frames)
  102. AVIStreamRead(psC, frame, ....) // read compressed frames
  103. To use the "write" method:
  104. AVIFileOpen(&pf, "foo.avi", OF_CREATE | OF_WRITE...)
  105. AVIFileCreateStream(pf, &ps, &strhdr, ....)
  106. AVIMakeCompressedStream(ps, &psU, &options, ...)
  107. AVIStreamSetFormat(psU, lpFormatU, cbFormatU) // set format of data
  108. // to compress
  109. for (loop through frames)
  110. AVIStreamWrite(psU, frame, ....) // write uncompressed frames,
  111. // which will be compressed and
  112. // written to the file
  113. Using the Clipboard functions
  114. The clipboard functions are easy. To copy a bunch of streams to
  115. the clipboard, call AVIMakeFileFromStreams to bundle them up into a
  116. single PAVIFILE, then call AVIPutFileOnClipboard. To get data off of
  117. the clipboard, call AVIGetFromClipboard. To see whether any data is
  118. present on the clipboard, for enabling menus or such, you can just
  119. call AVIGetFromClipboard to see if it returns anything, and release
  120. any file it returns.