├── .gitignore ├── .gitlab-ci.yml ├── AUTHORS ├── COPYING ├── Doxyfile ├── Makefile.am ├── NEWS ├── README.md ├── bootstrap ├── configure.ac ├── examples ├── helloworld │ └── main.cpp ├── imem │ └── imem.cpp └── renderers │ └── discovery.cpp ├── libvlcpp.pc.in ├── m4 └── stdcxx_11.m4 ├── test └── main.cpp └── vlcpp ├── Dialog.hpp ├── Equalizer.hpp ├── EventManager.hpp ├── Instance.hpp ├── Internal.hpp ├── Media.hpp ├── MediaDiscoverer.hpp ├── MediaLibrary.hpp ├── MediaList.hpp ├── MediaListPlayer.hpp ├── MediaPlayer.hpp ├── Picture.hpp ├── RendererDiscoverer.hpp ├── common.hpp ├── structures.hpp └── vlc.hpp /.gitignore: -------------------------------------------------------------------------------- 1 | compile 2 | config.status 3 | config.h* 4 | config.log 5 | configure 6 | Makefile 7 | Makefile.in 8 | aclocal.m4 9 | *.cache 10 | depcomp 11 | install-sh 12 | missing 13 | build* 14 | -------------------------------------------------------------------------------- /.gitlab-ci.yml: -------------------------------------------------------------------------------- 1 | variables: 2 | VLC30_IMAGE: registry.videolan.org/medialibrary:20201009131431 3 | VLC40_IMAGE: registry.videolan.org/libvlcpp-unstable:20221213095400 4 | 5 | .common_build: 6 | rules: 7 | - if: '$CI_PIPELINE_SOURCE == "merge_request_event"' 8 | - if: '$CI_PIPELINE_SOURCE == "push" && $CI_COMMIT_BRANCH == "$CI_DEFAULT_BRANCH@videolan/libvlcpp"' 9 | tags: 10 | - docker 11 | - amd64 12 | script: 13 | - ./bootstrap 14 | - ./configure --enable-examples --enable-werror 15 | - make -j4 16 | - make -j4 distcheck 17 | 18 | continuous_build_4.0: 19 | extends: .common_build 20 | image: $VLC40_IMAGE 21 | 22 | continuous_build_3.0: 23 | extends: .common_build 24 | image: $VLC30_IMAGE 25 | 26 | -------------------------------------------------------------------------------- /AUTHORS: -------------------------------------------------------------------------------- 1 | Alexey Sokolov 2 | Hugo Beauzée-Luyssen 3 | -------------------------------------------------------------------------------- /COPYING: -------------------------------------------------------------------------------- 1 | GNU LESSER GENERAL PUBLIC LICENSE 2 | Version 2.1, February 1999 3 | 4 | Copyright (C) 1991, 1999 Free Software Foundation, Inc. 5 | 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA 6 | Everyone is permitted to copy and distribute verbatim copies 7 | of this license document, but changing it is not allowed. 8 | 9 | [This is the first released version of the Lesser GPL. It also counts 10 | as the successor of the GNU Library Public License, version 2, hence 11 | the version number 2.1.] 12 | 13 | Preamble 14 | 15 | The licenses for most software are designed to take away your 16 | freedom to share and change it. By contrast, the GNU General Public 17 | Licenses are intended to guarantee your freedom to share and change 18 | free software--to make sure the software is free for all its users. 19 | 20 | This license, the Lesser General Public License, applies to some 21 | specially designated software packages--typically libraries--of the 22 | Free Software Foundation and other authors who decide to use it. You 23 | can use it too, but we suggest you first think carefully about whether 24 | this license or the ordinary General Public License is the better 25 | strategy to use in any particular case, based on the explanations below. 26 | 27 | When we speak of free software, we are referring to freedom of use, 28 | not price. Our General Public Licenses are designed to make sure that 29 | you have the freedom to distribute copies of free software (and charge 30 | for this service if you wish); that you receive source code or can get 31 | it if you want it; that you can change the software and use pieces of 32 | it in new free programs; and that you are informed that you can do 33 | these things. 34 | 35 | To protect your rights, we need to make restrictions that forbid 36 | distributors to deny you these rights or to ask you to surrender these 37 | rights. These restrictions translate to certain responsibilities for 38 | you if you distribute copies of the library or if you modify it. 39 | 40 | For example, if you distribute copies of the library, whether gratis 41 | or for a fee, you must give the recipients all the rights that we gave 42 | you. You must make sure that they, too, receive or can get the source 43 | code. If you link other code with the library, you must provide 44 | complete object files to the recipients, so that they can relink them 45 | with the library after making changes to the library and recompiling 46 | it. And you must show them these terms so they know their rights. 47 | 48 | We protect your rights with a two-step method: (1) we copyright the 49 | library, and (2) we offer you this license, which gives you legal 50 | permission to copy, distribute and/or modify the library. 51 | 52 | To protect each distributor, we want to make it very clear that 53 | there is no warranty for the free library. Also, if the library is 54 | modified by someone else and passed on, the recipients should know 55 | that what they have is not the original version, so that the original 56 | author's reputation will not be affected by problems that might be 57 | introduced by others. 58 | 59 | Finally, software patents pose a constant threat to the existence of 60 | any free program. We wish to make sure that a company cannot 61 | effectively restrict the users of a free program by obtaining a 62 | restrictive license from a patent holder. Therefore, we insist that 63 | any patent license obtained for a version of the library must be 64 | consistent with the full freedom of use specified in this license. 65 | 66 | Most GNU software, including some libraries, is covered by the 67 | ordinary GNU General Public License. This license, the GNU Lesser 68 | General Public License, applies to certain designated libraries, and 69 | is quite different from the ordinary General Public License. We use 70 | this license for certain libraries in order to permit linking those 71 | libraries into non-free programs. 72 | 73 | When a program is linked with a library, whether statically or using 74 | a shared library, the combination of the two is legally speaking a 75 | combined work, a derivative of the original library. The ordinary 76 | General Public License therefore permits such linking only if the 77 | entire combination fits its criteria of freedom. The Lesser General 78 | Public License permits more lax criteria for linking other code with 79 | the library. 80 | 81 | We call this license the "Lesser" General Public License because it 82 | does Less to protect the user's freedom than the ordinary General 83 | Public License. It also provides other free software developers Less 84 | of an advantage over competing non-free programs. These disadvantages 85 | are the reason we use the ordinary General Public License for many 86 | libraries. However, the Lesser license provides advantages in certain 87 | special circumstances. 88 | 89 | For example, on rare occasions, there may be a special need to 90 | encourage the widest possible use of a certain library, so that it becomes 91 | a de-facto standard. To achieve this, non-free programs must be 92 | allowed to use the library. A more frequent case is that a free 93 | library does the same job as widely used non-free libraries. In this 94 | case, there is little to gain by limiting the free library to free 95 | software only, so we use the Lesser General Public License. 96 | 97 | In other cases, permission to use a particular library in non-free 98 | programs enables a greater number of people to use a large body of 99 | free software. For example, permission to use the GNU C Library in 100 | non-free programs enables many more people to use the whole GNU 101 | operating system, as well as its variant, the GNU/Linux operating 102 | system. 103 | 104 | Although the Lesser General Public License is Less protective of the 105 | users' freedom, it does ensure that the user of a program that is 106 | linked with the Library has the freedom and the wherewithal to run 107 | that program using a modified version of the Library. 108 | 109 | The precise terms and conditions for copying, distribution and 110 | modification follow. Pay close attention to the difference between a 111 | "work based on the library" and a "work that uses the library". The 112 | former contains code derived from the library, whereas the latter must 113 | be combined with the library in order to run. 114 | 115 | GNU LESSER GENERAL PUBLIC LICENSE 116 | TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION 117 | 118 | 0. This License Agreement applies to any software library or other 119 | program which contains a notice placed by the copyright holder or 120 | other authorized party saying it may be distributed under the terms of 121 | this Lesser General Public License (also called "this License"). 122 | Each licensee is addressed as "you". 123 | 124 | A "library" means a collection of software functions and/or data 125 | prepared so as to be conveniently linked with application programs 126 | (which use some of those functions and data) to form executables. 127 | 128 | The "Library", below, refers to any such software library or work 129 | which has been distributed under these terms. A "work based on the 130 | Library" means either the Library or any derivative work under 131 | copyright law: that is to say, a work containing the Library or a 132 | portion of it, either verbatim or with modifications and/or translated 133 | straightforwardly into another language. (Hereinafter, translation is 134 | included without limitation in the term "modification".) 135 | 136 | "Source code" for a work means the preferred form of the work for 137 | making modifications to it. For a library, complete source code means 138 | all the source code for all modules it contains, plus any associated 139 | interface definition files, plus the scripts used to control compilation 140 | and installation of the library. 141 | 142 | Activities other than copying, distribution and modification are not 143 | covered by this License; they are outside its scope. The act of 144 | running a program using the Library is not restricted, and output from 145 | such a program is covered only if its contents constitute a work based 146 | on the Library (independent of the use of the Library in a tool for 147 | writing it). Whether that is true depends on what the Library does 148 | and what the program that uses the Library does. 149 | 150 | 1. You may copy and distribute verbatim copies of the Library's 151 | complete source code as you receive it, in any medium, provided that 152 | you conspicuously and appropriately publish on each copy an 153 | appropriate copyright notice and disclaimer of warranty; keep intact 154 | all the notices that refer to this License and to the absence of any 155 | warranty; and distribute a copy of this License along with the 156 | Library. 157 | 158 | You may charge a fee for the physical act of transferring a copy, 159 | and you may at your option offer warranty protection in exchange for a 160 | fee. 161 | 162 | 2. You may modify your copy or copies of the Library or any portion 163 | of it, thus forming a work based on the Library, and copy and 164 | distribute such modifications or work under the terms of Section 1 165 | above, provided that you also meet all of these conditions: 166 | 167 | a) The modified work must itself be a software library. 168 | 169 | b) You must cause the files modified to carry prominent notices 170 | stating that you changed the files and the date of any change. 171 | 172 | c) You must cause the whole of the work to be licensed at no 173 | charge to all third parties under the terms of this License. 174 | 175 | d) If a facility in the modified Library refers to a function or a 176 | table of data to be supplied by an application program that uses 177 | the facility, other than as an argument passed when the facility 178 | is invoked, then you must make a good faith effort to ensure that, 179 | in the event an application does not supply such function or 180 | table, the facility still operates, and performs whatever part of 181 | its purpose remains meaningful. 182 | 183 | (For example, a function in a library to compute square roots has 184 | a purpose that is entirely well-defined independent of the 185 | application. Therefore, Subsection 2d requires that any 186 | application-supplied function or table used by this function must 187 | be optional: if the application does not supply it, the square 188 | root function must still compute square roots.) 189 | 190 | These requirements apply to the modified work as a whole. If 191 | identifiable sections of that work are not derived from the Library, 192 | and can be reasonably considered independent and separate works in 193 | themselves, then this License, and its terms, do not apply to those 194 | sections when you distribute them as separate works. But when you 195 | distribute the same sections as part of a whole which is a work based 196 | on the Library, the distribution of the whole must be on the terms of 197 | this License, whose permissions for other licensees extend to the 198 | entire whole, and thus to each and every part regardless of who wrote 199 | it. 200 | 201 | Thus, it is not the intent of this section to claim rights or contest 202 | your rights to work written entirely by you; rather, the intent is to 203 | exercise the right to control the distribution of derivative or 204 | collective works based on the Library. 205 | 206 | In addition, mere aggregation of another work not based on the Library 207 | with the Library (or with a work based on the Library) on a volume of 208 | a storage or distribution medium does not bring the other work under 209 | the scope of this License. 210 | 211 | 3. You may opt to apply the terms of the ordinary GNU General Public 212 | License instead of this License to a given copy of the Library. To do 213 | this, you must alter all the notices that refer to this License, so 214 | that they refer to the ordinary GNU General Public License, version 2, 215 | instead of to this License. (If a newer version than version 2 of the 216 | ordinary GNU General Public License has appeared, then you can specify 217 | that version instead if you wish.) Do not make any other change in 218 | these notices. 219 | 220 | Once this change is made in a given copy, it is irreversible for 221 | that copy, so the ordinary GNU General Public License applies to all 222 | subsequent copies and derivative works made from that copy. 223 | 224 | This option is useful when you wish to copy part of the code of 225 | the Library into a program that is not a library. 226 | 227 | 4. You may copy and distribute the Library (or a portion or 228 | derivative of it, under Section 2) in object code or executable form 229 | under the terms of Sections 1 and 2 above provided that you accompany 230 | it with the complete corresponding machine-readable source code, which 231 | must be distributed under the terms of Sections 1 and 2 above on a 232 | medium customarily used for software interchange. 233 | 234 | If distribution of object code is made by offering access to copy 235 | from a designated place, then offering equivalent access to copy the 236 | source code from the same place satisfies the requirement to 237 | distribute the source code, even though third parties are not 238 | compelled to copy the source along with the object code. 239 | 240 | 5. A program that contains no derivative of any portion of the 241 | Library, but is designed to work with the Library by being compiled or 242 | linked with it, is called a "work that uses the Library". Such a 243 | work, in isolation, is not a derivative work of the Library, and 244 | therefore falls outside the scope of this License. 245 | 246 | However, linking a "work that uses the Library" with the Library 247 | creates an executable that is a derivative of the Library (because it 248 | contains portions of the Library), rather than a "work that uses the 249 | library". The executable is therefore covered by this License. 250 | Section 6 states terms for distribution of such executables. 251 | 252 | When a "work that uses the Library" uses material from a header file 253 | that is part of the Library, the object code for the work may be a 254 | derivative work of the Library even though the source code is not. 255 | Whether this is true is especially significant if the work can be 256 | linked without the Library, or if the work is itself a library. The 257 | threshold for this to be true is not precisely defined by law. 258 | 259 | If such an object file uses only numerical parameters, data 260 | structure layouts and accessors, and small macros and small inline 261 | functions (ten lines or less in length), then the use of the object 262 | file is unrestricted, regardless of whether it is legally a derivative 263 | work. (Executables containing this object code plus portions of the 264 | Library will still fall under Section 6.) 265 | 266 | Otherwise, if the work is a derivative of the Library, you may 267 | distribute the object code for the work under the terms of Section 6. 268 | Any executables containing that work also fall under Section 6, 269 | whether or not they are linked directly with the Library itself. 270 | 271 | 6. As an exception to the Sections above, you may also combine or 272 | link a "work that uses the Library" with the Library to produce a 273 | work containing portions of the Library, and distribute that work 274 | under terms of your choice, provided that the terms permit 275 | modification of the work for the customer's own use and reverse 276 | engineering for debugging such modifications. 277 | 278 | You must give prominent notice with each copy of the work that the 279 | Library is used in it and that the Library and its use are covered by 280 | this License. You must supply a copy of this License. If the work 281 | during execution displays copyright notices, you must include the 282 | copyright notice for the Library among them, as well as a reference 283 | directing the user to the copy of this License. Also, you must do one 284 | of these things: 285 | 286 | a) Accompany the work with the complete corresponding 287 | machine-readable source code for the Library including whatever 288 | changes were used in the work (which must be distributed under 289 | Sections 1 and 2 above); and, if the work is an executable linked 290 | with the Library, with the complete machine-readable "work that 291 | uses the Library", as object code and/or source code, so that the 292 | user can modify the Library and then relink to produce a modified 293 | executable containing the modified Library. (It is understood 294 | that the user who changes the contents of definitions files in the 295 | Library will not necessarily be able to recompile the application 296 | to use the modified definitions.) 297 | 298 | b) Use a suitable shared library mechanism for linking with the 299 | Library. A suitable mechanism is one that (1) uses at run time a 300 | copy of the library already present on the user's computer system, 301 | rather than copying library functions into the executable, and (2) 302 | will operate properly with a modified version of the library, if 303 | the user installs one, as long as the modified version is 304 | interface-compatible with the version that the work was made with. 305 | 306 | c) Accompany the work with a written offer, valid for at 307 | least three years, to give the same user the materials 308 | specified in Subsection 6a, above, for a charge no more 309 | than the cost of performing this distribution. 310 | 311 | d) If distribution of the work is made by offering access to copy 312 | from a designated place, offer equivalent access to copy the above 313 | specified materials from the same place. 314 | 315 | e) Verify that the user has already received a copy of these 316 | materials or that you have already sent this user a copy. 317 | 318 | For an executable, the required form of the "work that uses the 319 | Library" must include any data and utility programs needed for 320 | reproducing the executable from it. However, as a special exception, 321 | the materials to be distributed need not include anything that is 322 | normally distributed (in either source or binary form) with the major 323 | components (compiler, kernel, and so on) of the operating system on 324 | which the executable runs, unless that component itself accompanies 325 | the executable. 326 | 327 | It may happen that this requirement contradicts the license 328 | restrictions of other proprietary libraries that do not normally 329 | accompany the operating system. Such a contradiction means you cannot 330 | use both them and the Library together in an executable that you 331 | distribute. 332 | 333 | 7. You may place library facilities that are a work based on the 334 | Library side-by-side in a single library together with other library 335 | facilities not covered by this License, and distribute such a combined 336 | library, provided that the separate distribution of the work based on 337 | the Library and of the other library facilities is otherwise 338 | permitted, and provided that you do these two things: 339 | 340 | a) Accompany the combined library with a copy of the same work 341 | based on the Library, uncombined with any other library 342 | facilities. This must be distributed under the terms of the 343 | Sections above. 344 | 345 | b) Give prominent notice with the combined library of the fact 346 | that part of it is a work based on the Library, and explaining 347 | where to find the accompanying uncombined form of the same work. 348 | 349 | 8. You may not copy, modify, sublicense, link with, or distribute 350 | the Library except as expressly provided under this License. Any 351 | attempt otherwise to copy, modify, sublicense, link with, or 352 | distribute the Library is void, and will automatically terminate your 353 | rights under this License. However, parties who have received copies, 354 | or rights, from you under this License will not have their licenses 355 | terminated so long as such parties remain in full compliance. 356 | 357 | 9. You are not required to accept this License, since you have not 358 | signed it. However, nothing else grants you permission to modify or 359 | distribute the Library or its derivative works. These actions are 360 | prohibited by law if you do not accept this License. Therefore, by 361 | modifying or distributing the Library (or any work based on the 362 | Library), you indicate your acceptance of this License to do so, and 363 | all its terms and conditions for copying, distributing or modifying 364 | the Library or works based on it. 365 | 366 | 10. Each time you redistribute the Library (or any work based on the 367 | Library), the recipient automatically receives a license from the 368 | original licensor to copy, distribute, link with or modify the Library 369 | subject to these terms and conditions. You may not impose any further 370 | restrictions on the recipients' exercise of the rights granted herein. 371 | You are not responsible for enforcing compliance by third parties with 372 | this License. 373 | 374 | 11. If, as a consequence of a court judgment or allegation of patent 375 | infringement or for any other reason (not limited to patent issues), 376 | conditions are imposed on you (whether by court order, agreement or 377 | otherwise) that contradict the conditions of this License, they do not 378 | excuse you from the conditions of this License. If you cannot 379 | distribute so as to satisfy simultaneously your obligations under this 380 | License and any other pertinent obligations, then as a consequence you 381 | may not distribute the Library at all. For example, if a patent 382 | license would not permit royalty-free redistribution of the Library by 383 | all those who receive copies directly or indirectly through you, then 384 | the only way you could satisfy both it and this License would be to 385 | refrain entirely from distribution of the Library. 386 | 387 | If any portion of this section is held invalid or unenforceable under any 388 | particular circumstance, the balance of the section is intended to apply, 389 | and the section as a whole is intended to apply in other circumstances. 390 | 391 | It is not the purpose of this section to induce you to infringe any 392 | patents or other property right claims or to contest validity of any 393 | such claims; this section has the sole purpose of protecting the 394 | integrity of the free software distribution system which is 395 | implemented by public license practices. Many people have made 396 | generous contributions to the wide range of software distributed 397 | through that system in reliance on consistent application of that 398 | system; it is up to the author/donor to decide if he or she is willing 399 | to distribute software through any other system and a licensee cannot 400 | impose that choice. 401 | 402 | This section is intended to make thoroughly clear what is believed to 403 | be a consequence of the rest of this License. 404 | 405 | 12. If the distribution and/or use of the Library is restricted in 406 | certain countries either by patents or by copyrighted interfaces, the 407 | original copyright holder who places the Library under this License may add 408 | an explicit geographical distribution limitation excluding those countries, 409 | so that distribution is permitted only in or among countries not thus 410 | excluded. In such case, this License incorporates the limitation as if 411 | written in the body of this License. 412 | 413 | 13. The Free Software Foundation may publish revised and/or new 414 | versions of the Lesser General Public License from time to time. 415 | Such new versions will be similar in spirit to the present version, 416 | but may differ in detail to address new problems or concerns. 417 | 418 | Each version is given a distinguishing version number. If the Library 419 | specifies a version number of this License which applies to it and 420 | "any later version", you have the option of following the terms and 421 | conditions either of that version or of any later version published by 422 | the Free Software Foundation. If the Library does not specify a 423 | license version number, you may choose any version ever published by 424 | the Free Software Foundation. 425 | 426 | 14. If you wish to incorporate parts of the Library into other free 427 | programs whose distribution conditions are incompatible with these, 428 | write to the author to ask for permission. For software which is 429 | copyrighted by the Free Software Foundation, write to the Free 430 | Software Foundation; we sometimes make exceptions for this. Our 431 | decision will be guided by the two goals of preserving the free status 432 | of all derivatives of our free software and of promoting the sharing 433 | and reuse of software generally. 434 | 435 | NO WARRANTY 436 | 437 | 15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO 438 | WARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW. 439 | EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR 440 | OTHER PARTIES PROVIDE THE LIBRARY "AS IS" WITHOUT WARRANTY OF ANY 441 | KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE 442 | IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 443 | PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE 444 | LIBRARY IS WITH YOU. SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME 445 | THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION. 446 | 447 | 16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN 448 | WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY 449 | AND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU 450 | FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR 451 | CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE 452 | LIBRARY (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING 453 | RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A 454 | FAILURE OF THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF 455 | SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH 456 | DAMAGES. 457 | 458 | END OF TERMS AND CONDITIONS 459 | 460 | How to Apply These Terms to Your New Libraries 461 | 462 | If you develop a new library, and you want it to be of the greatest 463 | possible use to the public, we recommend making it free software that 464 | everyone can redistribute and change. You can do so by permitting 465 | redistribution under these terms (or, alternatively, under the terms of the 466 | ordinary General Public License). 467 | 468 | To apply these terms, attach the following notices to the library. It is 469 | safest to attach them to the start of each source file to most effectively 470 | convey the exclusion of warranty; and each file should have at least the 471 | "copyright" line and a pointer to where the full notice is found. 472 | 473 | 474 | Copyright (C) 475 | 476 | This library is free software; you can redistribute it and/or 477 | modify it under the terms of the GNU Lesser General Public 478 | License as published by the Free Software Foundation; either 479 | version 2.1 of the License, or (at your option) any later version. 480 | 481 | This library is distributed in the hope that it will be useful, 482 | but WITHOUT ANY WARRANTY; without even the implied warranty of 483 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 484 | Lesser General Public License for more details. 485 | 486 | You should have received a copy of the GNU Lesser General Public 487 | License along with this library; if not, write to the Free Software 488 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA 489 | 490 | Also add information on how to contact you by electronic and paper mail. 491 | 492 | You should also get your employer (if you work as a programmer) or your 493 | school, if any, to sign a "copyright disclaimer" for the library, if 494 | necessary. Here is a sample; alter the names: 495 | 496 | Yoyodyne, Inc., hereby disclaims all copyright interest in the 497 | library `Frob' (a library for tweaking knobs) written by James Random Hacker. 498 | 499 | , 1 April 1990 500 | Ty Coon, President of Vice 501 | 502 | That's all there is to it! 503 | -------------------------------------------------------------------------------- /Makefile.am: -------------------------------------------------------------------------------- 1 | ACLOCAL_AMFLAGS = -I m4 2 | 3 | MEDIALIB_CPPFLAGS = $(AM_CPPFLAGS) -I$(top_srcdir)/include -I$(top_srcdir)/src 4 | 5 | libvlcppdir = $(includedir)/vlcpp 6 | 7 | libvlcpp_HEADERS = \ 8 | vlcpp/common.hpp \ 9 | vlcpp/Equalizer.hpp \ 10 | vlcpp/EventManager.hpp \ 11 | vlcpp/Instance.hpp \ 12 | vlcpp/Internal.hpp \ 13 | vlcpp/MediaDiscoverer.hpp \ 14 | vlcpp/Media.hpp \ 15 | vlcpp/MediaLibrary.hpp \ 16 | vlcpp/MediaList.hpp \ 17 | vlcpp/MediaListPlayer.hpp \ 18 | vlcpp/MediaPlayer.hpp \ 19 | vlcpp/Dialog.hpp \ 20 | vlcpp/RendererDiscoverer.hpp \ 21 | vlcpp/Picture.hpp \ 22 | vlcpp/structures.hpp \ 23 | vlcpp/vlc.hpp \ 24 | $(NULL) 25 | 26 | pkgconfigdir = $(libdir)/pkgconfig 27 | pkgconfig_DATA = libvlcpp.pc 28 | 29 | if HAVE_EXAMPLES 30 | noinst_PROGRAMS = helloworld tests imem discovery 31 | 32 | AM_CPPFLAGS = $(vlc_CFLAGS) -Wextra -Wall 33 | 34 | if HAVE_WERROR 35 | # This is meant to make our builds fail if a deprecated method is present 36 | AM_CPPFLAGS += -Werror 37 | endif 38 | 39 | helloworld_SOURCES = examples/helloworld/main.cpp 40 | helloworld_LDADD = $(vlc_LIBS) 41 | imem_SOURCES = examples/imem/imem.cpp 42 | imem_LDADD = $(vlc_LIBS) 43 | tests_SOURCES = test/main.cpp 44 | tests_LDADD = $(vlc_LIBS) 45 | discovery_SOURCES = examples/renderers/discovery.cpp 46 | discovery_LDADD = $(vlc_LIBS) 47 | 48 | endif 49 | -------------------------------------------------------------------------------- /NEWS: -------------------------------------------------------------------------------- 1 | Changes between 0.1.x and 0.2.0-git: 2 | ------------------------------------ 3 | 4 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # libvlcpp 2 | 3 | [![Join the chat at https://discord.gg/3h3K3JF](https://img.shields.io/discord/716939396464508958?label=discord)](https://discord.gg/3h3K3JF) 4 | 5 | [libvlcpp](https://code.videolan.org/videolan/libvlcpp) is a header-only, C++ bindings for the libvlc crossplatform multimedia API. It is an official binding over the VideoLAN libvlc library and can be used on many platforms. 6 | 7 | ## Documentation 8 | 9 | Since libvlcpp is a close wrapper over libvlc, your documentation needs will be best served by either checking the libvlcpp source code, or the [libvlc documentation](https://www.videolan.org/developers/vlc/doc/doxygen/html/group__libvlc.html). 10 | 11 | ## Issues 12 | 13 | libvlcpp tickets are located on our [GitLab](https://code.videolan.org/videolan/libvlcpp/-/issues). 14 | 15 | ## Contribution 16 | 17 | Contribution are always welcome! 18 | 19 | Feel free to open a merge request on our [GitLab](https://code.videolan.org/videolan/libvlcpp/-/merge_requests). 20 | 21 | ## Examples 22 | 23 | For usage examples, head over to the examples folder where you will find several code samples, such as [helloworld](examples/helloworld/main.cpp) and more. 24 | 25 | ## Used by 26 | 27 | libvlcpp is being used and tested extensively in various projects, such as the VideoLAN [medialibrary](https://code.videolan.org/videolan/medialibrary), the previous [VLC for UWP](https://code.videolan.org/videolan/vlc-winrt) app and more. -------------------------------------------------------------------------------- /bootstrap: -------------------------------------------------------------------------------- 1 | #! /bin/sh 2 | set -x 3 | 4 | cd "$(dirname "$0")" 5 | 6 | autoreconf -fis 7 | -------------------------------------------------------------------------------- /configure.ac: -------------------------------------------------------------------------------- 1 | m4_define([VLCPP_MAJOR], [0]) 2 | m4_define([VLCPP_MINOR], [1]) 3 | m4_define([VLCPP_MICRO], [0]) 4 | 5 | AC_COPYRIGHT([Copyright 2014-2016 VideoLAN - VideoLabs]) 6 | 7 | AC_INIT([libvlcpp], [VLCPP_MAJOR.VLCPP_MINOR.VLCPP_MICRO]) 8 | 9 | AM_INIT_AUTOMAKE([foreign subdir-objects]) 10 | m4_ifdef([AM_SILENT_RULES], [ 11 | AM_SILENT_RULES([yes]) 12 | ]) 13 | 14 | AC_CONFIG_MACRO_DIR([m4]) 15 | AC_PROG_CXX 16 | AX_CXX_COMPILE_STDCXX_11([noext]) 17 | 18 | AC_ARG_ENABLE(examples, AS_HELP_STRING([--enable-examples], [build examples programs])) 19 | AM_CONDITIONAL([HAVE_EXAMPLES], [test "${enable_examples}" = "yes"]) 20 | AS_IF([test "${enable_examples}" = "yes"], [PKG_CHECK_MODULES(vlc, libvlc)]) 21 | 22 | AC_ARG_ENABLE(werror, AS_HELP_STRING([--enable-werror], [build examples with -Werror])) 23 | AM_CONDITIONAL([HAVE_WERROR], [test "${enable_werror}" = "yes"]) 24 | 25 | AC_CONFIG_FILES([ 26 | Makefile 27 | libvlcpp.pc 28 | ]) 29 | 30 | AC_OUTPUT 31 | -------------------------------------------------------------------------------- /examples/helloworld/main.cpp: -------------------------------------------------------------------------------- 1 | #include "vlcpp/vlc.hpp" 2 | #include 3 | #include 4 | 5 | int main(int ac, char** av) 6 | { 7 | if (ac < 2) 8 | { 9 | std::cerr << "usage: " << av[0] << " " << std::endl; 10 | return 1; 11 | } 12 | auto instance = VLC::Instance(0, nullptr); 13 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 14 | auto media = VLC::Media(av[1], VLC::Media::FromPath); 15 | auto mp = VLC::MediaPlayer(instance, media); 16 | #else 17 | auto media = VLC::Media(instance, av[1], VLC::Media::FromPath); 18 | auto mp = VLC::MediaPlayer(media); 19 | #endif 20 | mp.play(); 21 | std::this_thread::sleep_for( std::chrono::seconds( 10 ) ); 22 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 23 | mp.stopAsync(); 24 | #else 25 | mp.stop(); 26 | #endif 27 | } 28 | -------------------------------------------------------------------------------- /examples/imem/imem.cpp: -------------------------------------------------------------------------------- 1 | #include "vlcpp/vlc.hpp" 2 | #include 3 | #include 4 | #include 5 | #include 6 | 7 | struct ImemOpaque 8 | { 9 | FILE* file; 10 | std::string path; 11 | }; 12 | 13 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 14 | int main(int ac, char**av) 15 | { 16 | if (ac < 3) 17 | { 18 | std::cerr << "usage: " << av[0] << " " << std::endl; 19 | return 1; 20 | } 21 | auto instance = VLC::Instance(0, nullptr); 22 | auto dummyOpaque = new ImemOpaque{}; 23 | dummyOpaque->path = av[1]; 24 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 25 | auto imemMedia = VLC::Media( 26 | #else 27 | auto imemMedia = VLC::Media( instance, 28 | #endif 29 | // Open 30 | [dummyOpaque]( void*, void** opaque, uint64_t* p_size ) -> int { 31 | dummyOpaque->file = fopen( dummyOpaque->path.c_str(), "rb" ); 32 | *opaque = dummyOpaque; 33 | fseek(dummyOpaque->file, 0, SEEK_END); 34 | *p_size = ftell( dummyOpaque->file ); 35 | rewind( dummyOpaque->file ); 36 | return 0; 37 | }, 38 | // Read: 39 | []( void* opaque, unsigned char* buf, size_t size ) -> ssize_t { 40 | auto context = reinterpret_cast( opaque ); 41 | auto res = fread( buf, 1, size, context->file ); 42 | if ( res == 0 ) 43 | return feof( context->file ) != 0 ? 0 : -1; 44 | return res; 45 | }, 46 | []( void* opaque, uint64_t seek ) -> int { 47 | auto context = reinterpret_cast( opaque ); 48 | if ( fseek( context->file, seek, SEEK_SET ) < 0 ) 49 | return -1; 50 | return 0; 51 | }, 52 | []( void* opaque ) { 53 | auto context = reinterpret_cast( opaque ); 54 | fclose( context->file ); 55 | }); 56 | 57 | auto opaque2 = new ImemOpaque{}; 58 | opaque2->file = fopen( av[2], "rb" ); 59 | 60 | // Do not use a user defined opaque 61 | // This is mostly meant to test that our nullptr overload are functionnal 62 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 63 | auto imemMedia2 = VLC::Media( 64 | #else 65 | auto imemMedia2 = VLC::Media( instance, 66 | #endif 67 | nullptr, 68 | [opaque2]( void* opaque, unsigned char* buf, size_t size ) -> ssize_t { 69 | assert( opaque == nullptr ); 70 | auto res = fread( buf, 1, size, opaque2->file ); 71 | if ( res == 0 ) 72 | return feof( opaque2->file ) != 0 ? 0 : -1; 73 | return res; 74 | }, 75 | [opaque2]( void*, uint64_t offset ) { 76 | if ( fseek( opaque2->file, offset, SEEK_CUR ) < -1 ) 77 | return -1; 78 | return 0; 79 | }, nullptr ); 80 | 81 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 82 | auto mp = VLC::MediaPlayer( instance, imemMedia ); 83 | mp.play(); 84 | 85 | auto mp2 = VLC::MediaPlayer( instance, imemMedia2 ); 86 | mp2.play(); 87 | #else 88 | auto mp = VLC::MediaPlayer( imemMedia ); 89 | mp.play(); 90 | 91 | auto mp2 = VLC::MediaPlayer( imemMedia2 ); 92 | mp2.play(); 93 | #endif 94 | 95 | std::this_thread::sleep_for( std::chrono::seconds( 10 ) ); 96 | 97 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 98 | mp.stopAsync(); 99 | mp2.stopAsync(); 100 | #else 101 | mp.stop(); 102 | mp2.stop(); 103 | #endif 104 | 105 | delete dummyOpaque; 106 | fclose(opaque2->file); 107 | delete opaque2; 108 | } 109 | #else 110 | int main(){} 111 | #endif 112 | -------------------------------------------------------------------------------- /examples/renderers/discovery.cpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | * discovery.cpp: Test vlcpp renderer discoverer binding 3 | ***************************************************************************** 4 | * Copyright © 2015-2018 libvlcpp authors & VideoLAN 5 | * 6 | * Authors: Hugo Beauzée-Luyssen 7 | * 8 | * This program is free software; you can redistribute it and/or modify 9 | * it under the terms of the GNU Lesser General Public License as published by 10 | * the Free Software Foundation; either version 2.1 of the License, or 11 | * (at your option) any later version. 12 | * 13 | * This program is distributed in the hope that it will be useful, 14 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 | * GNU Lesser General Public License for more details. 17 | * 18 | * You should have received a copy of the GNU Lesser General Public License 19 | * along with this program; if not, write to the Free Software 20 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. 21 | *****************************************************************************/ 22 | 23 | #include "vlcpp/vlc.hpp" 24 | 25 | #include 26 | #include 27 | 28 | int main() 29 | { 30 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 31 | VLC::Instance inst( 0, nullptr ); 32 | VLC::RendererDiscoverer disc( inst, "microdns" ); 33 | 34 | auto& em = disc.eventManager(); 35 | em.onItemAdded( []( const VLC::RendererDiscoverer::Item& item ) { 36 | std::cout << "New item discovered: " << item.name() << '\n' 37 | << "\tType: " << item.type() << '\n'; 38 | if ( item.canRenderVideo() ) 39 | std::cout << "\tCan render video\n"; 40 | if ( item.canRenderAudio() ) 41 | std::cout << "\tCan render audio\n"; 42 | std::cout << std::endl; 43 | }); 44 | if ( disc.start() == false ) 45 | abort(); 46 | std::this_thread::sleep_for( std::chrono::seconds{ 10 } ); 47 | #else 48 | std::cerr << "Renderer discovery isn't available before VLC 3." << std::endl; 49 | return 1; 50 | #endif 51 | } 52 | -------------------------------------------------------------------------------- /libvlcpp.pc.in: -------------------------------------------------------------------------------- 1 | prefix=@prefix@ 2 | exec_prefix=@exec_prefix@ 3 | libdir=${prefix}/lib 4 | includedir=${prefix}/include 5 | 6 | Name: libvlcpp 7 | Description: libvlc C++ bindings 8 | Version: @PACKAGE_VERSION@ 9 | Cflags: -I${includedir} 10 | Requires: libvlc >= 3 11 | -------------------------------------------------------------------------------- /m4/stdcxx_11.m4: -------------------------------------------------------------------------------- 1 | # ============================================================================ 2 | # http://www.gnu.org/software/autoconf-archive/ax_cxx_compile_stdcxx_11.html 3 | # ============================================================================ 4 | # 5 | # SYNOPSIS 6 | # 7 | # AX_CXX_COMPILE_STDCXX_11([ext|noext],[mandatory|optional]) 8 | # 9 | # DESCRIPTION 10 | # 11 | # Check for baseline language coverage in the compiler for the C++11 12 | # standard; if necessary, add switches to CXXFLAGS to enable support. 13 | # 14 | # The first argument, if specified, indicates whether you insist on an 15 | # extended mode (e.g. -std=gnu++11) or a strict conformance mode (e.g. 16 | # -std=c++11). If neither is specified, you get whatever works, with 17 | # preference for an extended mode. 18 | # 19 | # The second argument, if specified 'mandatory' or if left unspecified, 20 | # indicates that baseline C++11 support is required and that the macro 21 | # should error out if no mode with that support is found. If specified 22 | # 'optional', then configuration proceeds regardless, after defining 23 | # HAVE_CXX11 if and only if a supporting mode is found. 24 | # 25 | # LICENSE 26 | # 27 | # Copyright (c) 2008 Benjamin Kosnik 28 | # Copyright (c) 2012 Zack Weinberg 29 | # Copyright (c) 2013 Roy Stogner 30 | # Copyright (c) 2014 Alexey Sokolov 31 | # Copyright (c) 2014, 2015 Google Inc. 32 | # Copyright (c) 2015 VLC authors and VideoLAN 33 | # 34 | # Copying and distribution of this file, with or without modification, are 35 | # permitted in any medium without royalty provided the copyright notice 36 | # and this notice are preserved. This file is offered as-is, without any 37 | # warranty. 38 | 39 | #serial 7 40 | 41 | m4_define([_AX_CXX_COMPILE_STDCXX_11_testbody], [[ 42 | template 43 | struct check 44 | { 45 | static_assert(sizeof(int) <= sizeof(T), "not big enough"); 46 | }; 47 | 48 | struct Base { 49 | virtual void f() {} 50 | }; 51 | struct Child : public Base { 52 | virtual void f() override {} 53 | }; 54 | 55 | typedef check> right_angle_brackets; 56 | 57 | int a; 58 | decltype(a) b; 59 | 60 | typedef check check_type; 61 | check_type c; 62 | check_type&& cr = static_cast(c); 63 | 64 | auto d = a; 65 | auto l = [](){}; 66 | 67 | // http://stackoverflow.com/questions/13728184/template-aliases-and-sfinae 68 | // Clang 3.1 fails with headers of libstd++ 4.8.3 when using std::function because of this 69 | namespace test_template_alias_sfinae { 70 | struct foo {}; 71 | 72 | template 73 | using member = typename T::member_type; 74 | 75 | template 76 | void func(...) {} 77 | 78 | template 79 | void func(member*) {} 80 | 81 | void test() { 82 | func(0); 83 | } 84 | } 85 | 86 | #include 87 | constexpr uint64_t constantname = UINT64_C(0x100000000); 88 | ]]) 89 | 90 | AC_DEFUN([AX_CXX_COMPILE_STDCXX_11], [dnl 91 | m4_if([$1], [], [], 92 | [$1], [ext], [], 93 | [$1], [noext], [], 94 | [m4_fatal([invalid argument `$1' to AX_CXX_COMPILE_STDCXX_11])])dnl 95 | m4_if([$2], [], [ax_cxx_compile_cxx11_required=true], 96 | [$2], [mandatory], [ax_cxx_compile_cxx11_required=true], 97 | [$2], [optional], [ax_cxx_compile_cxx11_required=false], 98 | [m4_fatal([invalid second argument `$2' to AX_CXX_COMPILE_STDCXX_11])]) 99 | AC_LANG_PUSH([C++])dnl 100 | ac_success=no 101 | AC_CACHE_CHECK(whether $CXX supports C++11 features by default, 102 | ax_cv_cxx_compile_cxx11, 103 | [AC_COMPILE_IFELSE([AC_LANG_SOURCE([_AX_CXX_COMPILE_STDCXX_11_testbody])], 104 | [ax_cv_cxx_compile_cxx11=yes], 105 | [ax_cv_cxx_compile_cxx11=no])]) 106 | if test x$ax_cv_cxx_compile_cxx11 = xyes; then 107 | ac_success=yes 108 | fi 109 | 110 | m4_if([$1], [noext], [], [dnl 111 | if test x$ac_success = xno; then 112 | for switch in -std=gnu++11 -std=gnu++0x; do 113 | cachevar=AS_TR_SH([ax_cv_cxx_compile_cxx11_$switch]) 114 | AC_CACHE_CHECK(whether $CXX supports C++11 features with $switch, 115 | $cachevar, 116 | [ac_save_CXXFLAGS="$CXXFLAGS" 117 | CXXFLAGS="$CXXFLAGS $switch" 118 | AC_COMPILE_IFELSE([AC_LANG_SOURCE([_AX_CXX_COMPILE_STDCXX_11_testbody])], 119 | [eval $cachevar=yes], 120 | [eval $cachevar=no]) 121 | CXXFLAGS="$ac_save_CXXFLAGS"]) 122 | if eval test x\$$cachevar = xyes; then 123 | CXXFLAGS="$CXXFLAGS $switch" 124 | ac_success=yes 125 | break 126 | fi 127 | done 128 | fi]) 129 | 130 | m4_if([$1], [ext], [], [dnl 131 | if test x$ac_success = xno; then 132 | for switch in -std=c++11 -std=c++0x; do 133 | cachevar=AS_TR_SH([ax_cv_cxx_compile_cxx11_$switch]) 134 | AC_CACHE_CHECK(whether $CXX supports C++11 features with $switch, 135 | $cachevar, 136 | [ac_save_CXXFLAGS="$CXXFLAGS" 137 | CXXFLAGS="$CXXFLAGS $switch" 138 | AC_COMPILE_IFELSE([AC_LANG_SOURCE([_AX_CXX_COMPILE_STDCXX_11_testbody])], 139 | [eval $cachevar=yes], 140 | [eval $cachevar=no]) 141 | CXXFLAGS="$ac_save_CXXFLAGS"]) 142 | if eval test x\$$cachevar = xyes; then 143 | CXXFLAGS="$CXXFLAGS $switch" 144 | ac_success=yes 145 | break 146 | fi 147 | done 148 | fi]) 149 | AC_LANG_POP([C++]) 150 | if test x$ax_cxx_compile_cxx11_required = xtrue; then 151 | if test x$ac_success = xno; then 152 | AC_MSG_ERROR([*** A compiler with support for C++11 language features is required.]) 153 | fi 154 | else 155 | if test x$ac_success = xno; then 156 | HAVE_CXX11=0 157 | AC_MSG_NOTICE([No compiler with C++11 support was found]) 158 | else 159 | HAVE_CXX11=1 160 | AC_DEFINE(HAVE_CXX11,1, 161 | [define if the compiler supports basic C++11 syntax]) 162 | fi 163 | 164 | AC_SUBST(HAVE_CXX11) 165 | fi 166 | ]) 167 | -------------------------------------------------------------------------------- /test/main.cpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | * main.cpp: Simple test program 3 | ***************************************************************************** 4 | * Copyright © 2015 libvlcpp authors & VideoLAN 5 | * 6 | * Authors: Hugo Beauzée-Luyssen 7 | * 8 | * This program is free software; you can redistribute it and/or modify 9 | * it under the terms of the GNU Lesser General Public License as published by 10 | * the Free Software Foundation; either version 2.1 of the License, or 11 | * (at your option) any later version. 12 | * 13 | * This program is distributed in the hope that it will be useful, 14 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 | * GNU Lesser General Public License for more details. 17 | * 18 | * You should have received a copy of the GNU Lesser General Public License 19 | * along with this program; if not, write to the Free Software 20 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. 21 | *****************************************************************************/ 22 | 23 | #include "vlcpp/vlc.hpp" 24 | 25 | #include 26 | #include 27 | #include 28 | 29 | int main(int ac, char** av) 30 | { 31 | if (ac < 2) 32 | { 33 | std::cerr << "usage: " << av[0] << " " << std::endl; 34 | return 1; 35 | } 36 | const char* vlcArgs = "-vv"; 37 | auto imgBuffer = malloc(480 * 320 * 4); 38 | std::unique_ptr imgBufferPtr{ 39 | static_cast( imgBuffer ), &free }; 40 | auto instance = VLC::Instance(1, &vlcArgs); 41 | 42 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 43 | auto sds = instance.mediaDiscoverers( VLC::MediaDiscoverer::Category::Lan ); 44 | for ( const auto& sd : sds ) 45 | std::cout << "Found SD: " << sd.name() << "(" << sd.longName() << ")" << std::endl; 46 | #endif 47 | 48 | #if LIBVLC_VERSION_INT < LIBVLC_VERSION(4, 0, 0, 0) 49 | instance.setExitHandler([] { 50 | std::cout << "Libvlc is exiting" << std::endl; 51 | }); 52 | #endif 53 | 54 | instance.logSet([](int lvl, const libvlc_log_t*, std::string message ) { 55 | std::cout << "Hooked VLC log: " << lvl << ' ' << message << std::endl; 56 | }); 57 | 58 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 59 | auto media = VLC::Media(av[1], VLC::Media::FromPath); 60 | auto mp = VLC::MediaPlayer(instance, media); 61 | #else 62 | auto media = VLC::Media(instance, av[1], VLC::Media::FromPath); 63 | auto mp = VLC::MediaPlayer(media); 64 | #endif 65 | auto eventManager = mp.eventManager(); 66 | eventManager.onPlaying([&media]() { 67 | std::cout << media.mrl() << " is playing" << std::endl; 68 | }); 69 | 70 | mp.setVideoCallbacks([imgBuffer](void** pBuffer) -> void* { 71 | std::cout << "Lock" << std::endl; 72 | *pBuffer = imgBuffer; 73 | return nullptr; 74 | }, [](void*, void*const*) { 75 | std::cout << "unlock" << std::endl; 76 | }, nullptr); 77 | 78 | mp.setVideoFormatCallbacks([](char* chroma, uint32_t* width, uint32_t* height, uint32_t* pitch, uint32_t* lines) -> int { 79 | memcpy(chroma, "RV32", 4); 80 | *width = 480; 81 | *height = 320; 82 | *pitch = *width * 4; 83 | *lines = 320; 84 | return 1; 85 | }, nullptr); 86 | 87 | 88 | mp.play(); 89 | 90 | bool expected = true; 91 | 92 | mp.setAudioCallbacks([](const void*, uint32_t count, int64_t pts) { 93 | std::cout << "Playing " << count << " samples at pts " << pts << std::endl; 94 | }, nullptr, nullptr, nullptr, nullptr 95 | ); 96 | 97 | auto handler = mp.eventManager().onPositionChanged([&expected](float pos) { 98 | std::cout << "position changed " << pos << std::endl; 99 | assert(expected); 100 | }); 101 | std::this_thread::sleep_for( std::chrono::seconds( 2 ) ); 102 | handler->unregister(); 103 | // handler must be considered a dangling reference from now on. 104 | // We might want to fix this, but is it worth the cost of a shared/weak_pointer? 105 | expected = false; 106 | 107 | std::this_thread::sleep_for( std::chrono::seconds( 2 ) ); 108 | 109 | expected = true; 110 | auto l = [&expected] (float){ 111 | std::cout << "Lambda called" << std::endl; 112 | assert(expected); 113 | }; 114 | auto lFunc = std::function{ l }; 115 | auto h1 = mp.eventManager().onTimeChanged(lFunc); 116 | auto h2 = mp.eventManager().onPositionChanged(lFunc); 117 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 118 | mp.eventManager().onTitleSelectionChanged( 119 | [](const VLC::TitleDescription& t, int idx ) { 120 | std::cout << "New title selected: " << t.name() << " at index " << idx << std::endl; 121 | }); 122 | #endif 123 | 124 | std::this_thread::sleep_for( std::chrono::seconds( 2 ) ); 125 | 126 | // Unregistering multiple events at once. 127 | // h1 and h2 are now invalid. 128 | mp.eventManager().unregister(h1, h2); 129 | expected = false; 130 | 131 | std::this_thread::sleep_for( std::chrono::milliseconds(500) ); 132 | 133 | // Using scopped event manager to automatically unregister events 134 | { 135 | expected = true; 136 | // This is a copy. Assigning to a reference wouldn't clear the registered events 137 | auto em = mp.eventManager(); 138 | em.onPositionChanged([&expected](float) { 139 | assert(expected); 140 | }); 141 | std::this_thread::sleep_for( std::chrono::seconds(1) ); 142 | } 143 | // From here, the lambda declared in the scope isn't registered anymore 144 | expected = false; 145 | 146 | std::this_thread::sleep_for( std::chrono::milliseconds(500) ); 147 | 148 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 149 | auto tracks = mp.tracks( VLC::MediaTrack::Type::Video, false ); 150 | std::cout << "Got " << tracks.size() << " tracks" << std::endl; 151 | mp.selectTracks( VLC::MediaTrack::Type::Video, tracks ); 152 | std::this_thread::sleep_for( std::chrono::milliseconds(1000) ); 153 | #endif 154 | 155 | // Showing that copying an object shares the associated eventmanager 156 | auto mp2 = mp; 157 | expected = true; 158 | auto h3 = mp2.eventManager().onStopped([&expected]() { 159 | std::cout << "MediaPlayer stopped" << std::endl; 160 | assert(expected); 161 | // expect a single call since both media player share the same event manager 162 | expected = false; 163 | }); 164 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 165 | mp.stopAsync(); 166 | #else 167 | mp.stop(); 168 | #endif 169 | // Unregister the RegisteredEvent from the other MP's event manager. 170 | // It will be unregistered from both, and when the object gets destroyed 171 | // by leaving the scope, it won't be unregistered from mp2's eventManager. 172 | // If it did, libvlc would assert as the event has been unregistered already. 173 | mp.eventManager().unregister(h3); 174 | 175 | // List audio filters 176 | auto audioFilters = instance.audioFilterList(); 177 | for (const auto& f : audioFilters) 178 | { 179 | std::cout << f.name() << std::endl; 180 | } 181 | // Check that we don't use the old media player when releasing its event manager 182 | mp = VLC::MediaPlayer{}; 183 | } 184 | -------------------------------------------------------------------------------- /vlcpp/Dialog.hpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | * Dialog.hpp: libvlcpp dialog API 3 | ***************************************************************************** 4 | * Copyright © 2016 VLC authors and VideoLAN 5 | * 6 | * Authors: Bastien Penavayre 7 | * 8 | * This program is free software; you can redistribute it and/or modify it 9 | * under the terms of the GNU Lesser General Public License as published by 10 | * the Free Software Foundation; either version 2.1 of the License, or 11 | * (at your option) any later version. 12 | * 13 | * This program is distributed in the hope that it will be useful, 14 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 | * GNU Lesser General Public License for more details. 17 | * 18 | * You should have received a copy of the GNU Lesser General Public License 19 | * along with this program; if not, write to the Free Software Foundation, 20 | * Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. 21 | *****************************************************************************/ 22 | 23 | #ifndef LIBVLC_CXX_DIALOG_H 24 | #define LIBVLC_CXX_DIALOG_H 25 | 26 | #include 27 | 28 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 29 | namespace VLC 30 | { 31 | /// 32 | /// \brief The Dialog class exposes libvlc_dialog_id functionalities 33 | /// 34 | class Dialog 35 | { 36 | private: 37 | libvlc_dialog_id *m_id; 38 | 39 | Dialog() = delete; 40 | Dialog(const Dialog &) = delete; 41 | Dialog &operator=(const Dialog &) = delete; 42 | 43 | template 44 | friend struct CallbackWrapper; 45 | 46 | /** 47 | * The standard constructor. 48 | * 49 | * Used only by CallbackWrapper when setting up the callbacks. 50 | * \param id identifier for the current real dialog 51 | */ 52 | Dialog(libvlc_dialog_id *id) : m_id(id) 53 | { 54 | if (!m_id) 55 | throw std::runtime_error("The required id is NULL, Dialog inoperable"); 56 | } 57 | 58 | public: 59 | /** 60 | * Move constructor, steals the id of the instance given in parameter 61 | * \param other rvalue reference instance of this class 62 | */ 63 | Dialog(Dialog &&other) : m_id(other.m_id) 64 | { 65 | other.m_id = nullptr; 66 | } 67 | 68 | ~Dialog() 69 | { 70 | if (m_id) 71 | dismiss(); 72 | } 73 | 74 | /** 75 | * Post a login answer. 76 | * 77 | * After this call, the instance won't be valid anymore 78 | * 79 | * \param username valid non-empty string 80 | * \param password valid string 81 | * \param store if true stores the credentials 82 | * \return true if success, false otherwise 83 | */ 84 | bool postLogin(const std::string &username, const std::string &password, bool store) 85 | { 86 | if (!m_id) 87 | throw std::runtime_error("Calling method on dismissed Dialog instance"); 88 | bool ret = libvlc_dialog_post_login(m_id, username.c_str(), password.c_str(), store) == 0; 89 | m_id = nullptr; 90 | return ret; 91 | } 92 | 93 | /** 94 | * Post a question answer. 95 | * 96 | * After this call, this instance won't be valid anymore 97 | * 98 | * \see QuestionCb 99 | * \param actionIndex 1 for action1, 2 for action2 100 | * \return true on success, false otherwise 101 | */ 102 | bool postAction(int actionIndex) 103 | { 104 | if (!m_id) 105 | throw std::runtime_error("Calling method on dismissed Dialog instance"); 106 | bool ret = libvlc_dialog_post_action(m_id, actionIndex) == 0; 107 | m_id = nullptr; 108 | return ret; 109 | } 110 | 111 | /** 112 | * Dismiss a dialog. 113 | * 114 | * After this call, this instance won't be valid anymore 115 | * 116 | * \see CancelCb 117 | */ 118 | bool dismiss() 119 | { 120 | if (!m_id) 121 | throw std::runtime_error("Calling method on dismissed Dialog instance"); 122 | bool ret = libvlc_dialog_dismiss(m_id) == 0; 123 | m_id = nullptr; 124 | return ret; 125 | } 126 | }; 127 | } // namespace VLC 128 | #endif 129 | 130 | #endif /*LIBVLC_CXX_DIALOG_H*/ 131 | -------------------------------------------------------------------------------- /vlcpp/Equalizer.hpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | * Equalizer.hpp: Equalizer API 3 | ***************************************************************************** 4 | * Copyright © 2015 libvlcpp authors & VideoLAN 5 | * 6 | * Authors: Hugo Beauzée-Luyssen 7 | * 8 | * This program is free software; you can redistribute it and/or modify 9 | * it under the terms of the GNU Lesser General Public License as published by 10 | * the Free Software Foundation; either version 2.1 of the License, or 11 | * (at your option) any later version. 12 | * 13 | * This program is distributed in the hope that it will be useful, 14 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 | * GNU Lesser General Public License for more details. 17 | * 18 | * You should have received a copy of the GNU Lesser General Public License 19 | * along with this program; if not, write to the Free Software 20 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. 21 | *****************************************************************************/ 22 | 23 | #ifndef EQUALIZER_HPP 24 | #define EQUALIZER_HPP 25 | 26 | #include "common.hpp" 27 | #include "Internal.hpp" 28 | 29 | namespace VLC 30 | { 31 | 32 | class Equalizer : public Internal 33 | { 34 | public: 35 | /** 36 | * Create a new default equalizer, with all frequency values zeroed. 37 | * 38 | * The new equalizer can subsequently be applied to a media player by invoking 39 | * libvlc_media_player_set_equalizer(). 40 | * 41 | * \throw std::runtime_error when equalizer creation fails 42 | * 43 | * \version LibVLC 2.2.0 or later 44 | */ 45 | Equalizer() 46 | : Internal{ libvlc_audio_equalizer_new(), libvlc_audio_equalizer_release } 47 | { 48 | if ( isValid() == false ) 49 | throw std::runtime_error( "Failed to create audio equalizer" ); 50 | } 51 | 52 | /** 53 | * Create a new equalizer, with initial frequency values copied from an existing 54 | * preset. 55 | * 56 | * The new equalizer can subsequently be applied to a media player by invoking 57 | * libvlc_media_player_set_equalizer(). 58 | * 59 | * \param index index of the preset, counting from zero 60 | * 61 | * \throw std::runtime_error when equalizer creation fails 62 | * 63 | * \version LibVLC 2.2.0 or later 64 | */ 65 | Equalizer( unsigned int index ) 66 | : Internal{ libvlc_audio_equalizer_new_from_preset( index ), libvlc_audio_equalizer_release } 67 | { 68 | if ( isValid() == false ) 69 | throw std::runtime_error( "Failed to create audio equalizer" ); 70 | } 71 | 72 | /** 73 | * Set a new pre-amplification value for an equalizer. 74 | * 75 | * The new equalizer settings are subsequently applied to a media player by invoking 76 | * MediaPlayer::setEqualizer(). 77 | * 78 | * The supplied amplification value will be clamped to the -20.0 to +20.0 range. 79 | * 80 | * \param preamp preamp value (-20.0 to 20.0 Hz) 81 | * \return zero on success, -1 on error 82 | * \version LibVLC 2.2.0 or later 83 | */ 84 | int setPreamp( float preamp ) 85 | { 86 | return libvlc_audio_equalizer_set_preamp( *this, preamp ); 87 | } 88 | 89 | /** 90 | * Get the current pre-amplification value from an equalizer. 91 | * 92 | * \return preamp value (Hz) 93 | * \version LibVLC 2.2.0 or later 94 | */ 95 | float preamp() 96 | { 97 | return libvlc_audio_equalizer_get_preamp( *this ); 98 | } 99 | 100 | /** 101 | * Set a new amplification value for a particular equalizer frequency band. 102 | * 103 | * The new equalizer settings are subsequently applied to a media player by invoking 104 | * MediaPlayer::setEqualizer(). 105 | * 106 | * The supplied amplification value will be clamped to the -20.0 to +20.0 range. 107 | * 108 | * \param amp amplification value (-20.0 to 20.0 Hz) 109 | * \param band index, counting from zero, of the frequency band to set 110 | * \return zero on success, -1 on error 111 | * \version LibVLC 2.2.0 or later 112 | */ 113 | int setAmp( float amp, unsigned int band ) 114 | { 115 | return libvlc_audio_equalizer_set_amp_at_index( *this, amp, band ); 116 | } 117 | 118 | /** 119 | * Get the amplification value for a particular equalizer frequency band. 120 | * 121 | * \param u_band index, counting from zero, of the frequency band to get 122 | * \return amplification value (Hz); NaN if there is no such frequency band 123 | * \version LibVLC 2.2.0 or later 124 | */ 125 | float amp( unsigned int band ) 126 | { 127 | return libvlc_audio_equalizer_get_amp_at_index( *this, band ); 128 | } 129 | 130 | /** 131 | * Get the number of equalizer presets. 132 | * 133 | * \return number of presets 134 | * \version LibVLC 2.2.0 or later 135 | */ 136 | static unsigned int presetCount() 137 | { 138 | return libvlc_audio_equalizer_get_preset_count(); 139 | } 140 | 141 | /** 142 | * Get the name of a particular equalizer preset. 143 | * 144 | * This name can be used, for example, to prepare a preset label or menu in a user 145 | * interface. 146 | * 147 | * \param index index of the preset, counting from zero 148 | * \return preset name, or empty string if there is no such preset 149 | * \version LibVLC 2.2.0 or later 150 | */ 151 | static std::string presetName( unsigned index ) 152 | { 153 | return libvlc_audio_equalizer_get_preset_name( index ); 154 | } 155 | 156 | /** 157 | * Get the number of distinct frequency bands for an equalizer. 158 | * 159 | * \return number of frequency bands 160 | * \version LibVLC 2.2.0 or later 161 | */ 162 | static unsigned int bandCount() 163 | { 164 | return libvlc_audio_equalizer_get_band_count(); 165 | } 166 | 167 | /** 168 | * Get a particular equalizer band frequency. 169 | * 170 | * This value can be used, for example, to create a label for an equalizer band control 171 | * in a user interface. 172 | * 173 | * \param index index of the band, counting from zero 174 | * \return equalizer band frequency (Hz), or -1 if there is no such band 175 | * \version LibVLC 2.2.0 or later 176 | */ 177 | static float bandFrequency( unsigned int index ) 178 | { 179 | return libvlc_audio_equalizer_get_band_frequency( index ); 180 | } 181 | }; 182 | 183 | } 184 | 185 | #endif // EQUALIZER_HPP 186 | 187 | -------------------------------------------------------------------------------- /vlcpp/Instance.hpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | * Instance.hpp: Instance API 3 | ***************************************************************************** 4 | * Copyright © 2015 libvlcpp authors & VideoLAN 5 | * 6 | * Authors: Alexey Sokolov 7 | * Hugo Beauzée-Luyssen 8 | * Bastien Penavayre 9 | * 10 | * This program is free software; you can redistribute it and/or modify 11 | * it under the terms of the GNU Lesser General Public License as published by 12 | * the Free Software Foundation; either version 2.1 of the License, or 13 | * (at your option) any later version. 14 | * 15 | * This program is distributed in the hope that it will be useful, 16 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 | * GNU Lesser General Public License for more details. 19 | * 20 | * You should have received a copy of the GNU Lesser General Public License 21 | * along with this program; if not, write to the Free Software 22 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. 23 | *****************************************************************************/ 24 | 25 | #ifndef LIBVLC_CXX_INSTANCE_H 26 | #define LIBVLC_CXX_INSTANCE_H 27 | 28 | #include "common.hpp" 29 | #include "Internal.hpp" 30 | #include "structures.hpp" 31 | #include "Dialog.hpp" 32 | #include "MediaDiscoverer.hpp" 33 | 34 | #include 35 | #include 36 | #include 37 | #include 38 | #include 39 | #include 40 | 41 | namespace VLC 42 | { 43 | 44 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 45 | using Question = libvlc_dialog_question_type; 46 | 47 | namespace DialogType 48 | { 49 | #if !defined(_MSC_VER) || _MSC_VER >= 1900 50 | static constexpr Question normal = LIBVLC_DIALOG_QUESTION_NORMAL; 51 | static constexpr Question warning = LIBVLC_DIALOG_QUESTION_WARNING; 52 | static constexpr Question critical = LIBVLC_DIALOG_QUESTION_CRITICAL; 53 | #else 54 | static const Question normal = LIBVLC_DIALOG_QUESTION_NORMAL; 55 | static const Question warning = LIBVLC_DIALOG_QUESTION_WARNING; 56 | static const Question critical = LIBVLC_DIALOG_QUESTION_CRITICAL; 57 | #endif 58 | } 59 | #endif 60 | 61 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 62 | class Instance : protected CallbackOwner<8>, public Internal 63 | #else 64 | class Instance : protected CallbackOwner<5>, public Internal 65 | #endif 66 | { 67 | private: 68 | enum class CallbackIdx : unsigned int 69 | { 70 | Exit = 0, 71 | Log, 72 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 73 | ErrorDisplay, 74 | LoginDisplay, 75 | QuestionDisplay, 76 | ProgressDisplay, 77 | CancelDialog, 78 | ProgressUpdate 79 | #endif 80 | }; 81 | 82 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 83 | std::shared_ptr m_callbacks_pointers; 84 | #endif 85 | public: 86 | /** 87 | * Create and initialize a libvlc instance. This functions accept a list 88 | * of "command line" arguments similar to the main(). These arguments 89 | * affect the LibVLC instance default configuration. 90 | * 91 | * \version Arguments are meant to be passed from the command line to 92 | * LibVLC, just like VLC media player does. The list of valid arguments 93 | * depends on the LibVLC version, the operating system and platform, and 94 | * set of available LibVLC plugins. Invalid or unsupported arguments will 95 | * cause the function to fail (i.e. return nullptr). Also, some arguments 96 | * may alter the behaviour or otherwise interfere with other LibVLC 97 | * functions. 98 | * 99 | * \warning There is absolutely no warranty or promise of forward, 100 | * backward and cross-platform compatibility with regards to 101 | * Instance::Instance() arguments. We recommend that you do not use them, 102 | * other than when debugging. 103 | * 104 | * \param argc the number of arguments (should be 0) 105 | * 106 | * \param argv list of arguments (should be nullptr) 107 | */ 108 | Instance(int argc, const char *const * argv) 109 | : Internal{ libvlc_new( argc, argv ), libvlc_release } 110 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 111 | , m_callbacks_pointers { std::make_shared() } 112 | #endif 113 | { 114 | } 115 | 116 | /** 117 | * \brief Instance Wraps an existing libvlc instance to be used with libvlcpp 118 | * \param instance A libvlc_instance_t 119 | * 120 | * The instance will be held by the constructor, the caller can release it 121 | * as soon at the instance is constructed. 122 | */ 123 | explicit Instance( libvlc_instance_t* instance ) 124 | : Internal{ instance, libvlc_release } 125 | { 126 | libvlc_retain( instance ); 127 | } 128 | 129 | /** 130 | * Create an empty VLC instance. 131 | * 132 | * Calling any method on such an instance is undefined. 133 | */ 134 | Instance() = default; 135 | 136 | /** 137 | * Check if 2 Instance objects contain the same libvlc_instance_t. 138 | * \param another another Instance 139 | * \return true if they contain the same libvlc_instance_t 140 | */ 141 | bool operator==(const Instance& another) const 142 | { 143 | return m_obj == another.m_obj; 144 | } 145 | 146 | 147 | #if LIBVLC_VERSION_INT < LIBVLC_VERSION(4, 0, 0, 0) 148 | /** 149 | * Try to start a user interface for the libvlc instance. 150 | * 151 | * \param name interface name, or empty string for default 152 | */ 153 | bool addIntf(const std::string& name) 154 | { 155 | return libvlc_add_intf( *this, name.length() > 0 ? name.c_str() : nullptr ) == 0; 156 | } 157 | 158 | /** 159 | * Registers a callback for the LibVLC exit event. This is mostly useful 160 | * if the VLC playlist and/or at least one interface are started with 161 | * libvlc_playlist_play() or Instance::addIntf() respectively. Typically, 162 | * this function will wake up your application main loop (from another 163 | * thread). 164 | * 165 | * \note This function should be called before the playlist or interface 166 | * are started. Otherwise, there is a small race condition: the exit 167 | * event could be raised before the handler is registered. 168 | * 169 | * \param cb callback to invoke when LibVLC wants to exit, or nullptr to 170 | * disable the exit handler (as by default). It is expected to be a 171 | * std::function, or an equivalent Callable type 172 | */ 173 | template 174 | void setExitHandler(ExitCb&& exitCb) 175 | { 176 | static_assert(signature_match_or_nullptr::value, "Mismatched exit callback" ); 177 | libvlc_set_exit_handler( *this, 178 | CallbackWrapper<(unsigned int)CallbackIdx::Exit, void(*)(void*)>::wrap( *m_callbacks, std::forward( exitCb ) ), 179 | m_callbacks.get() ); 180 | } 181 | #endif 182 | 183 | /** 184 | * Sets the application name. LibVLC passes this as the user agent string 185 | * when a protocol requires it. 186 | * 187 | * \param name human-readable application name, e.g. "FooBar player 188 | * 1.2.3" 189 | * 190 | * \param http HTTP User Agent, e.g. "FooBar/1.2.3 Python/2.6.0" 191 | * 192 | * \version LibVLC 1.1.1 or later 193 | */ 194 | void setUserAgent(const std::string& name, const std::string& http) 195 | { 196 | libvlc_set_user_agent( *this, name.c_str(), http.c_str() ); 197 | } 198 | 199 | /** 200 | * Sets some meta-information about the application. See also 201 | * Instance::setUserAgent() . 202 | * 203 | * \param id Java-style application identifier, e.g. "com.acme.foobar" 204 | * 205 | * \param version application version numbers, e.g. "1.2.3" 206 | * 207 | * \param icon application icon name, e.g. "foobar" 208 | * 209 | * \version LibVLC 2.1.0 or later. 210 | */ 211 | void setAppId(const std::string& id, const std::string& version, const std::string& icon) 212 | { 213 | libvlc_set_app_id( *this, id.c_str(), version.c_str(), icon.c_str() ); 214 | } 215 | 216 | /** 217 | * Unsets the logging callback for a LibVLC instance. This is rarely 218 | * needed: the callback is implicitly unset when the instance is 219 | * destroyed. This function will wait for any pending callbacks 220 | * invocation to complete (causing a deadlock if called from within the 221 | * callback). 222 | * 223 | * \version LibVLC 2.1.0 or later 224 | */ 225 | void logUnset() 226 | { 227 | libvlc_log_unset( *this ); 228 | } 229 | 230 | /** 231 | * Sets the logging callback for a LibVLC instance. This function is 232 | * thread-safe: it will wait for any pending callbacks invocation to 233 | * complete. 234 | * 235 | * \note Some log messages (especially debug) are emitted by LibVLC while 236 | * is being initialized. These messages cannot be captured with this 237 | * interface. 238 | * 239 | * \param logCb A std::function 240 | * or an equivalent Callable type instance. 241 | * 242 | * \warning A deadlock may occur if this function is called from the 243 | * callback. 244 | * 245 | * \version LibVLC 2.1.0 or later 246 | */ 247 | template 248 | void logSet(LogCb&& logCb) 249 | { 250 | static_assert(signature_match::value, 251 | "Mismatched log callback" ); 252 | auto wrapper = [logCb](int level, const libvlc_log_t* ctx, const char* format, va_list va) { 253 | const char* psz_module; 254 | const char* psz_file; 255 | unsigned int i_line; 256 | libvlc_log_get_context( ctx, &psz_module, &psz_file, &i_line ); 257 | 258 | #ifndef _MSC_VER 259 | VaCopy vaCopy(va); 260 | int len = vsnprintf(nullptr, 0, format, vaCopy.va); 261 | if (len < 0) 262 | return; 263 | std::unique_ptr message{ new char[len + 1] }; 264 | char* psz_msg = message.get(); 265 | if (vsnprintf(psz_msg, len + 1, format, va) < 0 ) 266 | return; 267 | #else 268 | //MSVC treats passing nullptr as 1st vsnprintf(_s) as an error 269 | char psz_msg[512]; 270 | if ( _vsnprintf_s( psz_msg, _TRUNCATE, format, va ) < 0 ) 271 | return; 272 | #endif 273 | std::ostringstream ss; 274 | ss << '[' << psz_module << "] (" 275 | << psz_file << ':' << i_line 276 | << ") " << psz_msg; 277 | logCb( level, ctx, ss.str() ); 278 | }; 279 | libvlc_log_set(*this, CallbackWrapper<(unsigned int)CallbackIdx::Log, libvlc_log_cb>::wrap( *m_callbacks, std::move(wrapper)), 280 | m_callbacks.get() ); 281 | } 282 | 283 | /** 284 | * Sets up logging to a file. 285 | * 286 | * \param stream FILE pointer opened for writing (the FILE pointer must 287 | * remain valid until Instance::logUnset() ) 288 | * 289 | * \version LibVLC 2.1.0 or later 290 | */ 291 | void logSetFile(FILE * stream) 292 | { 293 | libvlc_log_set_file( *this, stream ); 294 | } 295 | 296 | /** 297 | * Returns a list of audio filters that are available. 298 | * 299 | * \see ModuleDescription 300 | */ 301 | std::vector audioFilterList() 302 | { 303 | std::unique_ptr 304 | ptr( libvlc_audio_filter_list_get(*this), libvlc_module_description_list_release ); 305 | if ( ptr == nullptr ) 306 | return {}; 307 | libvlc_module_description_t* p = ptr.get(); 308 | std::vector res; 309 | while ( p != nullptr ) 310 | { 311 | res.emplace_back( p ); 312 | p = p->p_next; 313 | } 314 | return res; 315 | } 316 | 317 | 318 | /** 319 | * Returns a list of video filters that are available. 320 | * 321 | * \see ModuleDescription 322 | */ 323 | std::vector videoFilterList() 324 | { 325 | std::unique_ptr 326 | ptr( libvlc_video_filter_list_get(*this), &libvlc_module_description_list_release ); 327 | if ( ptr == nullptr ) 328 | return {}; 329 | libvlc_module_description_t* p = ptr.get(); 330 | std::vector res; 331 | while ( p != nullptr ) 332 | { 333 | res.emplace_back( p ); 334 | p = p->p_next; 335 | } 336 | return res; 337 | } 338 | 339 | /** 340 | * Gets the list of available audio output modules. 341 | * 342 | * \see AudioOutputDescription 343 | */ 344 | std::vector audioOutputList() 345 | { 346 | std::unique_ptr 347 | result( libvlc_audio_output_list_get(*this), libvlc_audio_output_list_release ); 348 | if ( result == nullptr ) 349 | return {}; 350 | std::vector res; 351 | 352 | libvlc_audio_output_t* p = result.get(); 353 | while ( p != nullptr ) 354 | { 355 | res.emplace_back( p ); 356 | p = p->p_next; 357 | } 358 | return res; 359 | } 360 | 361 | #if LIBVLC_VERSION_INT < LIBVLC_VERSION(4, 0, 0, 0) 362 | /** 363 | * Gets a list of audio output devices for a given audio output module, 364 | * 365 | * \see Audio::outputDeviceSet() . 366 | * 367 | * \note Not all audio outputs support this. In particular, an empty 368 | * (nullptr) list of devices does imply that the specified audio output does 369 | * not work. 370 | * 371 | * \note The list might not be exhaustive. 372 | * 373 | * \warning Some audio output devices in the list might not actually work 374 | * in some circumstances. By default, it is recommended to not specify 375 | * any explicit audio device. 376 | * 377 | * \param psz_aout audio output name (as returned by 378 | * Instance::audioOutputList() ) 379 | * 380 | * \return A vector containing all audio output devices for this module 381 | * 382 | * \version LibVLC 2.1.0 or later. 383 | */ 384 | std::vector audioOutputDeviceList(const std::string& aout) 385 | { 386 | std::unique_ptr 387 | devices( libvlc_audio_output_device_list_get( *this, aout.c_str() ), libvlc_audio_output_device_list_release ); 388 | if ( devices == nullptr ) 389 | return {}; 390 | std::vector res; 391 | 392 | for ( auto p = devices.get(); p != nullptr; p = p->p_next ) 393 | res.emplace_back( p ); 394 | return res; 395 | } 396 | #endif 397 | 398 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 399 | #if !defined(_MSC_VER) || _MSC_VER >= 1900 400 | /** 401 | * Called when an error message needs to be displayed. 402 | * 403 | * \param title title of the dialog 404 | * \param text text of the dialog 405 | */ 406 | using ErrorCb = void(std::string &&title, std::string &&text); 407 | /** 408 | *Called when a login dialog needs to be displayed. 409 | * 410 | *You can interact with this dialog by using the postLogin method on dialog to post an answer or the dismiss method to cancel this dialog. 411 | * 412 | *\note to receive this callack, CancelCb should not be nullptr. 413 | *\param dialog used to interact with the dialog 414 | *\param title title of the dialog 415 | *\param text text of the dialog 416 | *\param defaultUserName user name that should be set on the user form 417 | *\param askToStore if true, ask the user if he wants to save the credentials 418 | */ 419 | using LoginCb = void(Dialog &&dialog, std::string &&title, std::string &&text, std::string &&defaultUserName, bool askToStore); 420 | /** 421 | * Called when a question dialog needs to be displayed 422 | * 423 | * You can interact with this dialog by using the postAction method on dialog 424 | * to post an answer or dismiss method to cancel this dialog. 425 | * 426 | * \note to receive this callack, CancelCb should not be nullptr. 427 | * 428 | * \param dialog used to interact with the dialog 429 | * \param title title of the diaog 430 | * \param text text of the dialog 431 | * \param qtype question type (or severity) of the dialog 432 | * \param cancel text of the cancel button 433 | * \param action1 text of the first button, if NULL, don't display this 434 | * button 435 | * \param action2 text of the second button, if NULL, don't display 436 | * this button 437 | */ 438 | using QuestionCb = void(Dialog &&dialog, std::string &&title, std::string &&text, Question qType, std::string &&cancel, std::string &&action1, std::string &&action2); 439 | /** 440 | * Called when a progress dialog needs to be displayed 441 | * 442 | * If cancellable (cancel != NULL), you can cancel this dialog by 443 | * calling the dismiss method on dialog 444 | * 445 | * \note to receive this callack, CancelCb and 446 | * UpdtProgressCb should not be NULL. 447 | * 448 | * \param dialog used to interact with the dialog 449 | * \param title title of the diaog 450 | * \param text text of the dialog 451 | * \param indeterminate true if the progress dialog is indeterminate 452 | * \param position initial position of the progress bar (between 0.0 and 453 | * 1.0) 454 | * \param cancel text of the cancel button, if NULL the dialog is not 455 | * cancellable 456 | */ 457 | using DspProgressCb = void(Dialog &&dialog, std::string &&title, std::string &&text, bool intermediate, float position, std::string &&cancel); 458 | /** 459 | * Called when a displayed dialog needs to be cancelled 460 | * 461 | * The implementation must call the method dismiss on dialog to really release 462 | * the dialog. 463 | * 464 | * \param dialog used to interact with the dialog 465 | */ 466 | using CancelCb = void(Dialog &&dialog); 467 | /** 468 | * Called when a progress dialog needs to be updated 469 | * 470 | * \param dialog used to interact with the dialog 471 | * \param position osition of the progress bar (between 0.0 and 1.0) 472 | * \param text new text of the progress dialog 473 | */ 474 | using UpdtProgressCb = void(Dialog &&dialog, float position, std::string &&text); 475 | #else 476 | typedef void (*ErrorCb)(std::string &&title, std::string &&text); 477 | typedef void (*LoginCb)(Dialog &&dialog, std::string &&title, std::string &&text, std::string &&defaultUserName, bool askToStore); 478 | typedef void (*QuestionCb)(Dialog &&dialog, std::string &&title, std::string &&text, Question qType, std::string &&cancel, std::string &&action1, std::string &&action2); 479 | typedef void (*DspProgressCb)(Dialog &&dialog, std::string &&title, std::string &&text, bool intermediate, float position, std::string &&cancel); 480 | typedef void (*CancelCb)(Dialog &&dialog); 481 | typedef void (*UpdtProgressCb)(Dialog &&dialog, float position, std::string &&text); 482 | #endif 483 | /** 484 | * Replaces all the dialog callbacks for this Instance instance 485 | * 486 | * \param error lambda callback that will get called when an error message needs to be displayed. \see ErrorCb 487 | * \param login lambda callback that will get called when a login dialog needs to be displayed. \see LoginCb 488 | * \param question lambda callback that will get called when a question dialog needs to be displayed. \see QuestionCb 489 | * \param dspProgress lambda callback that will get called when a progress dialog needs to be displayed. \see DspProgressCb 490 | * \param cancel lambda callback that will get called when a displayed dialog needs to be cancelled. \see CancelCb 491 | * \param updtProgress lambda callback that will get called when a progress dialog needs to be updated. \see UpdtProgressCb 492 | */ 493 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 494 | template 495 | void setDialogHandlers(Login&& login, Question&& question, DspProgress&& dspProgress, Cancel &&cancel, UpdtProgress &&updtProgress) 496 | { 497 | #if !defined(_MSC_VER) || _MSC_VER >= 1900 498 | static_assert(signature_match_or_nullptr::value, "Mismatched login display callback prototype"); 499 | static_assert(signature_match_or_nullptr::value, "Mismatched question display callback prototype"); 500 | static_assert(signature_match_or_nullptr::value, "Mismatched progress display callback prototype"); 501 | static_assert(signature_match_or_nullptr::value, "Mismatched cancel callback prototype"); 502 | static_assert(signature_match_or_nullptr::value, "Mismatched update progress callback prototype"); 503 | #endif 504 | libvlc_dialog_cbs tmp = { 505 | CallbackWrapper<(unsigned)CallbackIdx::LoginDisplay, decltype(libvlc_dialog_cbs::pf_display_login)>::wrap(*m_callbacks, std::forward(login)), 506 | CallbackWrapper<(unsigned)CallbackIdx::QuestionDisplay, decltype(libvlc_dialog_cbs::pf_display_question)>::wrap(*m_callbacks, std::forward(question)), 507 | CallbackWrapper<(unsigned)CallbackIdx::ProgressDisplay, decltype(libvlc_dialog_cbs::pf_display_progress)>::wrap(*m_callbacks, std::forward(dspProgress)), 508 | CallbackWrapper<(unsigned)CallbackIdx::CancelDialog, decltype(libvlc_dialog_cbs::pf_cancel)>::wrap(*m_callbacks, std::forward(cancel)), 509 | CallbackWrapper<(unsigned)CallbackIdx::ProgressUpdate, decltype(libvlc_dialog_cbs::pf_update_progress)>::wrap(*m_callbacks, std::forward(updtProgress)) 510 | }; 511 | m_callbacks_pointers = std::make_shared(tmp); 512 | libvlc_dialog_set_callbacks(*this, m_callbacks_pointers.get(), m_callbacks.get()); 513 | } 514 | 515 | template 516 | void setErrorCallback(Error&& error) 517 | { 518 | #if !defined(_MSC_VER) || _MSC_VER >= 1900 519 | static_assert(signature_match_or_nullptr::value, "Mismatched error callback prototype"); 520 | #endif 521 | libvlc_dialog_set_error_callback(*this, 522 | CallbackWrapper<(unsigned int)CallbackIdx::ErrorDisplay, libvlc_dialog_error_cbs>::wrap( 523 | *m_callbacks, std::forward(error))); 524 | } 525 | #else 526 | template 527 | void setDialogHandlers(Error&& error, Login&& login, Question&& question, DspProgress&& dspProgress, Cancel &&cancel, UpdtProgress &&updtProgress) 528 | { 529 | #if !defined(_MSC_VER) || _MSC_VER >= 1900 530 | static_assert(signature_match_or_nullptr::value, "Mismatched error display callback prototype"); 531 | static_assert(signature_match_or_nullptr::value, "Mismatched login display callback prototype"); 532 | static_assert(signature_match_or_nullptr::value, "Mismatched question display callback prototype"); 533 | static_assert(signature_match_or_nullptr::value, "Mismatched progress display callback prototype"); 534 | static_assert(signature_match_or_nullptr::value, "Mismatched cancel callback prototype"); 535 | static_assert(signature_match_or_nullptr::value, "Mismatched update progress callback prototype"); 536 | #endif 537 | libvlc_dialog_cbs tmp = { 538 | CallbackWrapper<(unsigned)CallbackIdx::ErrorDisplay, decltype(libvlc_dialog_cbs::pf_display_error)>::wrap(*m_callbacks, std::forward(error)), 539 | CallbackWrapper<(unsigned)CallbackIdx::LoginDisplay, decltype(libvlc_dialog_cbs::pf_display_login)>::wrap(*m_callbacks, std::forward(login)), 540 | CallbackWrapper<(unsigned)CallbackIdx::QuestionDisplay, decltype(libvlc_dialog_cbs::pf_display_question)>::wrap(*m_callbacks, std::forward(question)), 541 | CallbackWrapper<(unsigned)CallbackIdx::ProgressDisplay, decltype(libvlc_dialog_cbs::pf_display_progress)>::wrap(*m_callbacks, std::forward(dspProgress)), 542 | CallbackWrapper<(unsigned)CallbackIdx::CancelDialog, decltype(libvlc_dialog_cbs::pf_cancel)>::wrap(*m_callbacks, std::forward(cancel)), 543 | CallbackWrapper<(unsigned)CallbackIdx::ProgressUpdate, decltype(libvlc_dialog_cbs::pf_update_progress)>::wrap(*m_callbacks, std::forward(updtProgress)) 544 | }; 545 | m_callbacks_pointers = std::make_shared(tmp); 546 | libvlc_dialog_set_callbacks(*this, m_callbacks_pointers.get(), m_callbacks.get()); 547 | } 548 | #endif 549 | /** 550 | * Unset all callbacks 551 | */ 552 | void unsetDialogHandlers() 553 | { 554 | memset(m_callbacks_pointers.get(), 0, sizeof(libvlc_dialog_cbs)); 555 | std::fill(m_callbacks->begin() + 2, m_callbacks->end(), nullptr); 556 | libvlc_dialog_set_callbacks(*this, nullptr, nullptr); 557 | } 558 | 559 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 560 | /** 561 | * Get media discoverer services by category 562 | * 563 | * \version LibVLC 3.0.0 and later. 564 | * 565 | * \param category The category of services to fetch 566 | * 567 | * \return A vector containing the available media discoverers 568 | */ 569 | std::vector mediaDiscoverers(MediaDiscoverer::Category category) 570 | { 571 | libvlc_media_discoverer_description_t** pp_descs; 572 | auto nbSd = libvlc_media_discoverer_list_get( *this, static_cast( category ), 573 | &pp_descs ); 574 | if ( nbSd == 0 ) 575 | return {}; 576 | auto releaser = [nbSd](libvlc_media_discoverer_description_t** ptr) { 577 | libvlc_media_discoverer_list_release( ptr, nbSd ); 578 | }; 579 | std::unique_ptr descPtr( pp_descs, releaser ); 580 | std::vector res; 581 | res.reserve( nbSd ); 582 | for ( auto i = 0u; i < nbSd; ++i ) 583 | res.emplace_back( pp_descs[i]->psz_name, pp_descs[i]->psz_longname, pp_descs[i]->i_cat ); 584 | return res; 585 | } 586 | 587 | std::vector rendererDiscoverers() 588 | { 589 | libvlc_rd_description_t** pp_descs; 590 | auto nbSd = libvlc_renderer_discoverer_list_get(*this, &pp_descs); 591 | if (nbSd == 0) 592 | return {}; 593 | auto releaser = [nbSd](libvlc_rd_description_t** ptr) { 594 | libvlc_renderer_discoverer_list_release(ptr, nbSd); 595 | }; 596 | std::unique_ptr descPtr(pp_descs, releaser); 597 | std::vector res; 598 | res.reserve(nbSd); 599 | for (auto i = 0u; i < nbSd; ++i) 600 | res.emplace_back( pp_descs[i] ); 601 | return res; 602 | } 603 | 604 | #endif 605 | 606 | #endif // LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 607 | }; 608 | 609 | } // namespace VLC 610 | 611 | #endif 612 | 613 | -------------------------------------------------------------------------------- /vlcpp/Internal.hpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | * Internal.hpp: Wraps an internal vlc type. 3 | ***************************************************************************** 4 | * Copyright © 2014 VideoLAN 5 | * 6 | * Authors: Hugo Beauzée-Luyssen 7 | * 8 | * This program is free software; you can redistribute it and/or modify 9 | * it under the terms of the GNU Lesser General Public License as published by 10 | * the Free Software Foundation; either version 2.1 of the License, or 11 | * (at your option) any later version. 12 | * 13 | * This program is distributed in the hope that it will be useful, 14 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 | * GNU Lesser General Public License for more details. 17 | * 18 | * You should have received a copy of the GNU Lesser General Public License 19 | * along with this program; if not, write to the Free Software 20 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. 21 | *****************************************************************************/ 22 | 23 | #ifndef VLCPP_H 24 | #define VLCPP_H 25 | 26 | #include 27 | #include 28 | #include 29 | #include 30 | #include 31 | 32 | namespace VLC 33 | { 34 | 35 | /// 36 | /// @brief The Internal class is a helper to wrap a raw libvlc type in a common 37 | /// C++ type. 38 | /// 39 | template 40 | class Internal 41 | { 42 | public: 43 | using InternalType = T; 44 | using InternalPtr = T*; 45 | using Pointer = std::shared_ptr; 46 | 47 | /// 48 | /// \brief get returns the underlying libvlc type, or nullptr if this 49 | /// is an empty instance 50 | /// 51 | InternalPtr get() const { return m_obj.get(); } 52 | 53 | /// 54 | /// \brief isValid returns true if this instance isn't wrapping a nullptr 55 | /// \return 56 | /// 57 | bool isValid() const { return (bool)m_obj; } 58 | 59 | /// 60 | /// \brief operator T * helper to convert to the underlying libvlc type 61 | /// 62 | operator T*() const { return m_obj.get(); } 63 | 64 | protected: 65 | Internal() = default; 66 | 67 | 68 | Internal( InternalPtr obj, Releaser releaser ) 69 | { 70 | if ( obj == nullptr ) 71 | throw std::runtime_error("Wrapping a nullptr instance"); 72 | m_obj.reset( obj, releaser ); 73 | } 74 | 75 | Internal(Releaser releaser) 76 | : m_obj{ nullptr, releaser } 77 | { 78 | } 79 | 80 | protected: 81 | Pointer m_obj; 82 | }; 83 | 84 | } 85 | 86 | #endif // VLCPP_H 87 | -------------------------------------------------------------------------------- /vlcpp/Media.hpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | * Media.hpp: Media API 3 | ***************************************************************************** 4 | * Copyright © 2015 libvlcpp authors & VideoLAN 5 | * 6 | * Authors: Alexey Sokolov 7 | * Hugo Beauzée-Luyssen 8 | * 9 | * This program is free software; you can redistribute it and/or modify 10 | * it under the terms of the GNU Lesser General Public License as published by 11 | * the Free Software Foundation; either version 2.1 of the License, or 12 | * (at your option) any later version. 13 | * 14 | * This program is distributed in the hope that it will be useful, 15 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 | * GNU Lesser General Public License for more details. 18 | * 19 | * You should have received a copy of the GNU Lesser General Public License 20 | * along with this program; if not, write to the Free Software 21 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. 22 | *****************************************************************************/ 23 | 24 | #ifndef LIBVLC_CXX_MEDIA_H 25 | #define LIBVLC_CXX_MEDIA_H 26 | 27 | #include "common.hpp" 28 | 29 | #include 30 | #include 31 | 32 | namespace VLC 33 | { 34 | 35 | class MediaEventManager; 36 | class Instance; 37 | class MediaList; 38 | class TrackList; 39 | 40 | class Media : protected CallbackOwner<4>, public Internal 41 | { 42 | private: 43 | enum class CallbackIdx : unsigned int 44 | { 45 | Open, 46 | Read, 47 | Seek, 48 | Close, 49 | }; 50 | #if !defined(_MSC_VER) || _MSC_VER >= 1900 51 | static constexpr unsigned int NbEvents = 4; 52 | #else 53 | static const unsigned int NbEvents = 4; 54 | #endif 55 | 56 | public: 57 | /// 58 | /// \brief The FromType enum is used to drive the media creation. 59 | /// A media is usually created using a string, which can represent one of 3 things: 60 | /// 61 | enum class FromType 62 | { 63 | /** 64 | * Create a media for a certain file path. 65 | */ 66 | FromPath, 67 | /** 68 | * Create a media with a certain given media resource location, 69 | * for instance a valid URL. 70 | * 71 | * \note To refer to a local file with this function, 72 | * the file://... URI syntax must be used (see IETF RFC3986). 73 | * We recommend using FromPath instead when dealing with 74 | * local files. 75 | */ 76 | FromLocation, 77 | /** 78 | * Create a media as an empty node with a given name. 79 | */ 80 | AsNode, 81 | }; 82 | // To be able to write Media::FromLocation 83 | #if !defined(_MSC_VER) || _MSC_VER >= 1900 84 | constexpr static FromType FromPath = FromType::FromPath; 85 | constexpr static FromType FromLocation = FromType::FromLocation; 86 | constexpr static FromType AsNode = FromType::AsNode; 87 | #else 88 | static const FromType FromPath = FromType::FromPath; 89 | static const FromType FromLocation = FromType::FromLocation; 90 | static const FromType AsNode = FromType::AsNode; 91 | #endif 92 | 93 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 94 | enum class ParseFlags 95 | { 96 | /** 97 | * Parse media if it's a local file 98 | */ 99 | Local = libvlc_media_parse_local, 100 | /** 101 | * Parse media even if it's a network file 102 | */ 103 | Network = libvlc_media_parse_network, 104 | /** 105 | * Fetch meta and covert art using local resources 106 | */ 107 | FetchLocal = libvlc_media_fetch_local, 108 | /** 109 | * Fetch meta and covert art using network resources 110 | */ 111 | FetchNetwork = libvlc_media_fetch_network, 112 | /** 113 | * Interact with the user (via libvlc_dialog_cbs) when preparsing this item 114 | * (and not its sub items). Set this flag in order to receive a callback 115 | * when the input is asking for credentials. 116 | */ 117 | Interact = libvlc_media_do_interact, 118 | }; 119 | 120 | enum class ParsedStatus 121 | { 122 | Skipped = libvlc_media_parsed_status_skipped, 123 | Failed = libvlc_media_parsed_status_failed, 124 | Done = libvlc_media_parsed_status_done, 125 | Timeout = libvlc_media_parsed_status_timeout, 126 | }; 127 | 128 | enum class Type 129 | { 130 | Unknown = libvlc_media_type_unknown, 131 | File = libvlc_media_type_file, 132 | Directory = libvlc_media_type_directory, 133 | Disc = libvlc_media_type_disc, 134 | Stream = libvlc_media_type_stream, 135 | Playlist = libvlc_media_type_playlist, 136 | }; 137 | #endif 138 | 139 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 140 | /** 141 | * @brief Media Constructs a libvlc Media instance 142 | * @param instance A libvlc instance 143 | * @param mrl A path, location, or node name, depending on the 3rd parameter 144 | * @param type The type of the 2nd argument. \sa{FromType} 145 | */ 146 | Media(const std::string& mrl, FromType type) 147 | : Internal{ libvlc_media_release } 148 | { 149 | InternalPtr ptr = nullptr; 150 | switch (type) 151 | { 152 | case FromLocation: 153 | ptr = libvlc_media_new_location( mrl.c_str() ); 154 | break; 155 | case FromPath: 156 | ptr = libvlc_media_new_path( mrl.c_str() ); 157 | break; 158 | case AsNode: 159 | ptr = libvlc_media_new_as_node( mrl.c_str() ); 160 | break; 161 | default: 162 | break; 163 | } 164 | if ( ptr == nullptr ) 165 | throw std::runtime_error("Failed to construct a media"); 166 | m_obj.reset( ptr, libvlc_media_release ); 167 | } 168 | 169 | /** 170 | * Create a media for an already open file descriptor. 171 | * The file descriptor shall be open for reading (or reading and writing). 172 | * 173 | * Regular file descriptors, pipe read descriptors and character device 174 | * descriptors (including TTYs) are supported on all platforms. 175 | * Block device descriptors are supported where available. 176 | * Directory descriptors are supported on systems that provide fdopendir(). 177 | * Sockets are supported on all platforms where they are file descriptors, 178 | * i.e. all except Windows. 179 | * 180 | * \note This library will not automatically close the file descriptor 181 | * under any circumstance. Nevertheless, a file descriptor can usually only be 182 | * rendered once in a media player. To render it a second time, the file 183 | * descriptor should probably be rewound to the beginning with lseek(). 184 | * 185 | * \param fd open file descriptor 186 | * \return the newly created media 187 | */ 188 | Media( int fd) 189 | : Internal { libvlc_media_new_fd( fd ), 190 | libvlc_media_release } 191 | { 192 | } 193 | #else 194 | /** 195 | * @brief Media Constructs a libvlc Media instance 196 | * @param instance A libvlc instance 197 | * @param mrl A path, location, or node name, depending on the 3rd parameter 198 | * @param type The type of the 2nd argument. \sa{FromType} 199 | */ 200 | Media(const Instance& instance, const std::string& mrl, FromType type) 201 | : Internal{ libvlc_media_release } 202 | { 203 | InternalPtr ptr = nullptr; 204 | switch (type) 205 | { 206 | case FromLocation: 207 | ptr = libvlc_media_new_location( getInternalPtr( instance ), mrl.c_str() ); 208 | break; 209 | case FromPath: 210 | ptr = libvlc_media_new_path( getInternalPtr( instance ), mrl.c_str() ); 211 | break; 212 | case AsNode: 213 | ptr = libvlc_media_new_as_node( getInternalPtr( instance ), mrl.c_str() ); 214 | break; 215 | default: 216 | break; 217 | } 218 | if ( ptr == nullptr ) 219 | throw std::runtime_error("Failed to construct a media"); 220 | m_obj.reset( ptr, libvlc_media_release ); 221 | } 222 | 223 | /** 224 | * Create a media for an already open file descriptor. 225 | * The file descriptor shall be open for reading (or reading and writing). 226 | * 227 | * Regular file descriptors, pipe read descriptors and character device 228 | * descriptors (including TTYs) are supported on all platforms. 229 | * Block device descriptors are supported where available. 230 | * Directory descriptors are supported on systems that provide fdopendir(). 231 | * Sockets are supported on all platforms where they are file descriptors, 232 | * i.e. all except Windows. 233 | * 234 | * \note This library will not automatically close the file descriptor 235 | * under any circumstance. Nevertheless, a file descriptor can usually only be 236 | * rendered once in a media player. To render it a second time, the file 237 | * descriptor should probably be rewound to the beginning with lseek(). 238 | * 239 | * \param instance the instance 240 | * \param fd open file descriptor 241 | * \return the newly created media 242 | */ 243 | Media(const Instance& instance, int fd) 244 | : Internal { libvlc_media_new_fd( getInternalPtr( instance ), fd ), 245 | libvlc_media_release } 246 | { 247 | } 248 | #endif 249 | 250 | /** 251 | * Get media instance from this media list instance. This action will increase 252 | * the refcount on the media instance. 253 | * The libvlc_media_list_lock should NOT be held upon entering this function. 254 | * 255 | * \param list a media list instance 256 | * \return media instance 257 | */ 258 | Media(MediaList& list) 259 | : Internal{ libvlc_media_list_media( getInternalPtr( list ) ), 260 | libvlc_media_release } 261 | { 262 | } 263 | 264 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 265 | /** 266 | * Callback prototype to open a custom bitstream input media. 267 | * 268 | * The same media item can be opened multiple times. Each time, this callback 269 | * is invoked. It should allocate and initialize any instance-specific 270 | * resources, then store them in *datap. The instance resources can be freed 271 | * in the @ref libvlc_close_cb callback. 272 | * 273 | * \param opaque private pointer as passed to libvlc_media_new_callbacks() 274 | * \param datap storage space for a private data pointer [OUT] 275 | * \param sizep byte length of the bitstream or 0 if unknown [OUT] 276 | * 277 | * \note For convenience, *datap is initially NULL and *sizep is initially 0. 278 | * 279 | * \return 0 on success, non-zero on error. In case of failure, the other 280 | * callbacks will not be invoked and any value stored in *datap and *sizep is 281 | * discarded. 282 | */ 283 | using ExpectedMediaOpenCb = int(void*, void** datap, uint64_t* sizep); 284 | 285 | /** 286 | * Callback prototype to read data from a custom bitstream input media. 287 | * 288 | * \param opaque private pointer as set by the @ref libvlc_media_open_cb 289 | * callback 290 | * \param buf start address of the buffer to read data into 291 | * \param len bytes length of the buffer 292 | * 293 | * \return strictly positive number of bytes read, 0 on end-of-stream, 294 | * or -1 on non-recoverable error 295 | * 296 | * \note If no data is immediately available, then the callback should sleep. 297 | * \warning The application is responsible for avoiding deadlock situations. 298 | * In particular, the callback should return an error if playback is stopped; 299 | * if it does not return, then libvlc_media_player_stop() will never return. 300 | */ 301 | using ExpectedMediaReadCb = ptrdiff_t(void* opaque, unsigned char* buf, size_t len); 302 | 303 | /** 304 | * Callback prototype to seek a custom bitstream input media. 305 | * 306 | * \param opaque private pointer as set by the @ref libvlc_media_open_cb 307 | * callback 308 | * \param offset absolute byte offset to seek to 309 | * \return 0 on success, -1 on error. 310 | */ 311 | using ExpectedMediaSeekCb = int(void* opaque, uint64_t); 312 | 313 | /** 314 | * Callback prototype to close a custom bitstream input media. 315 | * \param opaque private pointer as set by the @ref libvlc_media_open_cb 316 | * callback 317 | */ 318 | using ExpectedMediaCloseCb = void(void* opaque); 319 | 320 | /** 321 | * Create a media with custom callbacks to read the data from. 322 | * 323 | * \param instance LibVLC instance 324 | * \param open_cb callback to open the custom bitstream input media 325 | * \param read_cb callback to read data (must not be nullptr) 326 | * \param seek_cb callback to seek, or nullptr if seeking is not supported 327 | * \param close_cb callback to close the media, or nullptr if unnecessary 328 | * 329 | * \return the newly created media. 330 | * 331 | * \throw std::runtime_error if the media creation fails 332 | * 333 | * \note If open_cb is NULL, the opaque pointer will be passed to read_cb, 334 | * seek_cb and close_cb, and the stream size will be treated as unknown. 335 | * 336 | * \note The callbacks may be called asynchronously (from another thread). 337 | * A single stream instance need not be reentrant. However the open_cb needs to 338 | * be reentrant if the media is used by multiple player instances. 339 | * 340 | * \warning The callbacks may be used until all or any player instances 341 | * that were supplied the media item are stopped. 342 | * 343 | * \see ExpectedMediaOpenCb 344 | * \see ExpectedMediaReadCb 345 | * \see ExpectedMediaSeekCb 346 | * \see ExpectedMediaCloseCb 347 | * 348 | * \version LibVLC 3.0.0 and later. 349 | */ 350 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 351 | template 352 | Media( OpenCb&& openCb, ReadCb&& readCb, SeekCb&& seekCb, CloseCb&& closeCb ) 353 | { 354 | static_assert( signature_match_or_nullptr::value, "Mismatched Open callback prototype" ); 355 | static_assert( signature_match_or_nullptr::value, "Mismatched Seek callback prototype" ); 356 | static_assert( signature_match_or_nullptr::value, "Mismatched Close callback prototype" ); 357 | static_assert( signature_match::value, "Mismatched Read callback prototype" ); 358 | 359 | auto ptr = libvlc_media_new_callbacks( 360 | imem::CallbackWrapper<(unsigned int)CallbackIdx::Open, libvlc_media_open_cb>:: 361 | wrap::Strategy>( 362 | *m_callbacks, std::forward( openCb ) ), 363 | imem::CallbackWrapper<(unsigned int)CallbackIdx::Read, libvlc_media_read_cb>:: 364 | wrap::Strategy>( 365 | *m_callbacks, std::forward( readCb ) ), 366 | imem::CallbackWrapper<(unsigned int)CallbackIdx::Seek, libvlc_media_seek_cb>:: 367 | wrap::Strategy>( 368 | *m_callbacks, std::forward( seekCb ) ), 369 | imem::CallbackWrapper<(unsigned int)CallbackIdx::Close, libvlc_media_close_cb>:: 370 | wrap::Strategy>( 371 | *m_callbacks, std::forward( closeCb ) ), 372 | m_callbacks.get() 373 | ); 374 | if ( ptr == nullptr ) 375 | throw std::runtime_error( "Failed to create media" ); 376 | m_obj.reset( ptr, libvlc_media_release ); 377 | } 378 | #else 379 | template 380 | Media( const Instance& instance, OpenCb&& openCb, ReadCb&& readCb, SeekCb&& seekCb, CloseCb&& closeCb ) 381 | { 382 | static_assert( signature_match_or_nullptr::value, "Mismatched Open callback prototype" ); 383 | static_assert( signature_match_or_nullptr::value, "Mismatched Seek callback prototype" ); 384 | static_assert( signature_match_or_nullptr::value, "Mismatched Close callback prototype" ); 385 | static_assert( signature_match::value, "Mismatched Read callback prototype" ); 386 | 387 | auto ptr = libvlc_media_new_callbacks( instance, 388 | imem::CallbackWrapper<(unsigned int)CallbackIdx::Open, libvlc_media_open_cb>:: 389 | wrap::Strategy>( 390 | *m_callbacks, std::forward( openCb ) ), 391 | imem::CallbackWrapper<(unsigned int)CallbackIdx::Read, libvlc_media_read_cb>:: 392 | wrap::Strategy>( 393 | *m_callbacks, std::forward( readCb ) ), 394 | imem::CallbackWrapper<(unsigned int)CallbackIdx::Seek, libvlc_media_seek_cb>:: 395 | wrap::Strategy>( 396 | *m_callbacks, std::forward( seekCb ) ), 397 | imem::CallbackWrapper<(unsigned int)CallbackIdx::Close, libvlc_media_close_cb>:: 398 | wrap::Strategy>( 399 | *m_callbacks, std::forward( closeCb ) ), 400 | m_callbacks.get() 401 | ); 402 | if ( ptr == nullptr ) 403 | throw std::runtime_error( "Failed to create media" ); 404 | m_obj.reset( ptr, libvlc_media_release ); 405 | } 406 | #endif 407 | #endif 408 | 409 | explicit Media( Internal::InternalPtr ptr, bool incrementRefCount) 410 | : Internal{ ptr, libvlc_media_release } 411 | { 412 | if ( incrementRefCount && ptr != nullptr ) 413 | retain(); 414 | } 415 | 416 | /** 417 | * Create an empty VLC Media instance. 418 | * 419 | * Calling any method on such an instance is undefined. 420 | */ 421 | Media() = default; 422 | 423 | /** 424 | * Check if 2 Media objects contain the same libvlc_media_t. 425 | * \param another another Media 426 | * \return true if they contain the same libvlc_media_t 427 | */ 428 | bool operator==(const Media& another) const 429 | { 430 | return m_obj == another.m_obj; 431 | } 432 | 433 | /** 434 | * Add an option to the media. 435 | * 436 | * This option will be used to determine how the media_player will read 437 | * the media. This allows to use VLC's advanced reading/streaming options 438 | * on a per-media basis. 439 | * 440 | * \note The options are listed in 'vlc long-help' from the command line, 441 | * e.g. "-sout-all". Keep in mind that available options and their 442 | * semantics vary across LibVLC versions and builds. 443 | * 444 | * \warning Not all options affects libvlc_media_t objects: Specifically, 445 | * due to architectural issues most audio and video options, such as text 446 | * renderer options, have no effects on an individual media. These 447 | * options must be set through Instance::Instance() instead. 448 | * 449 | * \param psz_options the options (as a string) 450 | */ 451 | void addOption(const std::string& psz_options) 452 | { 453 | libvlc_media_add_option(*this,psz_options.c_str()); 454 | } 455 | 456 | /** 457 | * Add an option to the media with configurable flags. 458 | * 459 | * This option will be used to determine how the media_player will read 460 | * the media. This allows to use VLC's advanced reading/streaming options 461 | * on a per-media basis. 462 | * 463 | * The options are detailed in vlc long-help, for instance "--sout-all". 464 | * Note that all options are not usable on medias: specifically, due to 465 | * architectural issues, video-related options such as text renderer 466 | * options cannot be set on a single media. They must be set on the whole 467 | * libvlc instance instead. 468 | * 469 | * \param psz_options the options (as a string) 470 | * 471 | * \param i_flags the flags for this option 472 | */ 473 | void addOptionFlag(const std::string& psz_options, unsigned i_flags) 474 | { 475 | libvlc_media_add_option_flag(*this,psz_options.c_str(), i_flags); 476 | } 477 | 478 | /** 479 | * Get the media resource locator (mrl) from a media descriptor object 480 | * 481 | * \return string with mrl of media descriptor object 482 | */ 483 | std::string mrl() 484 | { 485 | auto str = wrapCStr( libvlc_media_get_mrl(*this) ); 486 | if ( str == nullptr ) 487 | return {}; 488 | return str.get(); 489 | } 490 | 491 | /** 492 | * Duplicate a media descriptor object. 493 | */ 494 | Media duplicate() 495 | { 496 | auto obj = libvlc_media_duplicate(*this); 497 | // Assume failure to duplicate is due to VLC_ENOMEM. 498 | // libvlc_media_duplicate(nullptr) would also return nullptr, but 499 | // we consider the use of an empty libvlcpp instance undefined. 500 | if ( obj == nullptr ) 501 | throw std::bad_alloc(); 502 | return Media( obj, false ); 503 | } 504 | 505 | /** 506 | * Read the meta of the media. 507 | * 508 | * If the media has not yet been parsed this will return an empty string. 509 | * 510 | * This methods automatically calls parseAsync() , so after 511 | * calling it you may receive a libvlc_MediaMetaChanged event. If you 512 | * prefer a synchronous version ensure that you call parse() 513 | * before get_meta(). 514 | * 515 | * \see parse() 516 | * 517 | * \see parseAsync() 518 | * 519 | * \see libvlc_MediaMetaChanged 520 | * 521 | * \param e_meta the meta to read 522 | * 523 | * \return the media's meta 524 | */ 525 | std::string meta(libvlc_meta_t e_meta) 526 | { 527 | auto str = wrapCStr(libvlc_media_get_meta(*this, e_meta) ); 528 | if ( str == nullptr ) 529 | return {}; 530 | return str.get(); 531 | } 532 | 533 | /** 534 | * Set the meta of the media (this function will not save the meta, call 535 | * libvlc_media_save_meta in order to save the meta) 536 | * 537 | * \param e_meta the meta to write 538 | * 539 | * \param psz_value the media's meta 540 | */ 541 | void setMeta(libvlc_meta_t e_meta, const std::string& psz_value) 542 | { 543 | libvlc_media_set_meta(*this, e_meta, psz_value.c_str()); 544 | } 545 | 546 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 547 | /** 548 | * Save the meta previously set 549 | * 550 | * \return true if the write operation was successful 551 | */ 552 | bool saveMeta(const Instance& instance) 553 | { 554 | return libvlc_media_save_meta(getInternalPtr(instance), *this) != 0; 555 | } 556 | #else 557 | /** 558 | * Save the meta previously set 559 | * 560 | * \return true if the write operation was successful 561 | */ 562 | bool saveMeta() 563 | { 564 | return libvlc_media_save_meta(*this) != 0; 565 | } 566 | #endif 567 | 568 | #if LIBVLC_VERSION_INT < LIBVLC_VERSION(4, 0, 0, 0) 569 | /** 570 | * Get current state of media descriptor object. Possible media states 571 | * are defined in libvlc_structures.c ( libvlc_NothingSpecial=0, 572 | * libvlc_Opening, libvlc_Buffering, libvlc_Playing, libvlc_Paused, 573 | * libvlc_Stopped, libvlc_Ended, libvlc_Error). 574 | * 575 | * \see libvlc_state_t 576 | * 577 | * \return state of media descriptor object 578 | */ 579 | libvlc_state_t state() 580 | { 581 | return libvlc_media_get_state(*this); 582 | } 583 | #endif 584 | /** 585 | * Get the current statistics about the media 586 | * 587 | * \param p_stats structure that contain the statistics about the media 588 | * (this structure must be allocated by the caller) 589 | * 590 | * \return true if the statistics are available, false otherwise 591 | */ 592 | bool stats(libvlc_media_stats_t * p_stats) 593 | { 594 | return libvlc_media_get_stats(*this, p_stats) != 0; 595 | } 596 | 597 | /** 598 | * Get event manager from media descriptor object. NOTE: this function 599 | * doesn't increment reference counting. 600 | * 601 | * \return event manager object 602 | */ 603 | MediaEventManager& eventManager() 604 | { 605 | if ( m_eventManager == nullptr ) 606 | { 607 | libvlc_event_manager_t* obj = libvlc_media_event_manager(*this); 608 | m_eventManager = std::make_shared( obj, *this ); 609 | } 610 | return *m_eventManager; 611 | } 612 | 613 | /** 614 | * Get duration (in ms) of media descriptor object item. 615 | * 616 | * \return duration of media item or -1 on error 617 | */ 618 | libvlc_time_t duration() 619 | { 620 | return libvlc_media_get_duration(*this); 621 | } 622 | 623 | #if LIBVLC_VERSION_INT < LIBVLC_VERSION(3, 0, 0, 0) 624 | /** 625 | * Parse a media. 626 | * 627 | * This fetches (local) meta data and tracks information. The method is 628 | * synchronous. 629 | * 630 | * \see parseAsync() 631 | * 632 | * \see meta() 633 | * 634 | * \see tracksInfo() 635 | */ 636 | void parse() 637 | { 638 | libvlc_media_parse(*this); 639 | } 640 | 641 | /** 642 | * Parse a media. 643 | * 644 | * This fetches (local) meta data and tracks information. The method is 645 | * the asynchronous of parse() . 646 | * 647 | * To track when this is over you can listen to libvlc_MediaParsedChanged 648 | * event. However if the media was already parsed you will not receive 649 | * this event. 650 | * 651 | * \see parse() 652 | * 653 | * \see libvlc_MediaParsedChanged 654 | * 655 | * \see meta() 656 | * 657 | * \see tracks() 658 | */ 659 | void parseAsync() 660 | { 661 | libvlc_media_parse_async(*this); 662 | } 663 | 664 | /** 665 | * Get Parsed status for media descriptor object. 666 | * 667 | * \see libvlc_MediaParsedChanged 668 | * 669 | * \return true if media object has been parsed otherwise it returns 670 | * false 671 | */ 672 | bool isParsed() 673 | { 674 | return libvlc_media_is_parsed(*this) != 0; 675 | } 676 | #elif LIBVLC_VERSION_INT < LIBVLC_VERSION(4, 0, 0, 0) 677 | /** 678 | * Parse the media asynchronously with options. 679 | * 680 | * This fetches (local or network) art, meta data and/or tracks information. 681 | * This method is the extended version of libvlc_media_parse_async(). 682 | * 683 | * To track when this is over you can listen to libvlc_MediaParsedStatus 684 | * event. However if this functions returns an error, you will not receive any 685 | * events. 686 | * 687 | * It uses a flag to specify parse options (see libvlc_media_parse_flag_t). All 688 | * these flags can be combined. By default, media is parsed if it's a local 689 | * file. 690 | * 691 | * \see ParsedStatus 692 | * \see meta() 693 | * \see tracks() 694 | * \see parsedStatus 695 | * \see ParseFlag 696 | * 697 | * \return true on success, false otherwise 698 | * \param flags parse options 699 | * \param timeout maximum time allowed to preparse the media. If -1, the 700 | * default "preparse-timeout" option will be used as a timeout. If 0, it will 701 | * wait indefinitely. If > 0, the timeout will be used (in milliseconds). 702 | * \version LibVLC 3.0.0 or later 703 | */ 704 | bool parseWithOptions( ParseFlags flags, int timeout ) 705 | { 706 | return libvlc_media_parse_with_options( *this, static_cast( flags ), timeout ) == 0; 707 | } 708 | 709 | ParsedStatus parsedStatus() 710 | { 711 | return static_cast( libvlc_media_get_parsed_status( *this ) ); 712 | } 713 | 714 | void parseStop() 715 | { 716 | libvlc_media_parse_stop( *this ); 717 | } 718 | #else 719 | /** 720 | * Parse the media asynchronously with options. 721 | * 722 | * This fetches (local or network) art, meta data and/or tracks information. 723 | * This method is the extended version of libvlc_media_parse_async(). 724 | * 725 | * To track when this is over you can listen to libvlc_MediaParsedStatus 726 | * event. However if this functions returns an error, you will not receive any 727 | * events. 728 | * 729 | * It uses a flag to specify parse options (see libvlc_media_parse_flag_t). All 730 | * these flags can be combined. By default, media is parsed if it's a local 731 | * file. 732 | * 733 | * \see ParsedStatus 734 | * \see meta() 735 | * \see tracks() 736 | * \see parsedStatus 737 | * \see ParseFlag 738 | * 739 | * \return true on success, false otherwise 740 | * \param flags parse options 741 | * \param timeout maximum time allowed to preparse the media. If -1, the 742 | * default "preparse-timeout" option will be used as a timeout. If 0, it will 743 | * wait indefinitely. If > 0, the timeout will be used (in milliseconds). 744 | * \version LibVLC 3.0.0 or later 745 | */ 746 | bool parseRequest( const Instance& instance, ParseFlags flags, int timeout ) 747 | { 748 | return libvlc_media_parse_request( getInternalPtr( instance ), 749 | *this, static_cast( flags ), timeout ) == 0; 750 | } 751 | 752 | ParsedStatus parsedStatus( const Instance& instance ) 753 | { 754 | return static_cast( getInternalPtr( instance ), 755 | libvlc_media_get_parsed_status( *this ) ); 756 | } 757 | 758 | void parseStop( const Instance& instance ) 759 | { 760 | libvlc_media_parse_stop( getInternalPtr( instance ), 761 | *this ); 762 | } 763 | #endif 764 | 765 | /** 766 | * Sets media descriptor's user_data. user_data is specialized data 767 | * accessed by the host application, VLC.framework uses it as a pointer 768 | * to an native object that references a libvlc_media_t pointer 769 | * 770 | * \param p_new_user_data pointer to user data 771 | */ 772 | void setUserData(void * p_new_user_data) 773 | { 774 | libvlc_media_set_user_data(*this, p_new_user_data); 775 | } 776 | 777 | /** 778 | * Get media descriptor's user_data. user_data is specialized data 779 | * accessed by the host application, VLC.framework uses it as a pointer 780 | * to an native object that references a libvlc_media_t pointer 781 | */ 782 | void* userData() 783 | { 784 | return libvlc_media_get_user_data(*this); 785 | } 786 | 787 | /** 788 | * Get media descriptor's elementary streams description 789 | * 790 | * Note, you need to call parse() or play the media at least once 791 | * before calling this function. Not doing this will result in an empty 792 | * list. 793 | * 794 | * \version LibVLC 2.1.0 and later. 795 | * 796 | * \return a vector containing all tracks 797 | */ 798 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 799 | std::vector tracks( MediaTrack::Type type ) 800 | { 801 | using TrackListPtr = std::unique_ptr; 803 | TrackListPtr trackList{ libvlc_media_get_tracklist( *this, 804 | static_cast( type ) ), 805 | &libvlc_media_tracklist_delete }; 806 | if ( trackList == nullptr ) 807 | return {}; 808 | auto count = libvlc_media_tracklist_count( trackList.get() ); 809 | std::vector res{}; 810 | for ( auto i = 0u; i < count; ++i ) 811 | res.emplace_back( libvlc_media_tracklist_at( trackList.get(), i ) ); 812 | return res; 813 | } 814 | #elif LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 815 | std::vector tracks() 816 | { 817 | libvlc_media_track_t** tracks; 818 | uint32_t nbTracks = libvlc_media_tracks_get(*this, &tracks); 819 | std::vector res; 820 | 821 | if ( nbTracks == 0 ) 822 | return res; 823 | 824 | for ( uint32_t i = 0; i < nbTracks; ++i ) 825 | res.emplace_back( tracks[i] ); 826 | libvlc_media_tracks_release( tracks, nbTracks ); 827 | return res; 828 | } 829 | #endif 830 | 831 | std::shared_ptr subitems() 832 | { 833 | auto p = libvlc_media_subitems( *this ); 834 | if ( p == nullptr ) 835 | return nullptr; 836 | return std::make_shared( p ); 837 | } 838 | 839 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 840 | Type type() 841 | { 842 | return static_cast( libvlc_media_get_type( *this ) ); 843 | } 844 | 845 | /** 846 | * Add a slave to the current media. 847 | * 848 | * A slave is an external input source that may contains an additional subtitle 849 | * track (like a .srt) or an additional audio track (like a .ac3). 850 | * 851 | * \note This function must be called before the media is parsed (via parseWithOptions()) 852 | * or before the media is played (via MediaPlayer::play()) 853 | * 854 | * \version LibVLC 3.0.0 and later. 855 | * 856 | * \param uri Uri of the slave (should contain a valid scheme). 857 | * \param type subtitle or audio 858 | * \param priority from 0 (low priority) to 4 (high priority) 859 | * 860 | * \return true on success, false on error. 861 | */ 862 | bool addSlave(MediaSlave::Type type, unsigned priority, std::string const &uri) 863 | { 864 | return libvlc_media_slaves_add(*this, (libvlc_media_slave_type_t)type, priority, uri.c_str()) == 0; 865 | } 866 | 867 | /** 868 | * Clear all slaves previously added by addSlave() or 869 | * internally. 870 | * 871 | * \version LibVLC 3.0.0 and later. 872 | */ 873 | void slavesClear() 874 | { 875 | libvlc_media_slaves_clear(*this); 876 | } 877 | 878 | /** 879 | * Get a media descriptor's slaves in a vector 880 | * 881 | * The list will contain slaves parsed by VLC or previously added by 882 | * addSlave(). The typical use case of this function is to save 883 | * a list of slave in a database for a later use. 884 | * 885 | * \version LibVLC 3.0.0 and later. 886 | * 887 | * \see addSlave() 888 | * 889 | * \return a vector of MediaSlave 890 | */ 891 | std::vector slaves() const 892 | { 893 | libvlc_media_slave_t **list = nullptr; 894 | 895 | auto length = libvlc_media_slaves_get(*this, &list); 896 | if (length == 0) 897 | return {}; 898 | auto deletor = [length](libvlc_media_slave_t **p_list) { 899 | libvlc_media_slaves_release(p_list, length); 900 | }; 901 | std::unique_ptr scope_gard(list, deletor); 902 | std::vector res(list, list + length); 903 | return res; 904 | } 905 | #endif 906 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 907 | using ThumbnailRequest = libvlc_media_thumbnail_request_t; 908 | 909 | enum class ThumbnailSeekSpeed 910 | { 911 | Precise = libvlc_media_thumbnail_seek_precise, 912 | Fast = libvlc_media_thumbnail_seek_fast, 913 | }; 914 | 915 | ThumbnailRequest* thumbnailRequestByTime( const Instance& inst, libvlc_time_t time, ThumbnailSeekSpeed speed, 916 | uint32_t width, uint32_t height, bool crop, 917 | Picture::Type type, libvlc_time_t timeout ) 918 | { 919 | return libvlc_media_thumbnail_request_by_time( 920 | getInternalPtr( inst ), *this, time, 921 | static_cast( speed ), width, 922 | height, crop, static_cast( type ), timeout ); 923 | } 924 | 925 | ThumbnailRequest* thumbnailRequestByPos( const Instance& inst, float pos, ThumbnailSeekSpeed speed, 926 | uint32_t width, uint32_t height, bool crop, 927 | Picture::Type type, libvlc_time_t timeout ) 928 | { 929 | return libvlc_media_thumbnail_request_by_pos( 930 | getInternalPtr( inst ), *this, pos, 931 | static_cast( speed ), width, 932 | height, crop, static_cast( type ), timeout ); 933 | } 934 | 935 | /** 936 | * @brief thumbnailRequestDestroy Destroy and cancel a thumbnailing request 937 | * @param request An opaque thumbnail request object. 938 | * 939 | * This will also cancel the thumbnail request, no events will be emitted after 940 | * this call. 941 | */ 942 | void thumbnailRequestDestroy( ThumbnailRequest* request ) 943 | { 944 | libvlc_media_thumbnail_request_destroy( request ); 945 | } 946 | 947 | enum class FileStat : uint8_t 948 | { 949 | Mtime = libvlc_media_filestat_mtime, 950 | Size = libvlc_media_filestat_size, 951 | }; 952 | 953 | std::pair fileStat( FileStat s ) 954 | { 955 | uint64_t value = 0; 956 | auto res = libvlc_media_get_filestat( *this, static_cast( s ), &value ) == 1; 957 | return std::make_pair( res, value ); 958 | } 959 | #endif 960 | 961 | 962 | private: 963 | 964 | /** 965 | * Retain a reference to a media descriptor object (libvlc_media_t). Use 966 | * release() to decrement the reference count of a media 967 | * descriptor object. 968 | */ 969 | void retain() 970 | { 971 | if ( isValid() ) 972 | libvlc_media_retain(*this); 973 | } 974 | 975 | 976 | private: 977 | std::shared_ptr m_eventManager; 978 | }; 979 | 980 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 981 | inline VLC::Media::ParseFlags operator|(Media::ParseFlags l, Media::ParseFlags r) 982 | { 983 | #if !defined(_MSC_VER) || _MSC_VER >= 1900 984 | using T = typename std::underlying_type::type; 985 | #else 986 | using T = std::underlying_type::type; 987 | #endif 988 | return static_cast( static_cast( l ) | static_cast( r ) ); 989 | } 990 | #endif 991 | 992 | } // namespace VLC 993 | 994 | #endif 995 | 996 | -------------------------------------------------------------------------------- /vlcpp/MediaDiscoverer.hpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | * MediaDiscoverer.hpp: MediaDiscoverer API 3 | ***************************************************************************** 4 | * Copyright © 2015 libvlcpp authors & VideoLAN 5 | * 6 | * Authors: Alexey Sokolov 7 | * Hugo Beauzée-Luyssen 8 | * 9 | * This program is free software; you can redistribute it and/or modify 10 | * it under the terms of the GNU Lesser General Public License as published by 11 | * the Free Software Foundation; either version 2.1 of the License, or 12 | * (at your option) any later version. 13 | * 14 | * This program is distributed in the hope that it will be useful, 15 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 | * GNU Lesser General Public License for more details. 18 | * 19 | * You should have received a copy of the GNU Lesser General Public License 20 | * along with this program; if not, write to the Free Software 21 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. 22 | *****************************************************************************/ 23 | 24 | #ifndef LIBVLC_CXX_MEDIADISCOVERER_H 25 | #define LIBVLC_CXX_MEDIADISCOVERER_H 26 | 27 | #include "common.hpp" 28 | 29 | #include 30 | #include 31 | 32 | namespace VLC 33 | { 34 | 35 | class Instance; 36 | class MediaList; 37 | #if LIBVLC_VERSION_INT < LIBVLC_VERSION(3, 0, 0, 0) 38 | class MediaDiscovererEventManager; 39 | #endif 40 | 41 | class MediaDiscoverer : public Internal 42 | { 43 | public: 44 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 45 | enum class Category 46 | { 47 | Devices = libvlc_media_discoverer_devices, 48 | Lan = libvlc_media_discoverer_lan, 49 | Podcasts = libvlc_media_discoverer_podcasts, 50 | Localdirs = libvlc_media_discoverer_localdirs, 51 | }; 52 | 53 | class Description 54 | { 55 | public: 56 | explicit Description( const std::string& name, const std::string& longName, libvlc_media_discoverer_category_t cat ) 57 | : m_name( name ) 58 | , m_longName( longName ) 59 | , m_category( static_cast( cat ) ) 60 | { 61 | } 62 | 63 | const std::string& name() const 64 | { 65 | return m_name; 66 | } 67 | 68 | const std::string& longName() const 69 | { 70 | return m_longName; 71 | } 72 | 73 | Category category() const 74 | { 75 | return m_category; 76 | } 77 | 78 | private: 79 | std::string m_name; 80 | std::string m_longName; 81 | Category m_category; 82 | }; 83 | #endif 84 | /** 85 | * Discover media service by name. 86 | * 87 | * \param p_inst libvlc instance 88 | * 89 | * \param psz_name service name 90 | */ 91 | MediaDiscoverer(const Instance& inst, const std::string& name) 92 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 93 | : Internal{ libvlc_media_discoverer_new(getInternalPtr( inst ), name.c_str()), 94 | #else 95 | : Internal{ libvlc_media_discoverer_new_from_name(getInternalPtr( inst ), name.c_str()), 96 | #endif 97 | libvlc_media_discoverer_release } 98 | { 99 | } 100 | 101 | /** 102 | * Create an empty Media Discoverer instance. 103 | * 104 | * Calling any method on such an instance is undefined. 105 | */ 106 | MediaDiscoverer() = default; 107 | 108 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 109 | /** 110 | * Start media discovery. 111 | * 112 | * To stop it, call MediaDiscover::stop() or 113 | * destroy the object directly. 114 | * 115 | * \see MediaDiscover::stop 116 | * 117 | * \return false in case of error, true otherwise 118 | */ 119 | bool start() 120 | { 121 | return libvlc_media_discoverer_start( *this ) == 0; 122 | } 123 | 124 | /** 125 | * Stop media discovery. 126 | * 127 | * \see MediaDiscoverer::start() 128 | */ 129 | void stop() 130 | { 131 | libvlc_media_discoverer_stop( *this ); 132 | } 133 | #endif 134 | 135 | #if LIBVLC_VERSION_INT < LIBVLC_VERSION(3, 0, 0, 0) 136 | /** 137 | * Get media service discover object its localized name. 138 | * 139 | * \return localized name 140 | */ 141 | std::string localizedName() 142 | { 143 | auto str = wrapCStr( libvlc_media_discoverer_localized_name(*this) ); 144 | if ( str == nullptr ) 145 | return {}; 146 | return str.get(); 147 | } 148 | 149 | /** 150 | * Get event manager from media service discover object. 151 | * 152 | * \return event manager object. 153 | */ 154 | MediaDiscovererEventManager& eventManager() 155 | { 156 | if ( m_eventManager == nullptr ) 157 | { 158 | libvlc_event_manager_t* obj = libvlc_media_discoverer_event_manager( *this ); 159 | m_eventManager = std::make_shared( obj ); 160 | } 161 | return *m_eventManager; 162 | } 163 | #endif 164 | 165 | /** 166 | * Query if media service discover object is running. 167 | * 168 | * \return true if running, false if not 169 | */ 170 | bool isRunning() 171 | { 172 | return libvlc_media_discoverer_is_running(*this) != 0; 173 | } 174 | 175 | std::shared_ptr mediaList() 176 | { 177 | if ( m_mediaList == nullptr ) 178 | { 179 | auto mlist = libvlc_media_discoverer_media_list( *this ); 180 | if ( mlist == nullptr ) 181 | return nullptr; 182 | m_mediaList = std::make_shared( mlist ); 183 | } 184 | return m_mediaList; 185 | } 186 | 187 | private: 188 | #if LIBVLC_VERSION_INT < LIBVLC_VERSION(3, 0, 0, 0) 189 | std::shared_ptr m_eventManager; 190 | #endif 191 | std::shared_ptr m_mediaList; 192 | }; 193 | 194 | } // namespace VLC 195 | 196 | #endif 197 | 198 | -------------------------------------------------------------------------------- /vlcpp/MediaLibrary.hpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | * MediaLibrary.hpp: MediaLibrary API 3 | ***************************************************************************** 4 | * Copyright © 2015 libvlcpp authors & VideoLAN 5 | * 6 | * Authors: Alexey Sokolov 7 | * Hugo Beauzée-Luyssen 8 | * 9 | * This program is free software; you can redistribute it and/or modify 10 | * it under the terms of the GNU Lesser General Public License as published by 11 | * the Free Software Foundation; either version 2.1 of the License, or 12 | * (at your option) any later version. 13 | * 14 | * This program is distributed in the hope that it will be useful, 15 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 | * GNU Lesser General Public License for more details. 18 | * 19 | * You should have received a copy of the GNU Lesser General Public License 20 | * along with this program; if not, write to the Free Software 21 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. 22 | *****************************************************************************/ 23 | 24 | #ifndef LIBVLC_CXX_MEDIALIBRARY_H 25 | #define LIBVLC_CXX_MEDIALIBRARY_H 26 | 27 | #include "common.hpp" 28 | 29 | #if LIBVLC_VERSION_INT < LIBVLC_VERSION(4, 0, 0, 0) 30 | 31 | #include "Internal.hpp" 32 | 33 | namespace VLC 34 | { 35 | 36 | class MediaLibrary : public Internal 37 | { 38 | public: 39 | /** 40 | * Create an new Media Library object 41 | * 42 | * \param instance the libvlc instance 43 | */ 44 | MediaLibrary(Instance& instance) 45 | : Internal{ libvlc_media_library_new( getInternalPtr( instance ) ), 46 | libvlc_media_library_release } 47 | { 48 | } 49 | 50 | /** 51 | * Create an empty VLC MediaLibrary instance. 52 | * 53 | * Calling any method on such an instance is undefined. 54 | */ 55 | MediaLibrary() = default; 56 | 57 | /** 58 | * Check if 2 MediaLibrary objects contain the same libvlc_media_library_t. 59 | * \param another another MediaLibrary 60 | * \return true if they contain the same libvlc_media_library_t 61 | */ 62 | bool operator==(const MediaLibrary& another) const 63 | { 64 | return m_obj == another.m_obj; 65 | } 66 | 67 | /** 68 | * Load media library. 69 | */ 70 | bool load() 71 | { 72 | return libvlc_media_library_load(*this) == 0; 73 | } 74 | }; 75 | 76 | } // namespace VLC 77 | 78 | #endif 79 | 80 | #endif 81 | -------------------------------------------------------------------------------- /vlcpp/MediaList.hpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | * MediaList.hpp: MediaList API 3 | ***************************************************************************** 4 | * Copyright © 2015 libvlcpp authors & VideoLAN 5 | * 6 | * Authors: Alexey Sokolov 7 | * Hugo Beauzée-Luyssen 8 | * 9 | * This program is free software; you can redistribute it and/or modify 10 | * it under the terms of the GNU Lesser General Public License as published by 11 | * the Free Software Foundation; either version 2.1 of the License, or 12 | * (at your option) any later version. 13 | * 14 | * This program is distributed in the hope that it will be useful, 15 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 | * GNU Lesser General Public License for more details. 18 | * 19 | * You should have received a copy of the GNU Lesser General Public License 20 | * along with this program; if not, write to the Free Software 21 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. 22 | *****************************************************************************/ 23 | 24 | #ifndef LIBVLC_CXX_MEDIALIST_H 25 | #define LIBVLC_CXX_MEDIALIST_H 26 | 27 | #include "common.hpp" 28 | 29 | #include 30 | 31 | namespace VLC 32 | { 33 | 34 | class Media; 35 | class MediaListEventManager; 36 | class MediaDiscoverer; 37 | class MediaLibrary; 38 | 39 | class MediaList : public Internal 40 | { 41 | public: 42 | /// 43 | /// @brief A convenience RAII type to handle MediaList's lock 44 | /// 45 | using Lock = std::lock_guard; 46 | 47 | /** 48 | * Check if 2 MediaList objects contain the same libvlc_media_list_t. 49 | * \param another another MediaList 50 | * \return true if they contain the same libvlc_media_list_t 51 | */ 52 | bool operator==(const MediaList& another) const 53 | { 54 | return m_obj == another.m_obj; 55 | } 56 | 57 | /** 58 | * Get subitems of media descriptor object. 59 | */ 60 | MediaList(Media& md) 61 | : Internal{ libvlc_media_subitems( getInternalPtr( md ) ), libvlc_media_list_release } 62 | { 63 | } 64 | 65 | /** 66 | * Get media service discover media list. 67 | * 68 | * \param p_mdis media service discover object 69 | */ 70 | MediaList(MediaDiscoverer& mdis) 71 | : Internal{ libvlc_media_discoverer_media_list( getInternalPtr( mdis ) ), 72 | libvlc_media_list_release } 73 | { 74 | } 75 | 76 | #if LIBVLC_VERSION_INT < LIBVLC_VERSION(4, 0, 0, 0) 77 | /** 78 | * Get media library subitems. 79 | * 80 | * \param p_mlib media library object 81 | */ 82 | MediaList(MediaLibrary& mlib) 83 | : Internal{ libvlc_media_library_media_list( getInternalPtr( mlib ) ), libvlc_media_list_release } 84 | { 85 | } 86 | 87 | /** 88 | * Create an empty VLC MediaList instance. 89 | * 90 | * Calling any method on such an instance is undefined. 91 | */ 92 | MediaList() = default; 93 | 94 | /** 95 | * Create an empty media list. 96 | * 97 | * \param p_instance libvlc instance 98 | */ 99 | MediaList(const Instance& instance) 100 | : Internal{ libvlc_media_list_new( getInternalPtr( instance ) ), 101 | libvlc_media_list_release } 102 | { 103 | } 104 | #else 105 | /** 106 | * Create an empty media list. 107 | * 108 | * \param p_instance libvlc instance 109 | */ 110 | MediaList() 111 | : Internal{ libvlc_media_list_new(), 112 | libvlc_media_list_release } 113 | { 114 | } 115 | #endif 116 | 117 | MediaList( Internal::InternalPtr mediaList ) 118 | : Internal{ mediaList, libvlc_media_list_release } 119 | { 120 | } 121 | 122 | /** 123 | * Associate media instance with this media list instance. If another 124 | * media instance was present it will be released. The 125 | * MediaList lock should NOT be held upon entering this function. 126 | * 127 | * \param p_md media instance to add 128 | */ 129 | void setMedia(Media& md) 130 | { 131 | libvlc_media_list_set_media( *this, getInternalPtr( md ) ); 132 | } 133 | 134 | /** 135 | * Add media instance to media list The MediaList lock should be 136 | * held upon entering this function. 137 | * 138 | * \param p_md a media instance 139 | */ 140 | bool addMedia(Media& md) 141 | { 142 | return libvlc_media_list_add_media( *this, getInternalPtr( md ) ) == 0; 143 | } 144 | 145 | /** 146 | * Insert media instance in media list on a position The 147 | * MediaList lock should be held upon entering this function. 148 | * 149 | * \param p_md a media instance 150 | * 151 | * \param i_pos position in array where to insert 152 | */ 153 | bool insertMedia(Media& md, int pos) 154 | { 155 | return libvlc_media_list_insert_media( *this, getInternalPtr( md ), pos ) == 0; 156 | } 157 | 158 | /** 159 | * Remove media instance from media list on a position The 160 | * MediaList lock should be held upon entering this function. 161 | * 162 | * \param i_pos position in array where to insert 163 | */ 164 | bool removeIndex(int i_pos) 165 | { 166 | return libvlc_media_list_remove_index( *this, i_pos ) == 0; 167 | } 168 | 169 | /** 170 | * Get count on media list items The MediaList lock should be 171 | * held upon entering this function. 172 | * 173 | * \return number of items in media list 174 | */ 175 | int count() 176 | { 177 | return libvlc_media_list_count( *this ); 178 | } 179 | 180 | /** 181 | * List media instance in media list at a position The 182 | * MediaList lock should be held upon entering this function. 183 | * 184 | * \param i_pos position in array where to insert 185 | * 186 | * \return media instance at position i_pos, or nullptr if not found. 187 | */ 188 | MediaPtr itemAtIndex(int i_pos) 189 | { 190 | auto ptr = libvlc_media_list_item_at_index(*this,i_pos); 191 | if ( ptr == nullptr ) 192 | return nullptr; 193 | return std::make_shared( ptr, false ); 194 | } 195 | 196 | /** 197 | * Find index position of List media instance in media list. Warning: the 198 | * function will return the first matched position. The 199 | * MediaList lock should be held upon entering this function. 200 | * 201 | * \param p_md media instance 202 | * 203 | * \return position of media instance or -1 if media not found 204 | */ 205 | int indexOfItem(Media& md) 206 | { 207 | return libvlc_media_list_index_of_item( *this, getInternalPtr( md ) ); 208 | } 209 | 210 | /** 211 | * This indicates if this media list is read-only from a user point of 212 | * view 213 | * 214 | * \return true if readonly, false otherwise 215 | */ 216 | bool isReadonly() 217 | { 218 | return libvlc_media_list_is_readonly(*this) == 1; 219 | } 220 | 221 | /** 222 | * Get lock on media list items 223 | */ 224 | void lock() 225 | { 226 | libvlc_media_list_lock( *this ); 227 | } 228 | 229 | /** 230 | * Release lock on media list items The MediaList lock should be 231 | * held upon entering this function. 232 | */ 233 | void unlock() 234 | { 235 | libvlc_media_list_unlock( *this ); 236 | } 237 | 238 | /** 239 | * Get libvlc_event_manager from this media list instance. The 240 | * p_event_manager is immutable, so you don't have to hold the lock 241 | * 242 | * \return libvlc_event_manager 243 | */ 244 | MediaListEventManager& eventManager() 245 | { 246 | if ( m_eventManager == nullptr ) 247 | { 248 | libvlc_event_manager_t* obj = libvlc_media_list_event_manager( *this ); 249 | m_eventManager = std::make_shared( obj, *this ); 250 | } 251 | return *m_eventManager; 252 | } 253 | 254 | private: 255 | std::shared_ptr m_eventManager; 256 | }; 257 | 258 | } // namespace VLC 259 | 260 | #endif 261 | 262 | -------------------------------------------------------------------------------- /vlcpp/MediaListPlayer.hpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | * MediaListPlayer.hpp: MediaListPlayer API 3 | ***************************************************************************** 4 | * Copyright © 2015 libvlcpp authors & VideoLAN 5 | * 6 | * Authors: Alexey Sokolov 7 | * Hugo Beauzée-Luyssen 8 | * 9 | * This program is free software; you can redistribute it and/or modify 10 | * it under the terms of the GNU Lesser General Public License as published by 11 | * the Free Software Foundation; either version 2.1 of the License, or 12 | * (at your option) any later version. 13 | * 14 | * This program is distributed in the hope that it will be useful, 15 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 | * GNU Lesser General Public License for more details. 18 | * 19 | * You should have received a copy of the GNU Lesser General Public License 20 | * along with this program; if not, write to the Free Software 21 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. 22 | *****************************************************************************/ 23 | 24 | #ifndef LIBVLC_CXX_MEDIALISTPLAYER_H 25 | #define LIBVLC_CXX_MEDIALISTPLAYER_H 26 | 27 | #include 28 | 29 | #include "common.hpp" 30 | 31 | namespace VLC 32 | { 33 | 34 | class MediaListPlayerEventManager; 35 | class MediaPlayer; 36 | class MediaList; 37 | 38 | class MediaListPlayer : public Internal 39 | { 40 | public: 41 | /** 42 | * Check if 2 MediaListPlayer objects contain the same libvlc_media_list_player_t. 43 | * \param another another MediaListPlayer 44 | * \return true if they contain the same libvlc_media_list_player_t 45 | */ 46 | bool operator==(const MediaListPlayer& another) const 47 | { 48 | return m_obj == another.m_obj; 49 | } 50 | 51 | /** 52 | * Create new media_list_player. 53 | * 54 | * \param p_instance libvlc instance 55 | */ 56 | MediaListPlayer(const Instance& instance) 57 | : Internal{ libvlc_media_list_player_new( getInternalPtr( instance ) ), 58 | libvlc_media_list_player_release } 59 | { 60 | } 61 | 62 | /** 63 | * Create an empty VLC MediaListPlayer instance. 64 | * 65 | * Calling any method on such an instance is undefined. 66 | */ 67 | MediaListPlayer() = default; 68 | 69 | /** 70 | * Return the event manager of this media_list_player. 71 | * 72 | * \return the event manager 73 | */ 74 | MediaListPlayerEventManager& eventManager() 75 | { 76 | if ( m_eventManager == nullptr ) 77 | { 78 | libvlc_event_manager_t* obj = libvlc_media_list_player_event_manager(*this); 79 | m_eventManager = std::make_shared( obj, *this ); 80 | } 81 | return *m_eventManager; 82 | } 83 | 84 | 85 | /** 86 | * Replace media player in media_list_player with this instance. 87 | * 88 | * \param p_mi media player instance 89 | */ 90 | void setMediaPlayer(const MediaPlayer& mi) 91 | { 92 | libvlc_media_list_player_set_media_player( *this, 93 | getInternalPtr( mi ) ); 94 | } 95 | 96 | /** 97 | * Set the media list associated with the player 98 | * 99 | * \param p_mlist list of media 100 | */ 101 | void setMediaList(const MediaList& mlist) 102 | { 103 | libvlc_media_list_player_set_media_list( *this, 104 | getInternalPtr( mlist ) ); 105 | } 106 | 107 | /** 108 | * Play media list 109 | */ 110 | void play() 111 | { 112 | libvlc_media_list_player_play(*this); 113 | } 114 | 115 | /** 116 | * Toggle pause (or resume) media list 117 | */ 118 | void pause() 119 | { 120 | libvlc_media_list_player_pause(*this); 121 | } 122 | 123 | /** 124 | * Is media list playing? 125 | * 126 | * \return true for playing and false for not playing 127 | */ 128 | bool isPlaying() 129 | { 130 | return libvlc_media_list_player_is_playing(*this) != 0; 131 | } 132 | 133 | /** 134 | * Get current libvlc_state of media list player 135 | * 136 | * \return libvlc_state_t for media list player 137 | */ 138 | libvlc_state_t state() 139 | { 140 | return libvlc_media_list_player_get_state( *this ); 141 | } 142 | 143 | /** 144 | * Play media list item at position index 145 | * 146 | * \param i_index index in media list to play 147 | */ 148 | bool playItemAtIndex(int i_index) 149 | { 150 | return libvlc_media_list_player_play_item_at_index(*this, i_index) == 0; 151 | } 152 | 153 | /** 154 | * Play the given media item 155 | * 156 | * \param p_md the media instance 157 | */ 158 | bool playItem(const Media& md) 159 | { 160 | return libvlc_media_list_player_play_item( *this, 161 | getInternalPtr( md ) ) == 0; 162 | } 163 | 164 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 165 | /** 166 | * Stop playing media list 167 | */ 168 | void stopAsync() 169 | { 170 | libvlc_media_list_player_stop_async(*this); 171 | } 172 | #else 173 | /** 174 | * Stop playing media list 175 | */ 176 | void stop() 177 | { 178 | libvlc_media_list_player_stop(*this); 179 | } 180 | #endif 181 | 182 | /** 183 | * Play next item from media list 184 | */ 185 | bool next() 186 | { 187 | return libvlc_media_list_player_next(*this) == 0; 188 | } 189 | 190 | /** 191 | * Play previous item from media list 192 | */ 193 | bool previous() 194 | { 195 | return libvlc_media_list_player_previous(*this) == 0; 196 | } 197 | 198 | /** 199 | * Sets the playback mode for the playlist 200 | * 201 | * \param e_mode playback mode specification 202 | */ 203 | void setPlaybackMode(libvlc_playback_mode_t e_mode) 204 | { 205 | libvlc_media_list_player_set_playback_mode(*this, e_mode); 206 | } 207 | 208 | private: 209 | std::shared_ptr m_eventManager; 210 | 211 | }; 212 | 213 | } // namespace VLC 214 | 215 | #endif 216 | 217 | -------------------------------------------------------------------------------- /vlcpp/Picture.hpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | * Picture.hpp: Picture API 3 | ***************************************************************************** 4 | * Copyright © 2018 libvlcpp authors & VideoLAN 5 | * 6 | * Authors: Hugo Beauzée-Luyssen 7 | * 8 | * This program is free software; you can redistribute it and/or modify 9 | * it under the terms of the GNU Lesser General Public License as published by 10 | * the Free Software Foundation; either version 2.1 of the License, or 11 | * (at your option) any later version. 12 | * 13 | * This program is distributed in the hope that it will be useful, 14 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 | * GNU Lesser General Public License for more details. 17 | * 18 | * You should have received a copy of the GNU Lesser General Public License 19 | * along with this program; if not, write to the Free Software 20 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. 21 | *****************************************************************************/ 22 | 23 | #ifndef LIBVLC_CXX_PICTURE_HPP 24 | #define LIBVLC_CXX_PICTURE_HPP 25 | 26 | #include "common.hpp" 27 | 28 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 29 | 30 | namespace VLC 31 | { 32 | 33 | class Picture : public Internal 34 | { 35 | public: 36 | enum class Type : uint8_t 37 | { 38 | Argb = libvlc_picture_Argb, 39 | Jpg = libvlc_picture_Jpg, 40 | Png = libvlc_picture_Png, 41 | }; 42 | 43 | Picture() = default; 44 | 45 | explicit Picture( Internal::InternalPtr ptr ) 46 | : Internal( ptr, libvlc_picture_release ) 47 | { 48 | libvlc_picture_retain( ptr ); 49 | } 50 | 51 | /** 52 | * Saves this picture to a file. The image format is the same as the one 53 | * returned by \link Picture::type() \endlink 54 | * 55 | * \param path The path to the generated file 56 | * \return true in case of success, false otherwise 57 | */ 58 | bool save( const std::string& path ) const 59 | { 60 | return libvlc_picture_save( *this, path.c_str() ) == 0; 61 | } 62 | 63 | /** 64 | * Returns the image internal buffer, including potential padding. 65 | * The picture instance owns the returned buffer, which must not be modified 66 | * nor freed. 67 | * 68 | * \param size A pointer to a size_t that will hold the size of the buffer [out] [required] 69 | * \return A pointer to the internal buffer. 70 | */ 71 | const uint8_t* buffer( size_t* size ) const 72 | { 73 | return libvlc_picture_get_buffer( *this, size ); 74 | } 75 | 76 | /** 77 | * Returns the picture type 78 | * 79 | * \see Picture::Type 80 | */ 81 | Type type() const 82 | { 83 | return static_cast( libvlc_picture_type( *this ) ); 84 | } 85 | 86 | /** 87 | * Returns the image stride, ie. the number of bytes per line. 88 | * This can only be called on images of type Picture::Type::Argb 89 | */ 90 | uint32_t stride() const 91 | { 92 | return libvlc_picture_get_stride( *this ); 93 | } 94 | 95 | /** 96 | * Returns the width of the image in pixels 97 | */ 98 | uint32_t width() const 99 | { 100 | return libvlc_picture_get_width( *this ); 101 | } 102 | 103 | /** 104 | * Returns the height of the image in pixels 105 | */ 106 | uint32_t height() const 107 | { 108 | return libvlc_picture_get_height( *this ); 109 | } 110 | 111 | /** 112 | * Returns the time at which this picture was generated, in milliseconds 113 | */ 114 | libvlc_time_t time() const 115 | { 116 | return libvlc_picture_get_time( *this ); 117 | } 118 | }; 119 | 120 | } 121 | 122 | #endif 123 | 124 | #endif // LIBVLC_CXX_PICTURE_HPP 125 | -------------------------------------------------------------------------------- /vlcpp/RendererDiscoverer.hpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | * RendererDiscovery.hpp: Media Discoverer API 3 | ***************************************************************************** 4 | * Copyright © 2015-2018 libvlcpp authors & VideoLAN 5 | * 6 | * Authors: Hugo Beauzée-Luyssen 7 | * 8 | * This program is free software; you can redistribute it and/or modify 9 | * it under the terms of the GNU Lesser General Public License as published by 10 | * the Free Software Foundation; either version 2.1 of the License, or 11 | * (at your option) any later version. 12 | * 13 | * This program is distributed in the hope that it will be useful, 14 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 | * GNU Lesser General Public License for more details. 17 | * 18 | * You should have received a copy of the GNU Lesser General Public License 19 | * along with this program; if not, write to the Free Software 20 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. 21 | *****************************************************************************/ 22 | 23 | #ifndef LIBVLC_CXX_RENDERERDISCOVERER_HPP 24 | #define LIBVLC_CXX_RENDERERDISCOVERER_HPP 25 | 26 | #include "common.hpp" 27 | 28 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 29 | 30 | namespace VLC 31 | { 32 | 33 | class RendererDiscovererEventManager; 34 | 35 | class RendererDiscoverer : public Internal 36 | { 37 | public: 38 | class Item : public Internal 39 | { 40 | private: 41 | Item( InternalPtr item ) : Internal( item, libvlc_renderer_item_release ) 42 | { 43 | libvlc_renderer_item_hold( *this ); 44 | } 45 | 46 | public: 47 | std::string name() const 48 | { 49 | return libvlc_renderer_item_name( *this ); 50 | } 51 | 52 | std::string type() const 53 | { 54 | return libvlc_renderer_item_type( *this ); 55 | } 56 | 57 | std::string iconUri() const 58 | { 59 | return libvlc_renderer_item_icon_uri( *this ); 60 | } 61 | 62 | bool canRenderVideo() const 63 | { 64 | return ( libvlc_renderer_item_flags( *this ) & 65 | LIBVLC_RENDERER_CAN_VIDEO ) != 0; 66 | } 67 | 68 | bool canRenderAudio() const 69 | { 70 | return ( libvlc_renderer_item_flags( *this ) & 71 | LIBVLC_RENDERER_CAN_AUDIO ) != 0; 72 | } 73 | 74 | friend RendererDiscovererEventManager; 75 | }; 76 | 77 | RendererDiscoverer( const Instance& instance, const std::string& name ) 78 | : Internal( libvlc_renderer_discoverer_new( getInternalPtr( instance ), 79 | name.c_str() ), libvlc_renderer_discoverer_release ) 80 | { 81 | } 82 | 83 | bool start() 84 | { 85 | return libvlc_renderer_discoverer_start( *this ) == 0; 86 | } 87 | 88 | void stop() 89 | { 90 | libvlc_renderer_discoverer_stop( *this ); 91 | } 92 | 93 | RendererDiscovererEventManager& eventManager() 94 | { 95 | if ( m_eventManager == nullptr ) 96 | { 97 | libvlc_event_manager_t* obj = libvlc_renderer_discoverer_event_manager( *this ); 98 | m_eventManager = std::make_shared( obj, *this ); 99 | } 100 | return *m_eventManager; 101 | } 102 | 103 | private: 104 | std::shared_ptr m_eventManager; 105 | }; 106 | 107 | } 108 | 109 | #endif 110 | 111 | #endif // LIBVLC_CXX_RENDERERDISCOVERER_HPP 112 | -------------------------------------------------------------------------------- /vlcpp/common.hpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | * common.hpp: Basic shared types & helpers 3 | ***************************************************************************** 4 | * Copyright © 2015 libvlcpp authors & VideoLAN 5 | * 6 | * Authors: Hugo Beauzée-Luyssen 7 | * Jonathan Calmels 8 | * 9 | * This program is free software; you can redistribute it and/or modify 10 | * it under the terms of the GNU Lesser General Public License as published by 11 | * the Free Software Foundation; either version 2.1 of the License, or 12 | * (at your option) any later version. 13 | * 14 | * This program is distributed in the hope that it will be useful, 15 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 | * GNU Lesser General Public License for more details. 18 | * 19 | * You should have received a copy of the GNU Lesser General Public License 20 | * along with this program; if not, write to the Free Software 21 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. 22 | *****************************************************************************/ 23 | 24 | #ifndef LIBVLC_CXX_COMMON_H 25 | #define LIBVLC_CXX_COMMON_H 26 | 27 | #ifdef _MSC_VER 28 | using ssize_t = long int; 29 | #endif 30 | 31 | #include 32 | #include 33 | #include 34 | #include 35 | #include 36 | 37 | namespace VLC 38 | { 39 | class Media; 40 | using MediaPtr = std::shared_ptr; 41 | 42 | // Work around cross class dependencies 43 | // Class A needs to access B's internal pointer 44 | // Class B needs to access A's internal pointer 45 | // By using a template function to do this, we're delegating 46 | // the access to both classes' guts to a later point, when the compiler 47 | // already knows everything it needs. 48 | // The only drawback is that we can't return decltype(ptr->get()), since when 49 | // the compiler checks for the prototype, it hasn't parsed all the declarations yet. 50 | template 51 | TYPE* getInternalPtr(const REF& ref) 52 | { 53 | return ref.get(); 54 | } 55 | 56 | inline std::unique_ptr wrapCStr(char* str) 57 | { 58 | return std::unique_ptr( str, &libvlc_free ); 59 | } 60 | 61 | #if !defined(_MSC_VER) 62 | // Kudos to 3xxO for the signature_match helper 63 | template 64 | struct signature_match : std::false_type {}; 65 | 66 | template 67 | struct signature_match()(std::declval()...)), 71 | Ret 72 | >::value // true or false 73 | >::type // void or SFINAE 74 | > : std::true_type {}; 75 | #else 76 | template 77 | struct signature_match : std::false_type {}; 78 | 79 | template 80 | struct signature_match 81 | : std::integral_constant < bool, 82 | std::is_convertible < decltype(std::declval()(std::declval()...)), Ret 83 | > ::value 84 | > {}; 85 | #endif 86 | 87 | template 88 | struct signature_match_or_nullptr : std::integral_constant::value 90 | > 91 | { 92 | }; 93 | 94 | template 95 | struct signature_match_or_nullptr : std::true_type 96 | { 97 | }; 98 | 99 | struct CallbackHandlerBase 100 | { 101 | virtual ~CallbackHandlerBase() = default; 102 | }; 103 | 104 | template 105 | struct CallbackHandler : public CallbackHandlerBase 106 | { 107 | template 108 | CallbackHandler(FuncFwd&& f) : func( std::forward( f ) ) {} 109 | Func func; 110 | }; 111 | 112 | template 113 | using CallbackArray = std::array, NbEvent>; 114 | 115 | /// 116 | /// Utility class that contains a shared pointer to a callback array. 117 | /// We use a shared_ptr to allow multiple instances to share the same callback array 118 | /// This must be inherited before the Internal type, to ensure it gets deleted 119 | /// after the wrapped libvlc object. 120 | /// 121 | template 122 | class CallbackOwner 123 | { 124 | protected: 125 | CallbackOwner() 126 | : m_callbacks( std::make_shared>() ) 127 | { 128 | } 129 | std::shared_ptr> m_callbacks; 130 | }; 131 | 132 | template 133 | struct FromOpaque; 134 | 135 | template 136 | struct FromOpaque 137 | { 138 | static CallbackArray& get( void* opaque ) 139 | { 140 | return *reinterpret_cast*>( opaque ); 141 | } 142 | }; 143 | 144 | template 145 | struct FromOpaque 146 | { 147 | static CallbackArray& get(void** opaque) 148 | { 149 | return *reinterpret_cast*>( *opaque ); 150 | } 151 | }; 152 | 153 | namespace detail 154 | { 155 | template 156 | ArgType &&converterForNullToString(ArgType &&arg) 157 | { 158 | return std::forward(arg); 159 | } 160 | 161 | template <> 162 | inline const char * &&converterForNullToString(const char * &&str) 163 | { 164 | static const char* empty = ""; 165 | return std::forward(str == nullptr ? empty : str); 166 | } 167 | } 168 | 169 | template 170 | struct CallbackWrapper; 171 | 172 | // We assume that any callback will take a void*/void** opaque as its first parameter. 173 | // We intercept this parameter, and use it to fetch the list of user provided 174 | // functions. Once we know what function to call, we forward the rest of the 175 | // parameters. 176 | // Using partial specialization also allows us to get the list of the expected 177 | // callback parameters automatically, rather than having to specify them. 178 | template 179 | struct CallbackWrapper 180 | { 181 | using Wrapped = Ret(*)(Opaque, Args...); 182 | 183 | template 184 | static Wrapped wrap(CallbackArray& callbacks, Func&& func) 185 | { 186 | callbacks[Idx] = std::unique_ptr>( new CallbackHandler( std::forward( func ) ) ); 187 | return [](Opaque opaque, Args... args) -> Ret { 188 | auto& callbacks = FromOpaque::get( opaque ); 189 | assert(callbacks[Idx] != nullptr); 190 | auto cbHandler = static_cast*>( callbacks[Idx].get() ); 191 | return cbHandler->func( detail::converterForNullToString(std::forward(args))... ); 192 | }; 193 | } 194 | 195 | // Overload to handle null callbacks at build time. 196 | // We could try to compare any "Func" against nullptr at runtime, though 197 | // since Func is a template type, which roughly has to satisfy the "Callable" concept, 198 | // it could be an instance of a function object, which doesn't compare nicely against nullptr. 199 | // Using the specialization at build time is easier and performs better. 200 | template 201 | static std::nullptr_t wrap(CallbackArray&, std::nullptr_t) 202 | { 203 | return nullptr; 204 | } 205 | }; 206 | 207 | struct VaCopy 208 | { 209 | VaCopy(va_list va_) 210 | { 211 | va_copy( va, va_ ); 212 | } 213 | 214 | ~VaCopy() 215 | { 216 | va_end( va ); 217 | } 218 | 219 | VaCopy( const VaCopy& ) = delete; 220 | VaCopy& operator=(const VaCopy& ) = delete; 221 | VaCopy( VaCopy&& ) = delete; 222 | VaCopy& operator=( VaCopy&& ) = delete; 223 | 224 | va_list va; 225 | }; 226 | 227 | namespace imem 228 | { 229 | // libvlc_media_new_callbacks is a bit different from other libvlc's callbacks. 230 | // Instead of always receiving the initialy provided void* opaque, the open 231 | // callback is responsible for creating another opaque value, that will be 232 | // passed to read/seek/close. 233 | // Since we use the opaque value to pass a CallbackArray instance, we need 234 | // a way to keep the user's opaque value, and replace it by our own. 235 | // The Opaque type is a small boxing helper, that will be used for this purpose. 236 | // In case the OpenCallback is a nullptr, there is no need for boxing, since 237 | // the opaque value will be the inial opaque, provided when calling 238 | // libvlc_media_new_callbacks. 239 | template 240 | struct Opaque 241 | { 242 | CallbackArray* callbacks; 243 | void* userOpaque; 244 | }; 245 | 246 | enum class BoxingStrategy 247 | { 248 | /// No boxing required. 249 | NoBoxing, 250 | /// Used to create the Opaque wrapper and setup pointers 251 | Setup, 252 | /// Unbox CallbackArray/user callback pointers 253 | Unbox, 254 | /// Releases the Opaque, created during Setup 255 | Cleanup, 256 | }; 257 | 258 | /// Base case: this is an identity function. 259 | template 260 | struct GuessBoxingStrategy 261 | { 262 | #if !defined(_MSC_VER) || _MSC_VER >= 1900 263 | static constexpr BoxingStrategy Strategy = Strategy_; 264 | #else 265 | static const BoxingStrategy Strategy = Strategy_; 266 | #endif 267 | }; 268 | 269 | // In case the user provides a nullptr open callback, there's nothing 270 | // to box, as we get the original opaque (which is our CallbackArray*) 271 | template 272 | struct GuessBoxingStrategy 273 | { 274 | #if !defined(_MSC_VER) || _MSC_VER >= 1900 275 | static constexpr BoxingStrategy Strategy = BoxingStrategy::NoBoxing; 276 | #else 277 | static const BoxingStrategy Strategy = BoxingStrategy::NoBoxing; 278 | #endif 279 | }; 280 | 281 | template 282 | struct BoxOpaque; 283 | 284 | // This specialization is our base case. It unboxes an Opaque pointer 285 | // to a CallbackArray, of a user provided opaque. 286 | template 287 | struct BoxOpaque 288 | { 289 | template 290 | BoxOpaque(void* ptr, Args...) : m_ptr( reinterpret_cast*>( ptr ) ) {} 291 | // Assume the cast operator will be used when calling the callback. 292 | // In this case, decay the boxed type to the user provided value 293 | operator void*() { return m_ptr->userOpaque; } 294 | CallbackArray& callbacks() { return *(m_ptr->callbacks); } 295 | Opaque* m_ptr; 296 | }; 297 | 298 | // This specialization is used to hook the user provided opaque variable, 299 | // and store it in an Opaque wrapper. 300 | // We use RAII like code to prepare the hooking before the actual callback 301 | // call, and finilize the hooking once the callback has been called, 302 | // and has provided us with a value, store in the address stored in m_userOpaque. 303 | // This makes us receive all parameters so we can extract the void** param. 304 | // As a drawback, all other overloads have to receive those parameters, and 305 | // ignore them. 306 | template 307 | struct BoxOpaque 308 | : public BoxOpaque 309 | { 310 | using Base = BoxOpaque; 311 | template 312 | BoxOpaque(void* ptr, void** userOpaque, Args...) 313 | : Base( new Opaque ) 314 | , m_userOpaque( userOpaque ) 315 | { 316 | Base::m_ptr->callbacks = reinterpret_cast*>( ptr ); 317 | } 318 | operator void*() { return Base::m_ptr; } 319 | 320 | ~BoxOpaque() 321 | { 322 | // Store the user provided callback 323 | Base::m_ptr->userOpaque = *m_userOpaque; 324 | // And replace it with our boxed type 325 | *m_userOpaque = Base::m_ptr; 326 | } 327 | 328 | void** m_userOpaque; 329 | }; 330 | 331 | // This is a special case which is only used to delete the Opaque type, 332 | // created by the BoxingStrategy::Setup specialization 333 | template 334 | struct BoxOpaque 335 | : public BoxOpaque 336 | { 337 | using Base = BoxOpaque; 338 | template 339 | BoxOpaque(void* ptr, Args...) : BoxOpaque( ptr ) {} 340 | ~BoxOpaque() { delete Base::m_ptr; } 341 | }; 342 | 343 | // When no boxing is required, enfore the user provided callback as a nullptr. 344 | // Otherwise, we assume there is no Opaque wrapper, and therefore the 345 | // pointer we receive already is our CallbackOwner instance. 346 | template 347 | struct BoxOpaque 348 | { 349 | template 350 | BoxOpaque(void* ptr, Args...) : m_ptr( reinterpret_cast*>( ptr ) ) {} 351 | operator void*() { return nullptr; } 352 | CallbackArray& callbacks() { return *m_ptr; } 353 | 354 | CallbackArray* m_ptr; 355 | }; 356 | 357 | template 358 | struct CallbackWrapper; 359 | 360 | // Reimplement the general case CallbackWrapper for imem specific purpose. 361 | // This could be refactored away, if we delegate the actual call to the BoxOpaque 362 | // wrapper. 363 | // For this CallbackWrapper implementation, the BoxOpaque is always passed, 364 | // and will decay to a void* using a type conversion operator. 365 | // General-case doesn't need this, since we do not forward the opaque values. 366 | // This difference leads to a different call, and the need for 2 implementations. 367 | // Delegating the call to the Opaque class could remove this requirement, 368 | // and forward the user provided opaque only when it's actually used 369 | // However, this would mean that depending on the OpenCb type, the expected 370 | // prototype of Read/Seek/Close cb would change, which might not be ideal. 371 | // Using CallbackWrapper type is preferable to wrapping user provided callbacks 372 | // with lambdas, as we would lose the ability to detect when nullptr is provided, 373 | // so we'd have VLC call a no-op function, while the nullptr wrap() specialization 374 | // takes care of this. 375 | template 376 | struct CallbackWrapper 377 | { 378 | using Wrapped = Ret(*)(void*, Args...); 379 | 380 | template 381 | static Wrapped wrap(CallbackArray& callbacks, Func&& func) 382 | { 383 | callbacks[Idx] = std::unique_ptr>( new CallbackHandler( std::forward( func ) ) ); 384 | return [](void* opaque, Args... args) -> Ret { 385 | auto boxed = BoxOpaque( opaque, std::forward( args )... ); 386 | assert(boxed.callbacks()[Idx] != nullptr ); 387 | auto cbHandler = static_cast*>( boxed.callbacks()[Idx].get() ); 388 | return cbHandler->func( boxed, std::forward(args)... ); 389 | }; 390 | } 391 | 392 | template 393 | static std::nullptr_t wrap(CallbackArray&, std::nullptr_t) 394 | { 395 | return nullptr; 396 | } 397 | }; 398 | } //namespace imem 399 | } 400 | 401 | #endif 402 | -------------------------------------------------------------------------------- /vlcpp/structures.hpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | * structures.hpp: LibVLC++ structures 3 | ***************************************************************************** 4 | * Copyright © 2015 libvlcpp authors & VideoLAN 5 | * 6 | * Authors: Alexey Sokolov 7 | * Hugo Beauzée-Luyssen 8 | * 9 | * This program is free software; you can redistribute it and/or modify 10 | * it under the terms of the GNU Lesser General Public License as published by 11 | * the Free Software Foundation; either version 2.1 of the License, or 12 | * (at your option) any later version. 13 | * 14 | * This program is distributed in the hope that it will be useful, 15 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 | * GNU Lesser General Public License for more details. 18 | * 19 | * You should have received a copy of the GNU Lesser General Public License 20 | * along with this program; if not, write to the Free Software 21 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. 22 | *****************************************************************************/ 23 | 24 | #ifndef LIBVLC_CXX_STRUCTURES_H 25 | #define LIBVLC_CXX_STRUCTURES_H 26 | 27 | #include 28 | 29 | #include "common.hpp" 30 | #include "Picture.hpp" 31 | 32 | //FIXME: 33 | //Should we make the constructors private again and implement our own vector allocator? 34 | 35 | namespace VLC 36 | { 37 | 38 | /// 39 | /// \brief The ModuleDescription class describes a module 40 | /// 41 | class ModuleDescription 42 | { 43 | public: 44 | /// 45 | /// \brief name Returns the module name 46 | /// 47 | const std::string& name() const 48 | { 49 | return m_name; 50 | } 51 | 52 | /// 53 | /// \brief shortname Returns the module short name 54 | /// 55 | const std::string& shortname() const 56 | { 57 | return m_shortname; 58 | } 59 | 60 | /// 61 | /// \brief longname returns the module long name 62 | /// 63 | const std::string& longname() const 64 | { 65 | return m_longname; 66 | } 67 | 68 | /// 69 | /// \brief help Returns a basic help string for this module 70 | /// 71 | const std::string& help() const 72 | { 73 | return m_help; 74 | } 75 | 76 | explicit ModuleDescription( libvlc_module_description_t* c ) 77 | { 78 | if ( c->psz_name != nullptr ) 79 | m_name = c->psz_name; 80 | if ( c->psz_shortname != nullptr ) 81 | m_shortname = c->psz_shortname; 82 | if ( c->psz_longname != nullptr ) 83 | m_longname = c->psz_longname; 84 | if ( c->psz_help != nullptr ) 85 | m_help = c->psz_help; 86 | } 87 | 88 | private: 89 | std::string m_name; 90 | std::string m_shortname; 91 | std::string m_longname; 92 | std::string m_help; 93 | }; 94 | 95 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(4, 0, 0, 0) 96 | 97 | /// 98 | /// \brief The MediaTrack class describes a track 99 | /// 100 | class MediaTrack : public Internal 101 | { 102 | public: 103 | /// 104 | /// \brief The Type enum indicates the type of a track 105 | /// 106 | enum class Type 107 | { 108 | Unknown = libvlc_track_unknown, 109 | /// Audio track 110 | Audio = libvlc_track_audio, 111 | /// Video track 112 | Video = libvlc_track_video, 113 | /// Subtitle track (also called SPU sometimes) 114 | Subtitle = libvlc_track_text, 115 | }; 116 | 117 | /// 118 | /// \brief The Orientation enum indicates the orientation of a video 119 | /// 120 | enum class Orientation 121 | { 122 | TopLeft, 123 | TopRight, 124 | BottomLeft, 125 | BottomRight, 126 | LeftTop, 127 | LeftBottom, 128 | RightTop, 129 | RightBottom 130 | }; 131 | 132 | /// 133 | /// \brief The Projection enum indicates the projection of a video 134 | /// 135 | enum class Projection 136 | { 137 | Rectangular, 138 | /// 360 spherical 139 | Equirectangular, 140 | CubemapLayoutStandard = 0x100 141 | }; 142 | 143 | #if !defined(_MSC_VER) || _MSC_VER >= 1900 144 | constexpr static Type Unknown = Type::Unknown; 145 | constexpr static Type Audio = Type::Audio; 146 | constexpr static Type Video = Type::Video; 147 | constexpr static Type Subtitle = Type::Subtitle; 148 | #else 149 | const static Type Unknown = Type::Unknown; 150 | const static Type Audio = Type::Audio; 151 | const static Type Video = Type::Video; 152 | const static Type Subtitle = Type::Subtitle; 153 | #endif 154 | 155 | /// 156 | /// \brief codec Returns the codec as a fourcc 157 | /// 158 | /// This is the fourcc will use to select a codec, but it might be an 159 | /// interpretation of the original fourcc. 160 | /// \see originalFourCC() 161 | /// 162 | uint32_t codec() const 163 | { 164 | return m_obj->i_codec; 165 | } 166 | 167 | /// 168 | /// \brief originalFourCC Returns the fourcc as found in the file. 169 | /// 170 | /// VLC might chose to use a different fourcc internally. 171 | /// For instance, AVC1 & H264 fourcc are (almost?) identical. VLC would 172 | /// use H264 as the codec/fourcc, and store AVC1/H264 as the original fourcc 173 | /// 174 | uint32_t originalFourCC() const 175 | { 176 | return m_obj->i_original_fourcc; 177 | } 178 | 179 | /// 180 | /// \brief id The track internal ID. 181 | /// 182 | /// This can't be assume to grow one by one monotonically. 183 | /// 184 | int32_t id() const 185 | { 186 | return m_obj->i_id; 187 | } 188 | 189 | /// 190 | /// \brief type The track type 191 | /// 192 | /// \see MediaTrack::Type 193 | /// 194 | Type type() const 195 | { 196 | return static_cast( m_obj->i_type ); 197 | } 198 | 199 | /// 200 | /// \brief profile This track profile 201 | /// 202 | /// This might or might not be set, depending on the codec. 203 | /// 204 | int32_t profile() const 205 | { 206 | return m_obj->i_profile; 207 | } 208 | 209 | /// 210 | /// \brief level This track level 211 | /// 212 | /// This might or might not be set, depending on the codec 213 | /// 214 | int32_t level() const 215 | { 216 | return m_obj->i_level; 217 | } 218 | 219 | /// 220 | /// \brief bitrate This track bitrate, in bytes per second 221 | /// \return 222 | /// 223 | uint32_t bitrate() const 224 | { 225 | return m_obj->i_bitrate; 226 | } 227 | 228 | /// 229 | /// \brief language This track language, if available. 230 | /// 231 | std::string language() const 232 | { 233 | return m_obj->psz_language ? m_obj->psz_language : ""; 234 | } 235 | 236 | /// 237 | /// \brief description This track description 238 | /// 239 | std::string description() const 240 | { 241 | return m_obj->psz_description ? m_obj->psz_description : ""; 242 | } 243 | 244 | //////////////////////////////////////////////////////////////////////////// 245 | /// Audio specific 246 | //////////////////////////////////////////////////////////////////////////// 247 | 248 | /// 249 | /// \brief channels This track number of channels 250 | /// 251 | uint32_t channels() const 252 | { 253 | assert( m_obj->i_type == libvlc_track_audio ); 254 | return m_obj->audio->i_channels; 255 | } 256 | 257 | /// 258 | /// \brief rate This track samplerate, in hertz (Hz) 259 | /// 260 | uint32_t rate() const 261 | { 262 | assert( m_obj->i_type == libvlc_track_audio ); 263 | return m_obj->audio->i_rate; 264 | } 265 | 266 | //////////////////////////////////////////////////////////////////////////// 267 | // Video specific 268 | //////////////////////////////////////////////////////////////////////////// 269 | 270 | /// 271 | /// \brief height This track video height 272 | /// 273 | uint32_t height() const 274 | { 275 | assert( m_obj->i_type == libvlc_track_video ); 276 | return m_obj->video->i_height; 277 | } 278 | 279 | /// 280 | /// \brief width This track video width 281 | /// 282 | uint32_t width() const 283 | { 284 | assert( m_obj->i_type == libvlc_track_video ); 285 | return m_obj->video->i_width; 286 | } 287 | 288 | /// 289 | /// \brief sarNum This track aspect ratio numerator 290 | /// 291 | /// \see sarDen 292 | /// 293 | uint32_t sarNum() const 294 | { 295 | assert( m_obj->i_type == libvlc_track_video ); 296 | return m_obj->video->i_sar_num; 297 | } 298 | 299 | /// 300 | /// \brief sarDen This track aspect ratio denominator 301 | /// 302 | /// \see sarNum 303 | /// 304 | uint32_t sarDen() const 305 | { 306 | assert( m_obj->i_type == libvlc_track_video ); 307 | return m_obj->video->i_sar_den; 308 | } 309 | 310 | /// 311 | /// \brief fpsNum This track frame per second numerator 312 | /// 313 | /// \see fpsDen 314 | /// 315 | uint32_t fpsNum() const 316 | { 317 | assert( m_obj->i_type == libvlc_track_video ); 318 | return m_obj->video->i_frame_rate_num; 319 | } 320 | 321 | /// 322 | /// \brief fpsDen This track frame per second denominator 323 | /// 324 | /// \see fpsNum 325 | /// 326 | uint32_t fpsDen() const 327 | { 328 | assert( m_obj->i_type == libvlc_track_video ); 329 | return m_obj->video->i_frame_rate_den; 330 | } 331 | 332 | /// 333 | /// \brief Orientation 334 | /// 335 | /// \see orientation 336 | /// 337 | Orientation orientation() const 338 | { 339 | assert( m_obj->i_type == libvlc_track_video ); 340 | return static_cast( m_obj->video->i_orientation ); 341 | } 342 | 343 | /// 344 | /// \brief Projection 345 | /// 346 | /// \see projection 347 | /// 348 | Projection projection() const 349 | { 350 | assert( m_obj->i_type == libvlc_track_video ); 351 | return static_cast( m_obj->video->i_projection ); 352 | } 353 | 354 | std::string idStr() const 355 | { 356 | return m_obj->psz_id ? m_obj->psz_id : ""; 357 | } 358 | 359 | bool idStable() const 360 | { 361 | return m_obj->id_stable; 362 | } 363 | 364 | std::string name() const 365 | { 366 | return m_obj->psz_name ? m_obj->psz_name : ""; 367 | } 368 | 369 | bool selected() const 370 | { 371 | return m_obj->selected; 372 | } 373 | 374 | //////////////////////////////////////////////////////////////////////////// 375 | // Subtitles specific 376 | //////////////////////////////////////////////////////////////////////////// 377 | 378 | /// 379 | /// \brief encoding Subtitles text encoding 380 | /// 381 | std::string encoding() const 382 | { 383 | assert( m_obj->i_type == libvlc_track_text ); 384 | return m_obj->subtitle->psz_encoding ? m_obj->subtitle->psz_encoding : ""; 385 | } 386 | 387 | /// 388 | /// \brief MediaTrack Construct a libvlc_media_track_t representation 389 | /// \param c A valid media track 390 | /// 391 | /// \note The track will he held and released automatically. 392 | /// 393 | explicit MediaTrack(libvlc_media_track_t* c) 394 | : Internal{ libvlc_media_track_hold( c ), libvlc_media_track_release } 395 | { 396 | } 397 | }; 398 | 399 | #else 400 | 401 | /// 402 | /// \brief The MediaTrack class describes a track 403 | /// 404 | class MediaTrack 405 | { 406 | public: 407 | /// 408 | /// \brief The Type enum indicates the type of a track 409 | /// 410 | enum class Type 411 | { 412 | Unknown = libvlc_track_unknown, 413 | /// Audio track 414 | Audio = libvlc_track_audio, 415 | /// Video track 416 | Video = libvlc_track_video, 417 | /// Subtitle track (also called SPU sometimes) 418 | Subtitle = libvlc_track_text, 419 | }; 420 | 421 | /// 422 | /// \brief The Orientation enum indicates the orientation of a video 423 | /// 424 | enum class Orientation 425 | { 426 | TopLeft, 427 | TopRight, 428 | BottomLeft, 429 | BottomRight, 430 | LeftTop, 431 | LeftBottom, 432 | RightTop, 433 | RightBottom 434 | }; 435 | 436 | /// 437 | /// \brief The Projection enum indicates the projection of a video 438 | /// 439 | enum class Projection 440 | { 441 | Rectangular, 442 | /// 360 spherical 443 | Equirectangular, 444 | CubemapLayoutStandard = 0x100 445 | }; 446 | 447 | #if !defined(_MSC_VER) || _MSC_VER >= 1900 448 | constexpr static Type Unknown = Type::Unknown; 449 | constexpr static Type Audio = Type::Audio; 450 | constexpr static Type Video = Type::Video; 451 | constexpr static Type Subtitle = Type::Subtitle; 452 | #else 453 | const static Type Unknown = Type::Unknown; 454 | const static Type Audio = Type::Audio; 455 | const static Type Video = Type::Video; 456 | const static Type Subtitle = Type::Subtitle; 457 | #endif 458 | 459 | /// 460 | /// \brief codec Returns the codec as a fourcc 461 | /// 462 | /// This is the fourcc will use to select a codec, but it might be an 463 | /// interpretation of the original fourcc. 464 | /// \see originalFourCC() 465 | /// 466 | uint32_t codec() const 467 | { 468 | return m_codec; 469 | } 470 | 471 | /// 472 | /// \brief originalFourCC Returns the fourcc as found in the file. 473 | /// 474 | /// VLC might chose to use a different fourcc internally. 475 | /// For instance, AVC1 & H264 fourcc are (almost?) identical. VLC would 476 | /// use H264 as the codec/fourcc, and store AVC1/H264 as the original fourcc 477 | /// 478 | uint32_t originalFourCC() const 479 | { 480 | return m_originalFourcc; 481 | } 482 | 483 | /// 484 | /// \brief id The track internal ID. 485 | /// 486 | /// This can't be assume to grow one by one monotonically. 487 | /// 488 | int32_t id() const 489 | { 490 | return m_id; 491 | } 492 | 493 | /// 494 | /// \brief type The track type 495 | /// 496 | /// \see MediaTrack::Type 497 | /// 498 | Type type() const 499 | { 500 | return m_type; 501 | } 502 | 503 | /// 504 | /// \brief profile This track profile 505 | /// 506 | /// This might or might not be set, depending on the codec. 507 | /// 508 | int32_t profile() const 509 | { 510 | return m_profile; 511 | } 512 | 513 | /// 514 | /// \brief level This track level 515 | /// 516 | /// This might or might not be set, depending on the codec 517 | /// 518 | int32_t level() const 519 | { 520 | return m_level; 521 | } 522 | 523 | /// 524 | /// \brief bitrate This track bitrate, in bytes per second 525 | /// \return 526 | /// 527 | uint32_t bitrate() const 528 | { 529 | return m_bitrate; 530 | } 531 | 532 | /// 533 | /// \brief language This track language, if available. 534 | /// 535 | const std::string& language() const 536 | { 537 | return m_language; 538 | } 539 | 540 | /// 541 | /// \brief description This track description 542 | /// 543 | const std::string& description() const 544 | { 545 | return m_description; 546 | } 547 | 548 | //////////////////////////////////////////////////////////////////////////// 549 | /// Audio specific 550 | //////////////////////////////////////////////////////////////////////////// 551 | 552 | /// 553 | /// \brief channels This track number of channels 554 | /// 555 | uint32_t channels() const 556 | { 557 | return m_channels; 558 | } 559 | 560 | /// 561 | /// \brief rate This track samplerate, in hertz (Hz) 562 | /// 563 | uint32_t rate() const 564 | { 565 | return m_rate; 566 | } 567 | 568 | //////////////////////////////////////////////////////////////////////////// 569 | // Video specific 570 | //////////////////////////////////////////////////////////////////////////// 571 | 572 | /// 573 | /// \brief height This track video height 574 | /// 575 | uint32_t height() const 576 | { 577 | return m_height; 578 | } 579 | 580 | /// 581 | /// \brief width This track video width 582 | /// 583 | uint32_t width() const 584 | { 585 | return m_width; 586 | } 587 | 588 | /// 589 | /// \brief sarNum This track aspect ratio numerator 590 | /// 591 | /// \see sarDen 592 | /// 593 | uint32_t sarNum() const 594 | { 595 | return m_sarNum; 596 | } 597 | 598 | /// 599 | /// \brief sarDen This track aspect ratio denominator 600 | /// 601 | /// \see sarNum 602 | /// 603 | uint32_t sarDen() const 604 | { 605 | return m_sarDen; 606 | } 607 | 608 | /// 609 | /// \brief fpsNum This track frame per second numerator 610 | /// 611 | /// \see fpsDen 612 | /// 613 | uint32_t fpsNum() const 614 | { 615 | return m_fpsNum; 616 | } 617 | 618 | /// 619 | /// \brief fpsDen This track frame per second denominator 620 | /// 621 | /// \see fpsNum 622 | /// 623 | uint32_t fpsDen() const 624 | { 625 | return m_fpsDen; 626 | } 627 | 628 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 629 | /// 630 | /// \brief Orientation 631 | /// 632 | /// \see orientation 633 | /// 634 | Orientation orientation() const 635 | { 636 | return m_orientation; 637 | } 638 | 639 | /// 640 | /// \brief Projection 641 | /// 642 | /// \see projection 643 | /// 644 | Projection projection() const 645 | { 646 | return m_projection; 647 | } 648 | #endif 649 | 650 | //////////////////////////////////////////////////////////////////////////// 651 | // Subtitles specific 652 | //////////////////////////////////////////////////////////////////////////// 653 | 654 | /// 655 | /// \brief encoding Subtitles text encoding 656 | /// 657 | const std::string& encoding() const 658 | { 659 | return m_encoding; 660 | } 661 | 662 | explicit MediaTrack(libvlc_media_track_t* c) 663 | : m_codec( c->i_codec ) 664 | , m_originalFourcc( c->i_original_fourcc ) 665 | , m_id( c->i_id ) 666 | , m_profile( c->i_profile ) 667 | , m_level( c->i_level ) 668 | , m_bitrate( c->i_bitrate ) 669 | { 670 | if ( c->psz_language != nullptr ) 671 | m_language = c->psz_language; 672 | if ( c->psz_description != nullptr ) 673 | m_description = c->psz_description; 674 | switch ( c->i_type ) 675 | { 676 | case libvlc_track_audio: 677 | m_type = Audio; 678 | m_channels = c->audio->i_channels; 679 | m_rate = c->audio->i_rate; 680 | break; 681 | case libvlc_track_video: 682 | m_type = Video; 683 | m_height = c->video->i_height; 684 | m_width = c->video->i_width; 685 | m_sarNum = c->video->i_sar_num; 686 | m_sarDen = c->video->i_sar_den; 687 | m_fpsNum = c->video->i_frame_rate_num; 688 | m_fpsDen = c->video->i_frame_rate_den; 689 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 690 | m_orientation = static_cast( c->video->i_orientation ); 691 | m_projection = static_cast( c->video->i_projection ); 692 | #endif 693 | break; 694 | case libvlc_track_text: 695 | m_type = Subtitle; 696 | if ( c->subtitle->psz_encoding != nullptr ) 697 | m_encoding = c->subtitle->psz_encoding; 698 | break; 699 | case libvlc_track_unknown: 700 | default: 701 | m_type = Unknown; 702 | break; 703 | } 704 | } 705 | 706 | private: 707 | uint32_t m_codec; 708 | uint32_t m_originalFourcc; 709 | uint32_t m_id; 710 | Type m_type; 711 | int32_t m_profile; 712 | int32_t m_level; 713 | uint32_t m_bitrate; 714 | std::string m_language; 715 | std::string m_description; 716 | // Audio 717 | uint32_t m_channels; 718 | uint32_t m_rate; 719 | // Video 720 | uint32_t m_height; 721 | uint32_t m_width; 722 | uint32_t m_sarNum; 723 | uint32_t m_sarDen; 724 | uint32_t m_fpsNum; 725 | uint32_t m_fpsDen; 726 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 727 | Orientation m_orientation; 728 | Projection m_projection; 729 | #endif 730 | // Subtitles 731 | std::string m_encoding; 732 | }; 733 | 734 | #endif 735 | 736 | /// 737 | /// \brief The AudioOutputDescription class describes an audio output module 738 | /// 739 | class AudioOutputDescription 740 | { 741 | public: 742 | /// 743 | /// \brief name The module name 744 | /// 745 | const std::string& name() const 746 | { 747 | return m_name; 748 | } 749 | 750 | /// 751 | /// \brief description The module description 752 | /// 753 | const std::string& description() const 754 | { 755 | return m_description; 756 | } 757 | 758 | explicit AudioOutputDescription( libvlc_audio_output_t* c ) 759 | { 760 | if ( c->psz_name != nullptr ) 761 | m_name = c->psz_name; 762 | if ( c->psz_description != nullptr ) 763 | m_description = c->psz_description; 764 | } 765 | 766 | private: 767 | std::string m_name; 768 | std::string m_description; 769 | }; 770 | 771 | /// 772 | /// \brief The AudioOutputDeviceDescription class describes an audio device, as seen 773 | /// by an audio output module 774 | /// 775 | class AudioOutputDeviceDescription 776 | { 777 | public: 778 | /**< Device identifier string */ 779 | const std::string& device() const 780 | { 781 | return m_device; 782 | } 783 | 784 | /**< User-friendly device description */ 785 | const std::string& description() const 786 | { 787 | return m_description; 788 | } 789 | 790 | explicit AudioOutputDeviceDescription( libvlc_audio_output_device_t* d ) 791 | { 792 | if ( d->psz_device != nullptr ) 793 | m_device = d->psz_device; 794 | if ( d->psz_description != nullptr ) 795 | m_description = d->psz_description; 796 | } 797 | 798 | private: 799 | std::string m_device; 800 | std::string m_description; 801 | }; 802 | 803 | #if LIBVLC_VERSION_INT < LIBVLC_VERSION(4, 0, 0, 0) 804 | /// 805 | /// \brief The TrackDescription class describes a track 806 | /// 807 | class TrackDescription 808 | { 809 | public: 810 | /// 811 | /// \brief id The track id 812 | /// 813 | int id() const 814 | { 815 | return m_id; 816 | } 817 | 818 | /// 819 | /// \brief name The track name 820 | /// 821 | const std::string& name() const 822 | { 823 | return m_name; 824 | } 825 | 826 | explicit TrackDescription( libvlc_track_description_t* c ) 827 | : m_id( c->i_id ) 828 | { 829 | if ( c->psz_name != nullptr ) 830 | m_name = c->psz_name; 831 | } 832 | 833 | private: 834 | int m_id; 835 | std::string m_name; 836 | }; 837 | #endif 838 | 839 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 840 | /// 841 | /// \brief The TitleDescription class describes a title 842 | /// 843 | class TitleDescription 844 | { 845 | public: 846 | /// 847 | /// \brief duration The title duration in (ms) 848 | /// 849 | int64_t duration() const 850 | { 851 | return m_duration; 852 | } 853 | 854 | /// 855 | /// \brief name The title name 856 | /// 857 | const std::string& name() const 858 | { 859 | return m_name; 860 | } 861 | 862 | /// 863 | /// \brief name Is the title a menu? 864 | /// 865 | bool isMenu() const 866 | { 867 | return ( m_flags & libvlc_title_menu ) != 0; 868 | } 869 | 870 | bool isInteractive() const 871 | { 872 | return ( m_flags & libvlc_title_interactive ) != 0; 873 | } 874 | 875 | explicit TitleDescription( const libvlc_title_description_t* c ) 876 | : m_duration( c->i_duration ), m_flags( c->i_flags ) 877 | { 878 | if ( c->psz_name != nullptr ) 879 | m_name = c->psz_name; 880 | } 881 | 882 | private: 883 | int64_t m_duration; 884 | std::string m_name; 885 | int m_flags; 886 | }; 887 | 888 | /// 889 | /// \brief The ChapterDescription class describes a chapter 890 | /// 891 | class ChapterDescription 892 | { 893 | public: 894 | /// 895 | /// \brief timeoffset The chapter start time in (ms) 896 | /// 897 | int64_t starttime() const 898 | { 899 | return m_starttime; 900 | } 901 | 902 | /// 903 | /// \brief duration The chapter duration in (ms) 904 | /// 905 | int64_t duration() const 906 | { 907 | return m_duration; 908 | } 909 | 910 | /// 911 | /// \brief name The chapter name 912 | /// 913 | const std::string& name() const 914 | { 915 | return m_name; 916 | } 917 | 918 | explicit ChapterDescription( libvlc_chapter_description_t* c ) 919 | : m_duration( c->i_duration ), m_starttime( c->i_time_offset ) 920 | { 921 | if ( c->psz_name != nullptr ) 922 | m_name = c->psz_name; 923 | } 924 | 925 | private: 926 | int64_t m_duration, m_starttime; 927 | std::string m_name; 928 | }; 929 | #endif 930 | 931 | #if LIBVLC_VERSION_INT >= LIBVLC_VERSION(3, 0, 0, 0) 932 | /// 933 | /// \brief C++ Type wrapper for libvlc_media_slave_t 934 | /// 935 | class MediaSlave 936 | { 937 | public: 938 | /// 939 | /// Type of a media slave: subtitle or audio. 940 | /// 941 | enum class Type 942 | { 943 | Subtitle = libvlc_media_slave_type_subtitle, 944 | Audio = libvlc_media_slave_type_audio 945 | }; 946 | 947 | MediaSlave( libvlc_media_slave_t *m ) 948 | : m_type( static_cast( m->i_type ) ) 949 | , m_priority( m->i_priority ) 950 | , m_uri( m->psz_uri ) 951 | { 952 | } 953 | 954 | public: 955 | Type type() const 956 | { 957 | return m_type; 958 | } 959 | 960 | unsigned priority() const 961 | { 962 | return m_priority; 963 | } 964 | 965 | const std::string& uri() const 966 | { 967 | return m_uri; 968 | } 969 | 970 | private: 971 | Type m_type; 972 | unsigned int m_priority; 973 | std::string m_uri; 974 | }; 975 | 976 | 977 | /// 978 | /// \brief C++ Type wrapper for libvlc_video_viewpoint_t 979 | /// 980 | class VideoViewpoint : public libvlc_video_viewpoint_t 981 | { 982 | public: 983 | VideoViewpoint( float yaw, float pitch, float roll, float fieldOfView ) 984 | { 985 | f_yaw = yaw; 986 | f_pitch = pitch; 987 | f_roll = roll; 988 | f_field_of_view = fieldOfView; 989 | } 990 | 991 | public: 992 | float yaw() const 993 | { 994 | return f_yaw; 995 | } 996 | 997 | float pitch() const 998 | { 999 | return f_pitch; 1000 | } 1001 | 1002 | float roll() const 1003 | { 1004 | return f_roll; 1005 | } 1006 | 1007 | float field_of_view() const 1008 | { 1009 | return f_field_of_view; 1010 | } 1011 | }; 1012 | 1013 | class RendererDiscovererDescription 1014 | { 1015 | public: 1016 | explicit RendererDiscovererDescription( const libvlc_rd_description_t* d ) 1017 | { 1018 | if (d->psz_name != nullptr) 1019 | m_name = d->psz_name; 1020 | if (d->psz_longname != nullptr) 1021 | m_longName = d->psz_longname; 1022 | } 1023 | 1024 | const std::string& name() const 1025 | { 1026 | return m_name; 1027 | } 1028 | 1029 | const std::string& longName() const 1030 | { 1031 | return m_longName; 1032 | } 1033 | 1034 | private: 1035 | std::string m_name; 1036 | std::string m_longName; 1037 | }; 1038 | 1039 | #endif 1040 | 1041 | } // namespace VLC 1042 | #endif 1043 | -------------------------------------------------------------------------------- /vlcpp/vlc.hpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | * vlc.hpp: Main VLC++ header. 3 | ***************************************************************************** 4 | * Copyright © 2015 libvlcpp authors & VideoLAN 5 | * 6 | * Authors: Alexey Sokolov 7 | * Hugo Beauzée-Luyssen 8 | * 9 | * This program is free software; you can redistribute it and/or modify 10 | * it under the terms of the GNU Lesser General Public License as published by 11 | * the Free Software Foundation; either version 2.1 of the License, or 12 | * (at your option) any later version. 13 | * 14 | * This program is distributed in the hope that it will be useful, 15 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 | * GNU Lesser General Public License for more details. 18 | * 19 | * You should have received a copy of the GNU Lesser General Public License 20 | * along with this program; if not, write to the Free Software 21 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. 22 | *****************************************************************************/ 23 | 24 | #ifndef LIBVLC_CXX_VLC_H 25 | #define LIBVLC_CXX_VLC_H 26 | 27 | #include "Instance.hpp" 28 | #include "Equalizer.hpp" 29 | #include "MediaListPlayer.hpp" 30 | #include "MediaDiscoverer.hpp" 31 | #include "Picture.hpp" 32 | #include "Media.hpp" 33 | #include "MediaList.hpp" 34 | #include "RendererDiscoverer.hpp" 35 | #include "MediaPlayer.hpp" 36 | #include "MediaLibrary.hpp" 37 | #include "EventManager.hpp" 38 | #include "structures.hpp" 39 | 40 | #endif 41 | --------------------------------------------------------------------------------