pax_global_header00006660000000000000000000000064131703036520014512gustar00rootroot0000000000000052 comment=1ea472870b7f72fe17d362dffcd71a0b66fbe320 gnome-mpv-0.13/000077500000000000000000000000001317030365200133425ustar00rootroot00000000000000gnome-mpv-0.13/.github/000077500000000000000000000000001317030365200147025ustar00rootroot00000000000000gnome-mpv-0.13/.github/CONTRIBUTING.md000066400000000000000000000013441317030365200171350ustar00rootroot00000000000000Reporting Bugs ============== - Make sure you're using the latest release. - If possible, also check if the problem has already been fixed in git master. - Don't report multiple unrelated/barely related bugs in one issue. - Attach a log file. - You can make gnome-mpv print log messages by running `G_MESSAGES_DEBUG=all gnome-mpv` - If the issue involves crashing, include a backtrace in the report. - You can create a backtrace by running `gdb -ex 'set pagination off' -ex run -ex bt gnome-mpv` and perform the action that triggers the crash. - If the issue is a regression, it would be very helpful if you could perform a [bisect](https://git-scm.com/docs/git-bisect) to locate the commit that introduces the regression. gnome-mpv-0.13/.github/ISSUE_TEMPLATE.md000066400000000000000000000001731317030365200174100ustar00rootroot00000000000000Overview Description: Steps to Reproduce: 1. 2. 3. Actual Results: Expected Results: Version: Additional Information: gnome-mpv-0.13/.gitignore000066400000000000000000000014351317030365200153350ustar00rootroot00000000000000# Files generated by autotools /autom4te.cache /aclocal.m4 /compile /configure /configure.sub /config.* /depcomp /install-sh /intltool-* /ltmain.sh /missing /ar-lib /libtool /test-driver /stamp-h1 /m4 Makefile.in.in Makefile.in Makefile config.* po/POTFILES po/stamp-it /po/Makevars.template /po/*~ /po/*.sed /po/*.sin /po/*.header /po/Rules-quot /ABOUT-NLS # Files generated by `make` *.o *.stamp *.la *.so *.dll *.a *.exe *.lo *.log *.trs *.test *.tar.xz .deps/ .libs/ data/*.valid data/gnome-mpv.appdata.xml data/gnome-mpv.desktop data/org.gnome-mpv.gschema.xml data/io.github.GnomeMpv.appdata.xml data/io.github.GnomeMpv.desktop data/io.github.GnomeMpv.gschema.xml po/gnome-mpv.pot po/*.gmo po/.intltool-merge-cache .dirstamp src/gnome-mpv src/authors.h src/marshal.* src/mpris/mpris_gdbus.* gnome-mpv-0.13/AUTHORS000066400000000000000000000004731317030365200144160ustar00rootroot00000000000000# Feel free to add/edit your name below. # The names in this file will be shown in the about dialog. # Format: name # is optional. Connor Duncan Gaurav Narula Harenome Ranaivoarivony Razanajato Michael Heyns Mingye Wang (Arthur2e5) Patrick Griffis Sun gipawu gnome-mpv tista500 xuzhen gnome-mpv-0.13/COPYING000066400000000000000000001045141317030365200144020ustar00rootroot00000000000000 GNU GENERAL PUBLIC LICENSE Version 3, 29 June 2007 Copyright (C) 2007 Free Software Foundation, Inc. Everyone is permitted to copy and distribute verbatim copies of this license document, but changing it is not allowed. Preamble The GNU General Public License is a free, copyleft license for software and other kinds of works. The licenses for most software and other practical works are designed to take away your freedom to share and change the works. By contrast, the GNU General Public License is intended to guarantee your freedom to share and change all versions of a program--to make sure it remains free software for all its users. We, the Free Software Foundation, use the GNU General Public License for most of our software; it applies also to any other work released this way by its authors. You can apply it to your programs, too. When we speak of free software, we are referring to freedom, not price. Our General Public Licenses are designed to make sure that you have the freedom to distribute copies of free software (and charge for them if you wish), that you receive source code or can get it if you want it, that you can change the software or use pieces of it in new free programs, and that you know you can do these things. To protect your rights, we need to prevent others from denying you these rights or asking you to surrender the rights. Therefore, you have certain responsibilities if you distribute copies of the software, or if you modify it: responsibilities to respect the freedom of others. For example, if you distribute copies of such a program, whether gratis or for a fee, you must pass on to the recipients the same freedoms that you received. You must make sure that they, too, receive or can get the source code. And you must show them these terms so they know their rights. Developers that use the GNU GPL protect your rights with two steps: (1) assert copyright on the software, and (2) offer you this License giving you legal permission to copy, distribute and/or modify it. For the developers' and authors' protection, the GPL clearly explains that there is no warranty for this free software. For both users' and authors' sake, the GPL requires that modified versions be marked as changed, so that their problems will not be attributed erroneously to authors of previous versions. Some devices are designed to deny users access to install or run modified versions of the software inside them, although the manufacturer can do so. This is fundamentally incompatible with the aim of protecting users' freedom to change the software. The systematic pattern of such abuse occurs in the area of products for individuals to use, which is precisely where it is most unacceptable. Therefore, we have designed this version of the GPL to prohibit the practice for those products. If such problems arise substantially in other domains, we stand ready to extend this provision to those domains in future versions of the GPL, as needed to protect the freedom of users. Finally, every program is threatened constantly by software patents. States should not allow patents to restrict development and use of software on general-purpose computers, but in those that do, we wish to avoid the special danger that patents applied to a free program could make it effectively proprietary. To prevent this, the GPL assures that patents cannot be used to render the program non-free. The precise terms and conditions for copying, distribution and modification follow. TERMS AND CONDITIONS 0. Definitions. "This License" refers to version 3 of the GNU General Public License. "Copyright" also means copyright-like laws that apply to other kinds of works, such as semiconductor masks. "The Program" refers to any copyrightable work licensed under this License. Each licensee is addressed as "you". "Licensees" and "recipients" may be individuals or organizations. To "modify" a work means to copy from or adapt all or part of the work in a fashion requiring copyright permission, other than the making of an exact copy. The resulting work is called a "modified version" of the earlier work or a work "based on" the earlier work. A "covered work" means either the unmodified Program or a work based on the Program. To "propagate" a work means to do anything with it that, without permission, would make you directly or secondarily liable for infringement under applicable copyright law, except executing it on a computer or modifying a private copy. Propagation includes copying, distribution (with or without modification), making available to the public, and in some countries other activities as well. To "convey" a work means any kind of propagation that enables other parties to make or receive copies. Mere interaction with a user through a computer network, with no transfer of a copy, is not conveying. An interactive user interface displays "Appropriate Legal Notices" to the extent that it includes a convenient and prominently visible feature that (1) displays an appropriate copyright notice, and (2) tells the user that there is no warranty for the work (except to the extent that warranties are provided), that licensees may convey the work under this License, and how to view a copy of this License. If the interface presents a list of user commands or options, such as a menu, a prominent item in the list meets this criterion. 1. Source Code. The "source code" for a work means the preferred form of the work for making modifications to it. "Object code" means any non-source form of a work. A "Standard Interface" means an interface that either is an official standard defined by a recognized standards body, or, in the case of interfaces specified for a particular programming language, one that is widely used among developers working in that language. The "System Libraries" of an executable work include anything, other than the work as a whole, that (a) is included in the normal form of packaging a Major Component, but which is not part of that Major Component, and (b) serves only to enable use of the work with that Major Component, or to implement a Standard Interface for which an implementation is available to the public in source code form. A "Major Component", in this context, means a major essential component (kernel, window system, and so on) of the specific operating system (if any) on which the executable work runs, or a compiler used to produce the work, or an object code interpreter used to run it. The "Corresponding Source" for a work in object code form means all the source code needed to generate, install, and (for an executable work) run the object code and to modify the work, including scripts to control those activities. However, it does not include the work's System Libraries, or general-purpose tools or generally available free programs which are used unmodified in performing those activities but which are not part of the work. For example, Corresponding Source includes interface definition files associated with source files for the work, and the source code for shared libraries and dynamically linked subprograms that the work is specifically designed to require, such as by intimate data communication or control flow between those subprograms and other parts of the work. The Corresponding Source need not include anything that users can regenerate automatically from other parts of the Corresponding Source. The Corresponding Source for a work in source code form is that same work. 2. Basic Permissions. All rights granted under this License are granted for the term of copyright on the Program, and are irrevocable provided the stated conditions are met. This License explicitly affirms your unlimited permission to run the unmodified Program. The output from running a covered work is covered by this License only if the output, given its content, constitutes a covered work. This License acknowledges your rights of fair use or other equivalent, as provided by copyright law. You may make, run and propagate covered works that you do not convey, without conditions so long as your license otherwise remains in force. You may convey covered works to others for the sole purpose of having them make modifications exclusively for you, or provide you with facilities for running those works, provided that you comply with the terms of this License in conveying all material for which you do not control copyright. Those thus making or running the covered works for you must do so exclusively on your behalf, under your direction and control, on terms that prohibit them from making any copies of your copyrighted material outside their relationship with you. Conveying under any other circumstances is permitted solely under the conditions stated below. Sublicensing is not allowed; section 10 makes it unnecessary. 3. Protecting Users' Legal Rights From Anti-Circumvention Law. No covered work shall be deemed part of an effective technological measure under any applicable law fulfilling obligations under article 11 of the WIPO copyright treaty adopted on 20 December 1996, or similar laws prohibiting or restricting circumvention of such measures. When you convey a covered work, you waive any legal power to forbid circumvention of technological measures to the extent such circumvention is effected by exercising rights under this License with respect to the covered work, and you disclaim any intention to limit operation or modification of the work as a means of enforcing, against the work's users, your or third parties' legal rights to forbid circumvention of technological measures. 4. Conveying Verbatim Copies. You may convey verbatim copies of the Program's source code as you receive it, in any medium, provided that you conspicuously and appropriately publish on each copy an appropriate copyright notice; keep intact all notices stating that this License and any non-permissive terms added in accord with section 7 apply to the code; keep intact all notices of the absence of any warranty; and give all recipients a copy of this License along with the Program. You may charge any price or no price for each copy that you convey, and you may offer support or warranty protection for a fee. 5. Conveying Modified Source Versions. You may convey a work based on the Program, or the modifications to produce it from the Program, in the form of source code under the terms of section 4, provided that you also meet all of these conditions: a) The work must carry prominent notices stating that you modified it, and giving a relevant date. b) The work must carry prominent notices stating that it is released under this License and any conditions added under section 7. This requirement modifies the requirement in section 4 to "keep intact all notices". c) You must license the entire work, as a whole, under this License to anyone who comes into possession of a copy. This License will therefore apply, along with any applicable section 7 additional terms, to the whole of the work, and all its parts, regardless of how they are packaged. This License gives no permission to license the work in any other way, but it does not invalidate such permission if you have separately received it. d) If the work has interactive user interfaces, each must display Appropriate Legal Notices; however, if the Program has interactive interfaces that do not display Appropriate Legal Notices, your work need not make them do so. A compilation of a covered work with other separate and independent works, which are not by their nature extensions of the covered work, and which are not combined with it such as to form a larger program, in or on a volume of a storage or distribution medium, is called an "aggregate" if the compilation and its resulting copyright are not used to limit the access or legal rights of the compilation's users beyond what the individual works permit. Inclusion of a covered work in an aggregate does not cause this License to apply to the other parts of the aggregate. 6. Conveying Non-Source Forms. You may convey a covered work in object code form under the terms of sections 4 and 5, provided that you also convey the machine-readable Corresponding Source under the terms of this License, in one of these ways: a) Convey the object code in, or embodied in, a physical product (including a physical distribution medium), accompanied by the Corresponding Source fixed on a durable physical medium customarily used for software interchange. b) Convey the object code in, or embodied in, a physical product (including a physical distribution medium), accompanied by a written offer, valid for at least three years and valid for as long as you offer spare parts or customer support for that product model, to give anyone who possesses the object code either (1) a copy of the Corresponding Source for all the software in the product that is covered by this License, on a durable physical medium customarily used for software interchange, for a price no more than your reasonable cost of physically performing this conveying of source, or (2) access to copy the Corresponding Source from a network server at no charge. c) Convey individual copies of the object code with a copy of the written offer to provide the Corresponding Source. This alternative is allowed only occasionally and noncommercially, and only if you received the object code with such an offer, in accord with subsection 6b. d) Convey the object code by offering access from a designated place (gratis or for a charge), and offer equivalent access to the Corresponding Source in the same way through the same place at no further charge. You need not require recipients to copy the Corresponding Source along with the object code. If the place to copy the object code is a network server, the Corresponding Source may be on a different server (operated by you or a third party) that supports equivalent copying facilities, provided you maintain clear directions next to the object code saying where to find the Corresponding Source. Regardless of what server hosts the Corresponding Source, you remain obligated to ensure that it is available for as long as needed to satisfy these requirements. e) Convey the object code using peer-to-peer transmission, provided you inform other peers where the object code and Corresponding Source of the work are being offered to the general public at no charge under subsection 6d. A separable portion of the object code, whose source code is excluded from the Corresponding Source as a System Library, need not be included in conveying the object code work. A "User Product" is either (1) a "consumer product", which means any tangible personal property which is normally used for personal, family, or household purposes, or (2) anything designed or sold for incorporation into a dwelling. In determining whether a product is a consumer product, doubtful cases shall be resolved in favor of coverage. For a particular product received by a particular user, "normally used" refers to a typical or common use of that class of product, regardless of the status of the particular user or of the way in which the particular user actually uses, or expects or is expected to use, the product. A product is a consumer product regardless of whether the product has substantial commercial, industrial or non-consumer uses, unless such uses represent the only significant mode of use of the product. "Installation Information" for a User Product means any methods, procedures, authorization keys, or other information required to install and execute modified versions of a covered work in that User Product from a modified version of its Corresponding Source. The information must suffice to ensure that the continued functioning of the modified object code is in no case prevented or interfered with solely because modification has been made. If you convey an object code work under this section in, or with, or specifically for use in, a User Product, and the conveying occurs as part of a transaction in which the right of possession and use of the User Product is transferred to the recipient in perpetuity or for a fixed term (regardless of how the transaction is characterized), the Corresponding Source conveyed under this section must be accompanied by the Installation Information. But this requirement does not apply if neither you nor any third party retains the ability to install modified object code on the User Product (for example, the work has been installed in ROM). The requirement to provide Installation Information does not include a requirement to continue to provide support service, warranty, or updates for a work that has been modified or installed by the recipient, or for the User Product in which it has been modified or installed. Access to a network may be denied when the modification itself materially and adversely affects the operation of the network or violates the rules and protocols for communication across the network. Corresponding Source conveyed, and Installation Information provided, in accord with this section must be in a format that is publicly documented (and with an implementation available to the public in source code form), and must require no special password or key for unpacking, reading or copying. 7. Additional Terms. "Additional permissions" are terms that supplement the terms of this License by making exceptions from one or more of its conditions. Additional permissions that are applicable to the entire Program shall be treated as though they were included in this License, to the extent that they are valid under applicable law. If additional permissions apply only to part of the Program, that part may be used separately under those permissions, but the entire Program remains governed by this License without regard to the additional permissions. When you convey a copy of a covered work, you may at your option remove any additional permissions from that copy, or from any part of it. (Additional permissions may be written to require their own removal in certain cases when you modify the work.) You may place additional permissions on material, added by you to a covered work, for which you have or can give appropriate copyright permission. Notwithstanding any other provision of this License, for material you add to a covered work, you may (if authorized by the copyright holders of that material) supplement the terms of this License with terms: a) Disclaiming warranty or limiting liability differently from the terms of sections 15 and 16 of this License; or b) Requiring preservation of specified reasonable legal notices or author attributions in that material or in the Appropriate Legal Notices displayed by works containing it; or c) Prohibiting misrepresentation of the origin of that material, or requiring that modified versions of such material be marked in reasonable ways as different from the original version; or d) Limiting the use for publicity purposes of names of licensors or authors of the material; or e) Declining to grant rights under trademark law for use of some trade names, trademarks, or service marks; or f) Requiring indemnification of licensors and authors of that material by anyone who conveys the material (or modified versions of it) with contractual assumptions of liability to the recipient, for any liability that these contractual assumptions directly impose on those licensors and authors. All other non-permissive additional terms are considered "further restrictions" within the meaning of section 10. If the Program as you received it, or any part of it, contains a notice stating that it is governed by this License along with a term that is a further restriction, you may remove that term. If a license document contains a further restriction but permits relicensing or conveying under this License, you may add to a covered work material governed by the terms of that license document, provided that the further restriction does not survive such relicensing or conveying. If you add terms to a covered work in accord with this section, you must place, in the relevant source files, a statement of the additional terms that apply to those files, or a notice indicating where to find the applicable terms. Additional terms, permissive or non-permissive, may be stated in the form of a separately written license, or stated as exceptions; the above requirements apply either way. 8. Termination. You may not propagate or modify a covered work except as expressly provided under this License. Any attempt otherwise to propagate or modify it is void, and will automatically terminate your rights under this License (including any patent licenses granted under the third paragraph of section 11). However, if you cease all violation of this License, then your license from a particular copyright holder is reinstated (a) provisionally, unless and until the copyright holder explicitly and finally terminates your license, and (b) permanently, if the copyright holder fails to notify you of the violation by some reasonable means prior to 60 days after the cessation. Moreover, your license from a particular copyright holder is reinstated permanently if the copyright holder notifies you of the violation by some reasonable means, this is the first time you have received notice of violation of this License (for any work) from that copyright holder, and you cure the violation prior to 30 days after your receipt of the notice. Termination of your rights under this section does not terminate the licenses of parties who have received copies or rights from you under this License. If your rights have been terminated and not permanently reinstated, you do not qualify to receive new licenses for the same material under section 10. 9. Acceptance Not Required for Having Copies. You are not required to accept this License in order to receive or run a copy of the Program. Ancillary propagation of a covered work occurring solely as a consequence of using peer-to-peer transmission to receive a copy likewise does not require acceptance. However, nothing other than this License grants you permission to propagate or modify any covered work. These actions infringe copyright if you do not accept this License. Therefore, by modifying or propagating a covered work, you indicate your acceptance of this License to do so. 10. Automatic Licensing of Downstream Recipients. Each time you convey a covered work, the recipient automatically receives a license from the original licensors, to run, modify and propagate that work, subject to this License. You are not responsible for enforcing compliance by third parties with this License. An "entity transaction" is a transaction transferring control of an organization, or substantially all assets of one, or subdividing an organization, or merging organizations. If propagation of a covered work results from an entity transaction, each party to that transaction who receives a copy of the work also receives whatever licenses to the work the party's predecessor in interest had or could give under the previous paragraph, plus a right to possession of the Corresponding Source of the work from the predecessor in interest, if the predecessor has it or can get it with reasonable efforts. You may not impose any further restrictions on the exercise of the rights granted or affirmed under this License. For example, you may not impose a license fee, royalty, or other charge for exercise of rights granted under this License, and you may not initiate litigation (including a cross-claim or counterclaim in a lawsuit) alleging that any patent claim is infringed by making, using, selling, offering for sale, or importing the Program or any portion of it. 11. Patents. A "contributor" is a copyright holder who authorizes use under this License of the Program or a work on which the Program is based. The work thus licensed is called the contributor's "contributor version". A contributor's "essential patent claims" are all patent claims owned or controlled by the contributor, whether already acquired or hereafter acquired, that would be infringed by some manner, permitted by this License, of making, using, or selling its contributor version, but do not include claims that would be infringed only as a consequence of further modification of the contributor version. For purposes of this definition, "control" includes the right to grant patent sublicenses in a manner consistent with the requirements of this License. Each contributor grants you a non-exclusive, worldwide, royalty-free patent license under the contributor's essential patent claims, to make, use, sell, offer for sale, import and otherwise run, modify and propagate the contents of its contributor version. In the following three paragraphs, a "patent license" is any express agreement or commitment, however denominated, not to enforce a patent (such as an express permission to practice a patent or covenant not to sue for patent infringement). To "grant" such a patent license to a party means to make such an agreement or commitment not to enforce a patent against the party. If you convey a covered work, knowingly relying on a patent license, and the Corresponding Source of the work is not available for anyone to copy, free of charge and under the terms of this License, through a publicly available network server or other readily accessible means, then you must either (1) cause the Corresponding Source to be so available, or (2) arrange to deprive yourself of the benefit of the patent license for this particular work, or (3) arrange, in a manner consistent with the requirements of this License, to extend the patent license to downstream recipients. "Knowingly relying" means you have actual knowledge that, but for the patent license, your conveying the covered work in a country, or your recipient's use of the covered work in a country, would infringe one or more identifiable patents in that country that you have reason to believe are valid. If, pursuant to or in connection with a single transaction or arrangement, you convey, or propagate by procuring conveyance of, a covered work, and grant a patent license to some of the parties receiving the covered work authorizing them to use, propagate, modify or convey a specific copy of the covered work, then the patent license you grant is automatically extended to all recipients of the covered work and works based on it. A patent license is "discriminatory" if it does not include within the scope of its coverage, prohibits the exercise of, or is conditioned on the non-exercise of one or more of the rights that are specifically granted under this License. You may not convey a covered work if you are a party to an arrangement with a third party that is in the business of distributing software, under which you make payment to the third party based on the extent of your activity of conveying the work, and under which the third party grants, to any of the parties who would receive the covered work from you, a discriminatory patent license (a) in connection with copies of the covered work conveyed by you (or copies made from those copies), or (b) primarily for and in connection with specific products or compilations that contain the covered work, unless you entered into that arrangement, or that patent license was granted, prior to 28 March 2007. Nothing in this License shall be construed as excluding or limiting any implied license or other defenses to infringement that may otherwise be available to you under applicable patent law. 12. No Surrender of Others' Freedom. If conditions are imposed on you (whether by court order, agreement or otherwise) that contradict the conditions of this License, they do not excuse you from the conditions of this License. If you cannot convey a covered work so as to satisfy simultaneously your obligations under this License and any other pertinent obligations, then as a consequence you may not convey it at all. For example, if you agree to terms that obligate you to collect a royalty for further conveying from those to whom you convey the Program, the only way you could satisfy both those terms and this License would be to refrain entirely from conveying the Program. 13. Use with the GNU Affero General Public License. Notwithstanding any other provision of this License, you have permission to link or combine any covered work with a work licensed under version 3 of the GNU Affero General Public License into a single combined work, and to convey the resulting work. The terms of this License will continue to apply to the part which is the covered work, but the special requirements of the GNU Affero General Public License, section 13, concerning interaction through a network will apply to the combination as such. 14. Revised Versions of this License. The Free Software Foundation may publish revised and/or new versions of the GNU General Public License from time to time. Such new versions will be similar in spirit to the present version, but may differ in detail to address new problems or concerns. Each version is given a distinguishing version number. If the Program specifies that a certain numbered version of the GNU General Public License "or any later version" applies to it, you have the option of following the terms and conditions either of that numbered version or of any later version published by the Free Software Foundation. If the Program does not specify a version number of the GNU General Public License, you may choose any version ever published by the Free Software Foundation. If the Program specifies that a proxy can decide which future versions of the GNU General Public License can be used, that proxy's public statement of acceptance of a version permanently authorizes you to choose that version for the Program. Later license versions may give you additional or different permissions. However, no additional obligations are imposed on any author or copyright holder as a result of your choosing to follow a later version. 15. Disclaimer of Warranty. THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION. 16. Limitation of Liability. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. 17. Interpretation of Sections 15 and 16. If the disclaimer of warranty and limitation of liability provided above cannot be given local legal effect according to their terms, reviewing courts shall apply local law that most closely approximates an absolute waiver of all civil liability in connection with the Program, unless a warranty or assumption of liability accompanies a copy of the Program in return for a fee. END OF TERMS AND CONDITIONS How to Apply These Terms to Your New Programs If you develop a new program, and you want it to be of the greatest possible use to the public, the best way to achieve this is to make it free software which everyone can redistribute and change under these terms. To do so, attach the following notices to the program. It is safest to attach them to the start of each source file to most effectively state the exclusion of warranty; and each file should have at least the "copyright" line and a pointer to where the full notice is found. Copyright (C) This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . Also add information on how to contact you by electronic and paper mail. If the program does terminal interaction, make it output a short notice like this when it starts in an interactive mode: Copyright (C) This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'. This is free software, and you are welcome to redistribute it under certain conditions; type `show c' for details. The hypothetical commands `show w' and `show c' should show the appropriate parts of the General Public License. Of course, your program's commands might be different; for a GUI interface, you would use an "about box". You should also get your employer (if you work as a programmer) or school, if any, to sign a "copyright disclaimer" for the program, if necessary. For more information on this, and how to apply and follow the GNU GPL, see . The GNU General Public License does not permit incorporating your program into proprietary programs. If your program is a subroutine library, you may consider it more useful to permit linking proprietary applications with the library. If this is what you want to do, use the GNU Lesser General Public License instead of this License. But first, please read . gnome-mpv-0.13/Makefile.am000066400000000000000000000007551317030365200154050ustar00rootroot00000000000000AUTOMAKE_OPTIONS = foreign SUBDIRS = src data docs po EXTRA_DIST = README.md AUTHORS meson.build meson_post_install.py po/meson.build UPDATE_DESKTOP = update-desktop-database -q || : UPDATE_ICON = gtk-update-icon-cache -q $(datadir)/icons/hicolor/ || : # Ensure that the dist tarball does not contain own/group from build system TAR_OPTIONS = --owner=0 --group=0 export TAR_OPTIONS install-data-hook: $(UPDATE_DESKTOP) $(UPDATE_ICON) uninstall-hook: $(UPDATE_DESKTOP) $(UPDATE_ICON) gnome-mpv-0.13/README.md000066400000000000000000000143411317030365200146240ustar00rootroot00000000000000# GNOME MPV GNOME MPV is a simple GTK+ frontend for mpv. GNOME MPV interacts with mpv via the client API exported by libmpv, allowing access to mpv's powerful playback capabilities. ![Screenshot](https://gnome-mpv.github.io/images/screenshot-0.png) ## Dependencies - appstream-glib[[1]](#note1) (build) - autoconf >= 2.69[[1]](#note1) (build) - autoconf-archive[[1]](#note1) (build) - automake >= 1.12[[1]](#note1) (build) - pkg-config (build) - gcc (build) - glib >= 2.44 - gtk >= 3.18[[2]](#note2) - mpv >= 0.21 - epoxy - lua (optional) - youtube-dl (optional) [1]: Not required when building from release tarballs [2]: Some features may be unavailable with gtk < 3.20 ## Installation ### GNU/Linux packages - Arch Linux: https://aur.archlinux.org/packages/gnome-mpv - Arch Linux (Git): https://aur.archlinux.org/packages/gnome-mpv-git - Debian testing: https://packages.debian.org/testing/gnome-mpv - Debian unstable: https://packages.debian.org/sid/gnome-mpv - Fedora (rpmfusion): https://admin.rpmfusion.org/pkgdb/package/free/gnome-mpv/ - Frugalware: http://www4.frugalware.org/pub/linux/distributions/frugalware/frugalware-current/source/xapps-extra/gnome-mpv/ - OpenSUSE: https://build.opensuse.org/package/show/home:mermoldy:multimedia/gnome-mpv - Gentoo: http://gpo.zugaina.org/media-video/gnome-mpv - Guix: https://www.gnu.org/software/guix/packages/g.html#gnome-mpv - Solus: https://packages.solus-project.com/shannon/g/gnome-mpv/ - Ubuntu: https://launchpad.net/~xuzhen666/+archive/ubuntu/gnome-mpv ### Flatpak [Flatpak](https://flatpak.org) packages support multiple distributions and are sandboxed. Flatpak 0.9.5+ is recommended for best integration. Stable releases are hosted on [Flathub](https://flathub.org): ```sh flatpak remote-add --if-not-exists flathub https://flathub.org/repo/flathub.flatpakrepo flatpak install flathub io.github.GnomeMpv ``` Development versions are also packaged: ```sh flatpak install https://dl.tingping.se/flatpak/gnome-mpv.flatpakref ``` ### Source code Run the following command in the source code directory to build and install: ```sh ./autogen.sh && make && sudo make install ``` When building from release tarballs, replace `./autogen.sh` with `./configure`: ```sh ./configure && make && sudo make install ``` Alternatively, you can use Meson: ```sh meson build && cd build && ninja && sudo ninja install ``` ## Usage ### Opening files There are 4 ways to open files in GNOME MPV. 1. Passing files and/or URIs as command line arguments. 2. Using the file chooser dialog box, accessible via the "Open" menu item. 3. Typing URI into the "Open Location" dialog box, accessible via the menu item with the same name. 4. Dragging and dropping files or URIs onto GNOME MPV. ### Manipulating playlist The playlist is hidden by default. To show the playlist, click the "Playlist" menu item or press F9. Files can be added by dragging and dropping files or URIs onto the playlist. Dropping files or URIs onto the video area will replace the content of the playlist. Playlist files or online playlists (eg. YouTube's playlist) will be automatically expanded into individual items when loaded. Items in the playlist can be reordered via drag-and-drop. To remove items from the playlist, select the item by clicking on it then press the delete button on your keyboard. ### Configuration GNOME MPV can be configured using the preferences dialog accessible via the "Preferences" menu item. Additional configuration options can be set from an external file using the same syntax as mpv's `mpv.conf`. See mpv's man page for the full list of options. The file must be specified and enabled in the preferences dialog under the "MPV Configuration" section. Options can also be set using the "Extra MPV Options" text box in the preferences dialog. The syntax used is the same as mpv's command line options. ### Lua Scripts GNOME MPV can use most mpv Lua scripts as-is. Some Lua scripts may define keybindings that conflict with GNOME MPV, in which case you'll need to resolve the conflict by explicitly defining new keybindings using `input.conf`. See [mpv's manual](https://mpv.io/manual/stable/#lua-scripting-[,flags]]%29) for more details. Lua scripts can be installed by switching to the `Lua Scripts` tab in the preferences dialog and dropping script files there. A list of mpv Lua scripts can be found [here](https://github.com/mpv-player/mpv/wiki/User-Scripts#lua-scripts). ### Keybindings GNOME MPV defines a set of keybindings in the macro `DEFAULT_KEYBINDS`, which can be found in [src/def.h](https://github.com/gnome-mpv/gnome-mpv/blob/master/src/gmpv_def.h). The syntax used is exactly the same as mpv's `input.conf`. These keybindings are applied on top of default keybindings provided by mpv. Additional keybindings can be defined in an external file using mpv's `input.conf` syntax. The file can be set in the preferences dialog under the "Keybindings" section. ## Contributing Translations GNOME MPV uses [Zanata](https://zanata.org) to coordinate translations. You can find GNOME MPV's page [here](https://translate.zanata.org/zanata/iteration/view/gnome-mpv/master). To start translating, follow the instructions [here](http://docs.zanata.org/en/release/user-guide/translator-guide/). If you'd like to add a new language, open an issue on GitHub. While translating, you will find the string `translator-credits`. You should not translate this string. Instead, you should put your name, and optionally your email address, in the following format: `FirstName LastName `. Your name will then appear in the About dialog when your translation is active. ## License GNOME MPV is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. GNOME MPV is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with GNOME MPV. If not, see . gnome-mpv-0.13/autogen.sh000077500000000000000000000011301317030365200153360ustar00rootroot00000000000000#!/bin/sh # Run this to generate all the initial makefiles, etc. srcdir=`dirname $0` test -z "$srcdir" && srcdir=. (test -f $srcdir/configure.ac) || { echo -n "**Error**: Directory "\`$srcdir\'" does not look like the top-level directory" exit 1 } aclocal --install -I m4 || exit 1 autoreconf --force --install -Wno-portability || exit 1 if [ "$NOCONFIGURE" = "" ]; then $srcdir/configure "$@" || exit 1 if [ "$1" = "--help" ]; then exit 0 else echo "Now type \`make\' to compile" || exit 1 fi else echo "Skipping configure process." fi set +x gnome-mpv-0.13/configure.ac000066400000000000000000000061611317030365200156340ustar00rootroot00000000000000AC_PREREQ([2.69]) AC_INIT( [gnome-mpv], [0.13], [http://github.com/gnome-mpv/gnome-mpv/issues], [gnome-mpv], [http://github.com/gnome-mpv/gnome-mpv] ) AC_CONFIG_SRCDIR([src/gmpv_main.c]) AC_CONFIG_MACRO_DIR([m4]) AC_USE_SYSTEM_EXTENSIONS AM_INIT_AUTOMAKE([1.12 tar-pax dist-xz no-dist-gzip subdir-objects foreign -Wall -Wno-portability]) AM_SILENT_RULES([yes]) AM_MAINTAINER_MODE([enable]) # i18n GETTEXT_PACKAGE=gnome-mpv AC_SUBST(GETTEXT_PACKAGE) AC_DEFINE_UNQUOTED(GETTEXT_PACKAGE,"$GETTEXT_PACKAGE", [GETTEXT package name]) AM_GNU_GETTEXT_VERSION([0.19.7]) AM_GNU_GETTEXT([external]) GLIB_GSETTINGS AC_ARG_ENABLE([debug], AS_HELP_STRING([--enable-debug], [turn on debugging]), [enable_debug=$enableval], [enable_debug=no]) AC_DEFUN([GM_CHECK_MACRO], [m4_ifndef([$1], [m4_fatal($1[ is not defined. Is ]$2[ installed?])])]) GM_CHECK_MACRO([AX_APPEND_COMPILE_FLAGS], [autoconf-archive]) GM_CHECK_MACRO([AX_APPEND_LINK_FLAGS], [autoconf-archive]) GM_CHECK_MACRO([AX_REQUIRE_DEFINED], [autoconf-archive]) GM_CHECK_MACRO([APPSTREAM_XML], [appstream-glib]) APPSTREAM_XML AS_IF([test "x$enable_debug" = "xyes"], [ AX_APPEND_COMPILE_FLAGS([-O0 -g]) ], [ AX_APPEND_COMPILE_FLAGS([-O2]) ]) AX_APPEND_COMPILE_FLAGS([ \ -std=gnu99 \ -funsigned-char \ -fstack-protector-strong \ -fPIE \ -fPIC \ -Wall \ -Wextra \ -Wconversion \ -Winline \ -Wno-padded \ -Wno-unused-parameter \ -Wstrict-prototypes \ -Wmissing-prototypes \ -Werror=implicit-function-declaration \ -Werror=pointer-arith \ -Werror=init-self \ -Werror=format-security \ -Werror=format=2 \ -Werror=missing-include-dirs \ -Werror=date-time \ ]) AX_APPEND_LINK_FLAGS([ \ -pie \ -Wl,-z,relro \ -Wl,-z,now \ ]) # Checks for programs. AC_PROG_CC AC_PROG_CC_STDC AC_PROG_AWK AC_PROG_SED AC_PATH_PROG(GDBUS_CODEGEN, [gdbus-codegen], []) AC_PATH_PROG(GLIB_GENMARSHAL, [glib-genmarshal], []) AS_IF([test "x$GDBUS_CODEGEN" = "x"], [ AC_MSG_ERROR([Could not find gdbus-codegen]) ]) AS_IF([test "x$GLIB_GENMARSHAL" = "x"], [ AC_MSG_ERROR([Could not find glib-genmarshal]) ]) PKG_CHECK_MODULES(DEPS, [gtk+-3.0 glib-2.0 >= 2.44 mpv >= 1.20 epoxy]) AC_DEFINE([GLIB_VERSION_MIN_REQUIRED], [GLIB_VERSION_2_44], [Dont warn using older APIs]) AC_DEFINE([GLIB_VERSION_MAX_ALLOWED], [GLIB_VERSION_2_44], [Prevents using newer APIs]) AM_CONDITIONAL([NEW_GTK], PKG_CHECK_EXISTS([gtk+-3.0 >= 3.20], true, false)) AM_COND_IF([NEW_GTK],[ AC_DEFINE([GDK_VERSION_MIN_REQUIRED], [GDK_VERSION_3_20], [Dont warn using older APIs]) AC_DEFINE([GDK_VERSION_MAX_ALLOWED], [GDK_VERSION_3_20], [Prevents using newer APIs]) ],[ AC_DEFINE([GDK_VERSION_MIN_REQUIRED], [GDK_VERSION_3_18], [Dont warn using older APIs]) AC_DEFINE([GDK_VERSION_MAX_ALLOWED], [GDK_VERSION_3_18], [Prevents using newer APIs]) ]) # Checks for header files. AC_CHECK_HEADERS([string.h stdio.h stdlib.h locale.h],[],[ AC_MSG_ERROR([Could not find required headers]) ]) AC_CHECK_FUNCS([setlocale],[],[ AC_MSG_ERROR([Could not find required functions]) ]) AC_CONFIG_FILES([Makefile src/Makefile data/Makefile docs/Makefile po/Makefile.in]) AC_OUTPUT echo " $PACKAGE $VERSION prefix ........: $prefix debug .........: $enable_debug " gnome-mpv-0.13/data/000077500000000000000000000000001317030365200142535ustar00rootroot00000000000000gnome-mpv-0.13/data/Makefile.am000066400000000000000000000024431317030365200163120ustar00rootroot00000000000000gsettings_SCHEMAS = io.github.GnomeMpv.gschema.xml org.gnome-mpv.gschema.xml @GSETTINGS_RULES@ appstream_in_files = io.github.GnomeMpv.appdata.xml.in appstream_XML = $(appstream_in_files:.xml.in=.xml) %.appdata.xml: %.appdata.xml.in $(AM_V_GEN)$(MSGFMT) --xml --template $< -d $(top_srcdir)/po -o $@ @APPSTREAM_XML_RULES@ dbusservicedir = $(datadir)/dbus-1/services dbusservice_in_files = io.github.GnomeMpv.service.in dbusservice_DATA = $(dbusservice_in_files:.service.in=.service) %.service: %.service.in Makefile $(AM_V_GEN) sed -e "s|\@bindir\@|$(bindir)|" $< > $@ desktopdir = $(datadir)/applications desktop_in_files = io.github.GnomeMpv.desktop.in desktop_DATA = $(desktop_in_files:.desktop.in=.desktop) %.desktop: %.desktop.in $(AM_V_GEN)$(MSGFMT) --desktop --template $< -d $(top_srcdir)/po -o $@ icondir = $(datadir)/icons/hicolor/scalable/apps icon_DATA = gnome-mpv.svg symicondir = $(datadir)/icons/hicolor/symbolic/apps symicon_DATA = gnome-mpv-symbolic.svg EXTRA_DIST = $(appstream_in_files) \ $(desktop_in_files) \ $(dbusservice_in_files) \ gnome-mpv.svg \ gnome-mpv-symbolic.svg \ org.gnome-mpv.gschema.xml \ io.github.GnomeMpv.gschema.xml \ gmpv_mpris_gdbus.xml \ gmpv_marshal.lst \ meson.build DISTCLEANFILES = $(appstream_XML) $(desktop_DATA) $(dbusservice_DATA) gnome-mpv-0.13/data/gmpv_marshal.lst000066400000000000000000000002371317030365200174610ustar00rootroot00000000000000VOID:POINTER,BOOLEAN VOID:STRING,POINTER VOID:INT,INT VOID:INT64,INT64 VOID:INT,STRING,STRING VOID:INT,POINTER VOID:BOOLEAN,BOOLEAN,POINTER,POINTER VOID:INT64 gnome-mpv-0.13/data/gmpv_mpris_gdbus.xml000066400000000000000000000063451317030365200203540ustar00rootroot00000000000000 gnome-mpv-0.13/data/gnome-mpv-symbolic.svg000066400000000000000000000005211317030365200205160ustar00rootroot00000000000000 gnome-mpv-0.13/data/gnome-mpv.svg000066400000000000000000000005211317030365200166770ustar00rootroot00000000000000 gnome-mpv-0.13/data/io.github.GnomeMpv.appdata.xml.in000066400000000000000000000034141317030365200224340ustar00rootroot00000000000000 io.github.GnomeMpv.desktop CC-BY-SA-4.0 GPL-3.0+ GNOME MPV GTK+ frontend for mpv io.github.GnomeMpv.desktop gnome-mpv

GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media player capable of playing virtually all video and audio formats. The design of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME libraries. GNOME MPV also offers an option to disable client-side decorations (CSD) for better compatibility with non-GNOME systems.

Features:

  • Drag and drop playlist
  • Loading external mpv configuration files
  • MPRIS2 D-Bus interface
http://gnome-mpv.github.io/images/screenshot-0.png <_caption>The main window showing the application in action http://gnome-mpv.github.io/images/screenshot-1.png The main window with CSD disabled http://gnome-mpv.github.io/images/screenshot-2.png The main window with playlist open http://gnome-mpv.github.io http://github.com/gnome-mpv/gnome-mpv/issues gnome-mpv_at_teknik.io
gnome-mpv-0.13/data/io.github.GnomeMpv.desktop.in000066400000000000000000000045311317030365200216750ustar00rootroot00000000000000[Desktop Entry] Version=1.0 Name=GNOME MPV Comment=GTK+ frontend for mpv Exec=gnome-mpv %U # Translators: This is an icon name, don't translate! Icon=gnome-mpv Terminal=false Type=Application StartupNotify=true DBusActivatable=true Categories=GTK;GNOME;AudioVideo;Player;Video;TV; MimeType=application/mpeg4-iod;application/mpeg4-muxcodetable;application/mxf;application/ogg;application/ram;application/sdp;application/streamingmedia;application/vnd.apple.mpegurl;application/vnd.ms-asf;application/vnd.rn-realmedia;application/vnd.rn-realmedia-vbr;application/x-extension-m4a;application/x-extension-mp4;application/x-flac;application/x-flash-video;application/x-matroska;application/x-ogg;application/x-streamingmedia;audio/3gpp;audio/3gpp2;audio/aac;audio/ac3;audio/amr;audio/amr-wb;audio/basic;audio/dv;audio/eac3;audio/flac;audio/m4a;audio/midi;audio/mp1;audio/mp2;audio/mp3;audio/mp4;audio/mpeg;audio/mpegurl;audio/mpg;audio/ogg;audio/opus;audio/scpls;audio/vnd.dolby.heaac.1;audio/vnd.dolby.heaac.2;audio/vnd.dolby.mlp;audio/vnd.dts;audio/vnd.dts.hd;audio/vnd.rn-realaudio;audio/wav;audio/webm;audio/x-aac;audio/x-aiff;audio/x-ape;audio/x-flac;audio/x-gsm;audio/x-it;audio/x-m4a;audio/x-matroska;audio/x-mod;audio/x-mp1;audio/x-mp2;audio/x-mp3;audio/x-mpeg;audio/x-mpegurl;audio/x-mpg;audio/x-ms-asf;audio/x-ms-wma;audio/x-musepack;audio/x-pn-aiff;audio/x-pn-au;audio/x-pn-realaudio;audio/x-pn-wav;audio/x-real-audio;audio/x-realaudio;audio/x-s3m;audio/x-scpls;audio/x-shorten;audio/x-speex;audio/x-tta;audio/x-vorbis;audio/x-vorbis+ogg;audio/x-wav;audio/x-wavpack;audio/x-xm;video/3gp;video/3gpp;video/3gpp2;video/divx;video/dv;video/fli;video/flv;video/mp2t;video/mp4;video/mp4v-es;video/mpeg;video/mpeg-system;video/msvideo;video/ogg;video/quicktime;video/vnd.mpegurl;video/vnd.rn-realvideo;video/webm;video/x-avi;video/x-flc;video/x-fli;video/x-flv;video/x-m4v;video/x-matroska;video/x-mpeg;video/x-mpeg-system;video/x-mpeg2;video/x-ms-asf;video/x-ms-wm;video/x-ms-wmv;video/x-ms-wmx;video/x-msvideo;video/x-nsv;video/x-ogm+ogg;video/x-theora;video/x-theora+ogg;x-content/audio-cdda;x-content/audio-player;x-content/video-dvd;x-scheme-handler/mms;x-scheme-handler/mmsh;x-scheme-handler/rtmp;x-scheme-handler/rtp;x-scheme-handler/rtsp; X-KDE-Protocols=ftp,http,https,mms,rtmp,rtsp,sftp,smb Actions=new-window; [Desktop Action new-window] Name=New Window Exec=gnome-mpv --new-window gnome-mpv-0.13/data/io.github.GnomeMpv.gschema.xml000066400000000000000000000077141317030365200220330ustar00rootroot00000000000000 false Whether the settings has already been migrated from the previous version true Enable or disable dark theme true Enable or disable client-side decorations false Whether or not to use floating controls in windowed mode false Whether or not to make file chooser dialog remember last folder accessed false Whether or not to create new windows when there is already an instance '' Options to pass to mpv '' Path to mpv configuration file false Load or don't load mpv configuration file '' Path to mpv input configuration file false Load or don't load mpv input configuration file true Whether or not to enable MPRIS support true Whether or not to enable GNOME-Settings-Daemon-based media keys support true Whether or not to prefetch metadata for non-current playlist entries 640 Width of the window 480 Height of the window 1.0 Volume of player 250 Width of the playlist true Show or not show the controls false Show or not show the playlist '' URI of the last folder accessed gnome-mpv-0.13/data/io.github.GnomeMpv.service.in000066400000000000000000000001271317030365200216610ustar00rootroot00000000000000[D-BUS Service] Name=io.github.GnomeMpv Exec=@bindir@/gnome-mpv --gapplication-service gnome-mpv-0.13/data/meson.build000066400000000000000000000022161317030365200164160ustar00rootroot00000000000000 schemadir = join_paths(get_option('datadir'), 'glib-2.0/schemas') install_data([ 'io.github.GnomeMpv.gschema.xml', 'org.gnome-mpv.gschema.xml' ], install_dir: schemadir) i18n.merge_file( input: 'io.github.GnomeMpv.appdata.xml.in', output: 'io.github.GnomeMpv.appdata.xml', po_dir: '../po', install: true, install_dir: join_paths(get_option('datadir'), 'appdata') ) i18n.merge_file( input: 'io.github.GnomeMpv.desktop.in', output: 'io.github.GnomeMpv.desktop', type: 'desktop', po_dir: '../po', install: true, install_dir: join_paths(get_option('datadir'), 'applications') ) icondir = join_paths(get_option('datadir'), 'icons/hicolor') install_data('gnome-mpv.svg', install_dir: join_paths(icondir, 'scalable/apps') ) install_data('gnome-mpv-symbolic.svg', install_dir: join_paths(icondir, 'symbolic/apps') ) service_conf = configuration_data() service_conf.set('bindir', join_paths(get_option('prefix'), get_option('bindir'))) configure_file( input: 'io.github.GnomeMpv.service.in', output: 'io.github.GnomeMpv.service', configuration: service_conf, install_dir: join_paths(get_option('datadir'), 'dbus-1', 'services') ) gnome-mpv-0.13/data/org.gnome-mpv.gschema.xml000066400000000000000000000051171317030365200211020ustar00rootroot00000000000000 true Enable or disable dark theme true Enable or disable client-side decorations false Whether or not to make file chooser dialog remember last folder accessed '' Options to pass to mpv '' Path to mpv configuration file false Load or don't load mpv configuration file '' Path to mpv input configuration file false Load or don't load mpv input configuration file 640 Width of the window 480 Height of the window 1.0 Volume of player 250 Width of the playlist false Show or not show the playlist '' URI of the last folder accessed gnome-mpv-0.13/docs/000077500000000000000000000000001317030365200142725ustar00rootroot00000000000000gnome-mpv-0.13/docs/Makefile.am000066400000000000000000000000611317030365200163230ustar00rootroot00000000000000man_MANS=gnome-mpv.1 EXTRA_DIST = $(man_MANS) gnome-mpv-0.13/docs/gnome-mpv.1000066400000000000000000000030041317030365200162560ustar00rootroot00000000000000.\"Copyright (c) 2017 gnome-mpv .\" .\"This file is part of GNOME MPV. .\" .\"GNOME MPV is free software: you can redistribute it and/or modify .\"it under the terms of the GNU General Public License as published by .\"the Free Software Foundation, either version 3 of the License, or .\"(at your option) any later version. .\" .\"GNOME MPV is distributed in the hope that it will be useful, .\"but WITHOUT ANY WARRANTY; without even the implied warranty of .\"MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the .\"GNU General Public License for more details. .\" .\"You should have received a copy of the GNU General Public License .\"along with GNOME MPV. If not, see . .TH gnome-mpv 1 "19 July 2017" .SH NAME GNOME MPV \- A simple GTK+ frontend for mpv .SH SYNOPSIS .B gnome-mpv [\fIoptions...\fR] [\fIfilenames\fR|\fIURIs\fR] .SH DESCRIPTION \fBGNOME MPV\fR is a simple GTK+ frontend for \fBmpv\fR. \fBGNOME MPV\fR interacts with \fBmpv\fR via the client API exported by libmpv, allowing access to \fBmpv\fR's powerful playback capabilities. .SH OPTIONS .TP \fB\-?, \-h, \-\-help\fR Show help options. .TP \fB\--new-window\fR Create a new window if there is already a running instance. The option has no effect otherwise. .TP \fB\--enqueue\fR Append the given files or URIs to the playlist if there is a running instance. The option has no effect otherwise. .TP \fB\--version\fR Print the release version and exit. .SH BUGS Please report bugs at https://github.com/gnome-mpv/gnome-mpv/issues. gnome-mpv-0.13/docs/meson.build000066400000000000000000000000331317030365200164300ustar00rootroot00000000000000install_man('gnome-mpv.1') gnome-mpv-0.13/meson.build000066400000000000000000000024701317030365200155070ustar00rootroot00000000000000project('gnome-mpv', 'c', version: '0.13', meson_version: '>= 0.37.0', default_options: [ 'warning_level=2', 'c_std=gnu99', ] ) i18n = import('i18n') cc = meson.get_compiler('c') test_cflags = [ '-funsigned-char', '-fstack-protector-strong', '-fPIE', '-fPIC', '-Wconversion', '-Winline', '-Wno-padded', '-Wno-unused-parameter', '-Wstrict-prototypes', '-Wmissing-prototypes', '-Werror=implicit-function-declaration', '-Werror=pointer-arith', '-Werror=init-self', ['-Werror=format-security', '-Werror=format=2'], # Must be checked together '-Werror=missing-include-dirs', '-Werror=date-time' ] global_cflags = [] foreach cflag : test_cflags if cc.has_multi_arguments(cflag) global_cflags += cflag endif endforeach if cc.has_header('execinfo.h') global_cflags += '-DHAVE_EXECINFO_H' endif add_project_arguments(global_cflags, language: 'c') test_ldflags = [ '-pie', '-Wl,-z,relro', '-Wl,-z,now' ] global_ldflags = [] foreach ldflag : test_ldflags if cc.has_argument(ldflag) global_ldflags += ldflag endif endforeach add_project_link_arguments(global_ldflags, language: 'c') if not cc.has_function('setlocale') error('Could not find setlocale()') endif subdir('src') subdir('data') subdir('docs') subdir('po') meson.add_install_script('meson_post_install.py') gnome-mpv-0.13/meson_post_install.py000077500000000000000000000012031317030365200176270ustar00rootroot00000000000000#!/usr/bin/env python3 import os import subprocess prefix = os.environ.get('MESON_INSTALL_PREFIX', '/usr/local') datadir = os.path.join(prefix, 'share') # Packaging tools define DESTDIR and this isn't needed for them if not 'DESTDIR' in os.environ: print('Compiling gsettings schemas...') subprocess.call(['glib-compile-schemas', os.path.join(datadir, 'glib-2.0', 'schemas')]) print('Updating icon cache...') subprocess.call(['gtk-update-icon-cache', '-qtf', os.path.join(datadir, 'icons', 'hicolor')]) print('Updating desktop database...') subprocess.call(['update-desktop-database', '-q', os.path.join(datadir, 'applications')]) gnome-mpv-0.13/po/000077500000000000000000000000001317030365200137605ustar00rootroot00000000000000gnome-mpv-0.13/po/LINGUAS000066400000000000000000000001211317030365200147770ustar00rootroot00000000000000bg ca cs de_DE es fr hu it ja nl pl pt_BR pt_PT ro ru sr sr@latin sv zh_CN zh_TW gnome-mpv-0.13/po/Makevars000066400000000000000000000007101317030365200154520ustar00rootroot00000000000000subdir = po top_builddir = .. DOMAIN = $(PACKAGE) XGETTEXT_OPTIONS = --from-code=UTF-8 --keyword=_ --keyword=N_ --keyword=C_:1c,2 --keyword=NC_:1c,2 --keyword=g_dngettext:2,3 --add-comments COPYRIGHT_HOLDER = GNOME MPV PACKAGE_GNU = no MSGID_BUGS_ADDRESS = https://github.com/gnome-mpv/gnome-mpv/issues EXTRA_LOCALE_CATEGORIES = USE_MSGCTXT = no MSGMERGE_OPTIONS = --quiet MSGINIT_OPTIONS = PO_DEPENDS_ON_POT = no DIST_DEPENDS_ON_UPDATE_PO = no gnome-mpv-0.13/po/POTFILES.in000066400000000000000000000013511317030365200155350ustar00rootroot00000000000000data/org.gnome-mpv.gschema.xml data/io.github.GnomeMpv.gschema.xml data/io.github.GnomeMpv.appdata.xml.in data/io.github.GnomeMpv.desktop.in src/gmpv_application.c src/gmpv_common.c src/gmpv_control_box.c src/gmpv_controller_actions.c src/gmpv_controller.c src/gmpv_controller_input.c src/gmpv_file_chooser.c src/gmpv_header_bar.c src/gmpv_main.c src/gmpv_main_window.c src/gmpv_menu.c src/gmpv_metadata_cache.c src/gmpv_model.c src/gmpv_mpv.c src/gmpv_mpv_wrapper.c src/gmpv_open_location_dialog.c src/gmpv_player.c src/gmpv_player_options.c src/gmpv_playlist_widget.c src/gmpv_plugins_manager.c src/gmpv_plugins_manager_item.c src/gmpv_preferences_dialog.c src/gmpv_seek_bar.c src/gmpv_shortcuts_window.c src/gmpv_video_area.c src/gmpv_view.c gnome-mpv-0.13/po/bg.po000066400000000000000000000635641317030365200147260ustar00rootroot00000000000000# cybercop , 2017. #zanata # gnome-mpv , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: 0.6\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2016-01-04 00:00+0700\n" "PO-Revision-Date: 2017-08-02 01:15-0400\n" "Last-Translator: cybercop \n" "Language-Team: Bulgarian\n" "Language: bg\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=3; plural=(n%10==1 && n%100!=11 ? 0 : n%10>=2 && n%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2);\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "Включване или изключване на тъмната тема" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 msgid "Enable or disable client-side decorations" msgstr "Включване или изключване на Gnome 3 декорацията" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "Да бъде ли запомнян последния избран файл или посетена папка" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "Внасяне на настройки от MPV" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 msgid "Path to mpv configuration file" msgstr "Път до конфигурационен файл на MPV" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 msgid "Load or don't load mpv configuration file" msgstr "Да се зареди ли конфигурационния файл от MPV" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 msgid "Path to mpv input configuration file" msgstr "Път до внесения конфигурационен файл на MPV" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 msgid "Load or don't load mpv input configuration file" msgstr "Да се зареди ли внесен MPV конфигурационен файл" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 msgid "Width of the window" msgstr "Ширина на прозореца" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 msgid "Height of the window" msgstr "Височина на прозореца" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 msgid "Volume of player" msgstr "Сила на звука на плеъра" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "Ширина на спъсъка за изпълнение" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "Показване и скриване на списъка за изпълнение" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "Адрес на последната посещавана папка" #: data/io.github.GnomeMpv.gschema.xml:10 msgid "" "Whether the settings has already been migrated from the previous version" msgstr "Дали настройките вече са прехвърлени от предишната версия" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "Да се ползват ли плаващи контролери в прозоречен режим" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "Разрешена ли е поддръжка на MPRIS" #: data/io.github.GnomeMpv.gschema.xml:82 msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "" "Включена ли е поддръжка на мултимедийни клавиши в GNOME-Settings-Daemon" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 msgid "Show or not show the controls" msgstr "Да се показват ли контролерите" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "GTK+ интерфейс за MPV" #: data/io.github.GnomeMpv.appdata.xml.in:12 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" "GNOME MPV е опростен GTK+ интерфейс за MPV, който е мощен мултимедиен плеър," " способен да възпрозвежда множество мултимедийни формати. Дизайна на GNOME " "MPV съответства GNOME HIG. GNOME MPV също предлага опция, която изключва " "Gnome 3 декорацията на прозорецa (CSD) за по- добра съвместимост с графични " "среди, различни от GNOME." #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "Опции:" #: data/io.github.GnomeMpv.appdata.xml.in:21 msgid "Drag and drop playlist" msgstr "Поддръжка на Drag'n'Drop" #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "Loading external mpv configuration files" msgstr "Зареждане на външни MPV конфигурационни файлове" #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "MPRIS2 D-Bus интерфейс" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "Главният прозорец с изключен CSD" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "Главният прозорец с отворен спъсък за изпълнение" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "gnome-mpv" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "Нов прозорец" #: src/gmpv_application.c:370 msgid "Playing" msgstr "Изпълнение" #: src/gmpv_application.c:415 msgid "Show release version" msgstr "Покажи текущата версия" #: src/gmpv_application.c:423 msgid "Enqueue" msgstr "На опашка" #: src/gmpv_application.c:431 msgid "Create a new window" msgstr "Създаване на нов прозорец" #: src/gmpv_application.c:439 msgid "Don't connect to an already-running instance" msgstr "Не свързвайте към вече стартиран екземпляр" #: src/gmpv_control_box.c:286 msgid "Pause" msgstr "Пауза" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 msgid "Play" msgstr "Изпълнение" #: src/gmpv_control_box.c:436 msgid "Stop" msgstr "Спиране" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "Напред" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "Назад" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "Следващо заглавие" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "Предишно заглавие" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 msgid "Toggle Fullscreen" msgstr "Включване/изключване режима на цял екран" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 msgid "Error" msgstr "Грешка" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "Отказ" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "_Отваряне" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 msgid "All Files" msgstr "Всички файлове" #: src/gmpv_file_chooser.c:143 msgid "Media Files" msgstr "Мултимедийни файлове" #: src/gmpv_file_chooser.c:154 msgid "Audio Files" msgstr "Аудио файлове" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "Видео файлове" #: src/gmpv_file_chooser.c:170 msgid "Image Files" msgstr "Файлове с изображения" #: src/gmpv_file_chooser.c:180 msgid "Subtitle Files" msgstr "Фалове със субтитри" #: src/gmpv_menu.c:102 msgid "None" msgstr "Няма" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 msgid "Unknown" msgstr "Неизвестно" #: src/gmpv_menu.c:150 msgid "_Load External…" msgstr "_Зареждане на външен…" #: src/gmpv_menu.c:243 msgid "_File" msgstr "_Файл" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "Отваряне на местоположение" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "Запазване на списък за изпълнение" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "_Изход" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "_Редактиране" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "_Предпочитания" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "_Видео запис" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 msgid "_Audio Track" msgstr "_Аудио запис" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 msgid "S_ubtitle Track" msgstr "Файл със субтитри" #: src/gmpv_menu.c:253 msgid "_View" msgstr "_Преглед" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "Включване/изключване на контролерите" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 msgid "_Toggle Playlist" msgstr "Включване/изключване на списъка за изпълнение" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "Режим на цял екран" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "Нормален размер" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 msgid "_Double Size" msgstr "Двоен размер" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 msgid "_Half Size" msgstr "Намален наполовина размер" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "_Помощ" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 msgid "_Keyboard Shortcuts" msgstr "Клавишни комбинации" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "Относно" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "Възпрозвеждането беше спряно непредвидено. Причина: %s." #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "Местоположение:" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "Не могат да бъдат приложени една или повече опции за MPV." #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "_Добавяне…" #: src/gmpv_playlist_widget.c:537 msgid "Add _Location…" msgstr "Добавяне на местоположение…" #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "Разбъркано" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "Повторение" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "Списък за изпълнение" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "Добавяне на Lua скрипт" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 msgid "Lua Scripts" msgstr "Lua скрипт" #: src/gmpv_plugins_manager.c:299 #, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "Неуспешно копиране на файл от '%s' в '%s'. Причина: %s" #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "Не е намерен Lua скрипт" #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "Премахване" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "" "Сигурен ли сте, че искате да премахнете този скрипт? Това действие не може " "да бъде отменено." #: src/gmpv_plugins_manager_item.c:184 #, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "Неуспешно изтриване на файл '%s'. Причина: %s" #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "Потребителски интерфейс" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "Включване на вградената Gnome 3 декорация" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "Включване на тъмната тема" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "Използване на плаващи контролери в прозоречен режим" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "Запомняне на последното местоположение на файловете" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr " MPV конфигурация" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "Зареждане на MPV конфигурационен файл" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr " MPV конфигурационен файл:" #: src/gmpv_preferences_dialog.c:314 msgid "Keybindings" msgstr "Клавишни комбинации" #: src/gmpv_preferences_dialog.c:317 msgid "Load MPV input configuration file" msgstr "Зареждане на внесен MPV конфигурационен файл" #: src/gmpv_preferences_dialog.c:320 msgid "MPV input configuration file:" msgstr "Внесен MPV конфигурационен файл:" #: src/gmpv_preferences_dialog.c:323 msgid "Miscellaneous" msgstr "Разни" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "Включване поддръжка на MPRIS" #: src/gmpv_preferences_dialog.c:335 msgid "Enable media keys support" msgstr "Включване поддръжка на мултимедийни клавиши" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "Допълнителни опции за MPV:" #: src/gmpv_preferences_dialog.c:371 msgid "General" msgstr "Общи" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "_Запазване" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "Предпочитания" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "Отваряне на файл" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "Отваряне на местоположение" #: src/gmpv_shortcuts_window.c:58 msgid "Add file to playlist" msgstr "Добавяне на файлове в списъка за изпълнение" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "Добавяне на местоположение в списъка за изпълнение" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "Показване на диалога с настройките" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "Показване/скриване на контролерите" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "Показване/скриване на списъка за изпълнение" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle fullscreen mode" msgstr "Превключване в режим на цял екран" #: src/gmpv_shortcuts_window.c:64 msgid "Leave fullscreen mode" msgstr "Изход от режима на цял екран" #: src/gmpv_shortcuts_window.c:65 msgid "Toggle OSD states between normal and playback time/duration" msgstr "" "Превключване в OSD режим между нормалното време и времето на " "възпроизвеждане/продължителност" #: src/gmpv_shortcuts_window.c:66 msgid "Show filename on the OSD" msgstr "Показване името на файла в OSD" #: src/gmpv_shortcuts_window.c:67 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "Показване на прогреса, оставащото време и продължителност в OSD" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 5 seconds" msgstr "Прескачане назад/напред с 5 секунди" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 1 second" msgstr "Прецизно прескачане назад/напред с 1 секунда" #: src/gmpv_shortcuts_window.c:72 msgid "Seek backward/forward 1 minute" msgstr "Прескачане назад/напред с 1 минута" #: src/gmpv_shortcuts_window.c:73 msgid "Exact seek backward/forward 5 seconds" msgstr "Прецизно прескачане назад/напред с 5 секунди" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to previous/next subtitle" msgstr "Преминаване към предишните/следващите субтитри" #: src/gmpv_shortcuts_window.c:75 msgid "Step backward/forward a single frame" msgstr "Стъпка назад/напред с един кадър" #: src/gmpv_shortcuts_window.c:76 msgid "Seek to the beginning of the previous/next chapter" msgstr "Преминаване към предишното/следващото заглавие" #: src/gmpv_shortcuts_window.c:79 msgid "Decrease/increase playback speed by 10%" msgstr "Намаляване/увеличаване скоростта на възпроизвеждане с 10%" #: src/gmpv_shortcuts_window.c:80 msgid "Halve/double current playback speed" msgstr "Намаляване наполовина/удвояване скоростта на изпълнение" #: src/gmpv_shortcuts_window.c:81 msgid "Reset playback speed to normal" msgstr "Нулиране скоростта на изпълнение до нормална стойност" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "Отиване назад/напред в списъка за изпълнение" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "Премахване на избраните елементи от списъка за изпълнение" #: src/gmpv_shortcuts_window.c:84 msgid "Save playlist" msgstr "Запазване на списъка за изпълнение" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "Задай/изчисти точки на повторение A-B" #: src/gmpv_shortcuts_window.c:86 msgid "Toggle infinite looping" msgstr "Включване/изключване на напрекъснатото повторение" #: src/gmpv_shortcuts_window.c:87 msgid "Pause or unpause" msgstr "Пауза и възобновяване" #: src/gmpv_shortcuts_window.c:88 msgid "Quit" msgstr "Изход" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "Запазване на текущата позиция на възпроизвеждане и изход" #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "Превъртане през аудио записите" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "Намаляване/увеличаване силата на звука" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "Заглушаване и пускане на звука" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "Задържане на аудиото с + / - 0,1 секунди" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "Превключване видимостта на субтитрите" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "Превъртане през наличните субтитри" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "Задържане на субтитрите с + / - 0,1 секунди" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "Превключване промяната стила на субтитрите SSA/ASS" #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "Преместване на субтитрите нагоре/надолу" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "Включване/изключване режим на VSFilter" #: src/gmpv_shortcuts_window.c:107 msgid "Cycle through video tracks" msgstr "Превъртане през видео записите" #: src/gmpv_shortcuts_window.c:108 msgid "Decrease/increase pan-and-scan range" msgstr "Намаляване/увеличаване диапазона на обхващане и сканиране" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot" msgstr "Направете снимка на екрана" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "Направете снимка на екрана без субтитри" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "Направете снимка на екрана с всичко в прозореца" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "Оразмеряване на видеото в половината от оригиналния размер" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "Оразмеряване на видеото в неговия оригинален размер" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "Оразмеряване на видеото в двоен размер спрямо оригинала" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "Настройка на контраста" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "Настройка на яркостта" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "Настройка на гамата" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "Настройка на наситеността" #: src/gmpv_shortcuts_window.c:119 msgid "Activate or deactivate deinterlacer" msgstr "Активирайте или деактивирайте деинтерлактора" #: src/gmpv_shortcuts_window.c:120 msgid "Cycle aspect ratio override" msgstr "Циклично презаписване на стойностите" #: src/gmpv_shortcuts_window.c:123 msgid "User Interface" msgstr "Потребителски интерфейс" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "Видео" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "Аудио" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "Субтитри" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "Възпроизвеждане" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "Търсене" #: src/gmpv_view.c:711 msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "" "Включването или изключването на вградената (Gnome 3) декорация изисква " "рестартиране за да влязат промените в сила." #: src/gmpv_view.c:1280 msgid "Add File to Playlist" msgstr "Добавяне на файл в списъка" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "Отваряне на файл" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "Добавяне местоположение до списък" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "Отвори местоположение" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "Зареди аудио запис…" #: src/gmpv_view.c:1349 msgid "Load Subtitle Track…" msgstr "Зареди файл със субтитри…" #: src/gmpv_view.c:1374 msgid "Save Playlist" msgstr "Запазване на списъка" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "GTK интерфейс за MPV" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "Kiril Kirilov , 2017." gnome-mpv-0.13/po/ca.po000066400000000000000000000460431317030365200147120ustar00rootroot00000000000000# Adolfo Jayme , 2016. #zanata # gnome-mpv , 2016. #zanata # gnome-mpv , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2016-08-16 23:25+0700\n" "PO-Revision-Date: 2017-08-02 12:11-0400\n" "Last-Translator: Copied by Zanata \n" "Language-Team: Catalan\n" "Language: ca\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1)\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "Habilita o inhabilita el tema fosc" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 msgid "Enable or disable client-side decorations" msgstr "Habilita o inhabilita les decoracions del client" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "" "Si el quadre de diàleg de selecció de fitxers haurà de recordar la darrera " "carpeta accedida" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "Opcions que passar a l’MPV" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 msgid "Path to mpv configuration file" msgstr "Camí al fitxer de configuració de l’MPV" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 msgid "Load or don't load mpv configuration file" msgstr "Carrega o no un fitxer de configuració de l’MPV" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 msgid "Path to mpv input configuration file" msgstr "Camí al fitxer de configuració d’entrada de l’MPV" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 msgid "Load or don't load mpv input configuration file" msgstr "Carrega o no un fitxer de configuració d’entrada de l’MPV" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 msgid "Width of the window" msgstr "Amplada de la finestra" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 msgid "Height of the window" msgstr "Alçada de la finestra" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 msgid "Volume of player" msgstr "Volum del reproductor" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "Amplada de la llista de reproducció" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "Mostra o amaga la llista de reproducció" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "URI de la darrera carpeta accedida" #: data/io.github.GnomeMpv.gschema.xml:10 msgid "" "Whether the settings has already been migrated from the previous version" msgstr "Si els paràmetres ja s’han migrat des d’una versió anterior" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:82 msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 msgid "Show or not show the controls" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "Frontal en GTK+ per a l’mpv" #: data/io.github.GnomeMpv.appdata.xml.in:12 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" "El GNOME MPV és un frontal senzill per a l’MPV, un reproductor multimèdia " "capaç de reproduir qualsevol format d’àudio i vídeo. S’ha dissenyat el GNOME" " MPV amb les directrius d’interfícies del GNOME, però no hi té cap " "dependència. El GNOME MPV també ofereix un paràmetre per inhabilitar la " "decoració del client (CSD) i millorar la compatibilitat amb altres sistemes " "diferents del GNOME." #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "Característiques:" #: data/io.github.GnomeMpv.appdata.xml.in:21 msgid "Drag and drop playlist" msgstr "" "La llista de reproducció es pot reorganitzar amb la tècnica d’arrossegar i " "deixar anar" #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "Loading external mpv configuration files" msgstr "Càrrega de fitxers de configuració externs de l’MPV" #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "Interfície per a MPRIS2 del D-Bus" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "La finestra principal amb la CSD inhabilitada" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "La finestra principal amb la llista de reproducció oberta" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "" #: src/gmpv_application.c:370 msgid "Playing" msgstr "En reproducció" #: src/gmpv_application.c:415 msgid "Show release version" msgstr "" #: src/gmpv_application.c:423 msgid "Enqueue" msgstr "" #: src/gmpv_application.c:431 msgid "Create a new window" msgstr "" #: src/gmpv_application.c:439 msgid "Don't connect to an already-running instance" msgstr "" #: src/gmpv_control_box.c:286 msgid "Pause" msgstr "Posa en pausa" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 msgid "Play" msgstr "Reprodueix" #: src/gmpv_control_box.c:436 msgid "Stop" msgstr "Atura" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "Avança" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "Rebobina" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "Capítol següent" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "Capítol anterior" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 msgid "Toggle Fullscreen" msgstr "Commuta la pantalla completa" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 msgid "Error" msgstr "Error" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "_Cancel·la" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "_Obre" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 msgid "All Files" msgstr "" #: src/gmpv_file_chooser.c:143 msgid "Media Files" msgstr "" #: src/gmpv_file_chooser.c:154 msgid "Audio Files" msgstr "" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "" #: src/gmpv_file_chooser.c:170 msgid "Image Files" msgstr "" #: src/gmpv_file_chooser.c:180 msgid "Subtitle Files" msgstr "" #: src/gmpv_menu.c:102 msgid "None" msgstr "Cap" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 msgid "Unknown" msgstr "Desconegut" #: src/gmpv_menu.c:150 msgid "_Load External…" msgstr "" #: src/gmpv_menu.c:243 msgid "_File" msgstr "_Fitxer" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "Obre una _ubicació" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "_Desa la llista de reproducció" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "_Surt" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "_Edita" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "_Preferències" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "Pista de _vídeo" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 msgid "_Audio Track" msgstr "Pista d’_àudio" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 msgid "S_ubtitle Track" msgstr "Pista de s_ubtítols" #: src/gmpv_menu.c:253 msgid "_View" msgstr "_Visualitza" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 msgid "_Toggle Playlist" msgstr "_Commuta la llista de reproducció" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "_Pantalla completa" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "Mida _normal" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 msgid "_Double Size" msgstr "Mida _doble" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 msgid "_Half Size" msgstr "_Meitat de la mida" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "_Ajuda" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 msgid "_Keyboard Shortcuts" msgstr "" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "_Quant a" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, fuzzy, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "La reproducció ha terminat de forma anòmala. Motiu: %s" #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "Ubicació:" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "No s’han pogut aplicar alguns paràmetres de l’MPV." #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "_Afegeix…" #: src/gmpv_playlist_widget.c:537 msgid "Add _Location…" msgstr "" #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "Llista de reproducció" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 msgid "Lua Scripts" msgstr "«Scripts» en Lua" #: src/gmpv_plugins_manager.c:299 #, fuzzy, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "No s’ha pogut copiar el fitxer de «%s» a «%s». Motiu: %s" #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "No s’ha trobat cap «script» en Lua" #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "Suprimeix" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "" "Esteu segur que voleu suprimir aquest «script»? Aquesta acció no es pot " "desfer." #: src/gmpv_plugins_manager_item.c:184 #, fuzzy, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "No s’ha pogut suprimir el fitxer «%s». Motiu: %s" #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "Interfície de l’usuari" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "Habilita les decoracions del client" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "Habilita el tema fosc" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "Recorda la ubicació del darrer fitxer" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr "Paràmetres de l’MPV" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "Carrega un fitxer de configuració de l’MPV" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr "Fitxer de configuració de l’MPV:" #: src/gmpv_preferences_dialog.c:314 msgid "Keybindings" msgstr "Assignacions de tecles" #: src/gmpv_preferences_dialog.c:317 msgid "Load MPV input configuration file" msgstr "Carrega un fitxer de configuració d’entrada de l’MPV" #: src/gmpv_preferences_dialog.c:320 msgid "MPV input configuration file:" msgstr "Fitxer de configuració d’entrada de l’MPV:" #: src/gmpv_preferences_dialog.c:323 msgid "Miscellaneous" msgstr "Altres" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "" #: src/gmpv_preferences_dialog.c:335 msgid "Enable media keys support" msgstr "" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "Opcions addicionals de l’MPV:" #: src/gmpv_preferences_dialog.c:371 msgid "General" msgstr "Generals" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "_Desa" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "Preferències" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "Obre un fitxer" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "Obre una ubicació" #: src/gmpv_shortcuts_window.c:58 msgid "Add file to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "Mostra el quadre de diàleg Preferències" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "Commuta la llista de reproducció" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle fullscreen mode" msgstr "Commuta el mode de pantalla completa" #: src/gmpv_shortcuts_window.c:64 msgid "Leave fullscreen mode" msgstr "Surt del mode de pantalla completa" #: src/gmpv_shortcuts_window.c:65 msgid "Toggle OSD states between normal and playback time/duration" msgstr "" #: src/gmpv_shortcuts_window.c:66 msgid "Show filename on the OSD" msgstr "" #: src/gmpv_shortcuts_window.c:67 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 5 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 1 second" msgstr "" #: src/gmpv_shortcuts_window.c:72 msgid "Seek backward/forward 1 minute" msgstr "" #: src/gmpv_shortcuts_window.c:73 msgid "Exact seek backward/forward 5 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to previous/next subtitle" msgstr "" #: src/gmpv_shortcuts_window.c:75 msgid "Step backward/forward a single frame" msgstr "" #: src/gmpv_shortcuts_window.c:76 msgid "Seek to the beginning of the previous/next chapter" msgstr "" #: src/gmpv_shortcuts_window.c:79 msgid "Decrease/increase playback speed by 10%" msgstr "" #: src/gmpv_shortcuts_window.c:80 msgid "Halve/double current playback speed" msgstr "" #: src/gmpv_shortcuts_window.c:81 msgid "Reset playback speed to normal" msgstr "" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "Treu l’element seleccionat de la llista" #: src/gmpv_shortcuts_window.c:84 msgid "Save playlist" msgstr "Desa la llista de reproducció" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "" #: src/gmpv_shortcuts_window.c:86 msgid "Toggle infinite looping" msgstr "" #: src/gmpv_shortcuts_window.c:87 msgid "Pause or unpause" msgstr "" #: src/gmpv_shortcuts_window.c:88 msgid "Quit" msgstr "Surt" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "" #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "" #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "" #: src/gmpv_shortcuts_window.c:107 msgid "Cycle through video tracks" msgstr "" #: src/gmpv_shortcuts_window.c:108 msgid "Decrease/increase pan-and-scan range" msgstr "" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot" msgstr "" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "" #: src/gmpv_shortcuts_window.c:119 msgid "Activate or deactivate deinterlacer" msgstr "" #: src/gmpv_shortcuts_window.c:120 msgid "Cycle aspect ratio override" msgstr "" #: src/gmpv_shortcuts_window.c:123 msgid "User Interface" msgstr "" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "" #: src/gmpv_view.c:711 msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "" #: src/gmpv_view.c:1280 msgid "Add File to Playlist" msgstr "Afegeix un fitxer a una llista de reproducció" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "Obre un fitxer" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "Obre una ubicació" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "" #: src/gmpv_view.c:1349 msgid "Load Subtitle Track…" msgstr "" #: src/gmpv_view.c:1374 msgid "Save Playlist" msgstr "Desa la llista de reproducció" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "Un frontal en GTK per a l’MPV" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "Adolfo Jayme Barrientos " gnome-mpv-0.13/po/cs.po000066400000000000000000000526161317030365200147370ustar00rootroot00000000000000# Czech translations for gnome-mpv package # gnome-mpv # Copyright (C) 2015 THE gnome-mpv'S COPYRIGHT HOLDER # This file is distributed under the same license as the gnome-mpv package. # Tomáš Marný, 2015. # gnome-mpv , 2015. #zanata # Marek Suchánek , 2016. #zanata # gnome-mpv , 2016. #zanata # Marek Suchánek , 2017. #zanata # gnome-mpv , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: gnome-mpv 0.2\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2015-11-23 10:58-0500\n" "PO-Revision-Date: 2017-08-02 12:11-0400\n" "Last-Translator: Copied by Zanata \n" "Language-Team: \n" "Language: cs\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=3; plural=(n==1) ? 0 : (n>=2 && n<=4) ? 1 : 2\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "Zapnout nebo vypnout tmavý motiv" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 msgid "Enable or disable client-side decorations" msgstr "Zapnout nebo vypnout dekorace na straně klienta" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "Zda si má dialog pro výběr souborů pamatovat poslední umístění" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "Přepínače pro mpv" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 msgid "Path to mpv configuration file" msgstr "Cesta ke konfiguračnímu souboru mpv" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 msgid "Load or don't load mpv configuration file" msgstr "Načíst nebo nenačíst konfigurační soubor mpv" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 msgid "Path to mpv input configuration file" msgstr "Cesta ke konfiguračnímu souboru vstupu mpv" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 msgid "Load or don't load mpv input configuration file" msgstr "Načíst nebo nenačíst konfigurační soubor vstupu mpv" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 msgid "Width of the window" msgstr "Šířka okna" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 msgid "Height of the window" msgstr "Výška okna" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 msgid "Volume of player" msgstr "Hlasitost přehrávání" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "Šířka seznamu přehrávání" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "Zobrazit nebo nezobrazit seznam přehrávání" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "Cesta k poslední použité složce" #: data/io.github.GnomeMpv.gschema.xml:10 msgid "" "Whether the settings has already been migrated from the previous version" msgstr "Zda už byly předvolby konvertovány ze staré na novou verzi" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "Zda v okenním režimu použít plovoucí ovládací prvky" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:82 msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 msgid "Show or not show the controls" msgstr "Zobrazit nebo nezobrazit ovládací tlačítka" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "GTK+ rozhraní nad mpv" #: data/io.github.GnomeMpv.appdata.xml.in:12 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" "GNOME MPV je jednoduché rozhraní vytvořené v GTK+ pro mpv, což je velice " "schopný přehrávač, který dokáže přehrát prakticky jakýkoliv formát videa i " "zvuku. Vzhled GNOME MPV se zakládá na konvencích GNOME, ale přitom na " "žádných knihovnách GNOME nezávisí. Navíc GNOME MPV umožňuje vypnout okenní " "dekorace na straně klienta (CSD), aby lépe zapadal do jiných prostředí." #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "Nabízí:" #: data/io.github.GnomeMpv.appdata.xml.in:21 msgid "Drag and drop playlist" msgstr "Seznam přehrávání („playlist“) s možností přetáhnout soubory myší" #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "Loading external mpv configuration files" msgstr "Načítání externího konfiguračního souboru pro mpv" #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "Rozhraní MPRIS2 D-Bus" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "Hlavní okno s vypnutými dekoracemi na straně klienta" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "Hlavní okno s otevřeným seznamem přehrávání" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "gnome-mpv" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "" #: src/gmpv_application.c:370 msgid "Playing" msgstr "Hraje" #: src/gmpv_application.c:415 msgid "Show release version" msgstr "Zobrazit verzi vydání" #: src/gmpv_application.c:423 msgid "Enqueue" msgstr "Zařadit do fronty" #: src/gmpv_application.c:431 msgid "Create a new window" msgstr "" #: src/gmpv_application.c:439 msgid "Don't connect to an already-running instance" msgstr "Nepřipojovat k již běžící instanci" #: src/gmpv_control_box.c:286 msgid "Pause" msgstr "Pozastavit" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 msgid "Play" msgstr "Přehrát" #: src/gmpv_control_box.c:436 msgid "Stop" msgstr "Zastavit" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "Vpřed" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "Zpět" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "Další kapitola" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "Předchozí kapitola" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 msgid "Toggle Fullscreen" msgstr "Zobrazení na celou obrazovku" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 msgid "Error" msgstr "Chyba" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "_Zrušit" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "_Otevřít" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 msgid "All Files" msgstr "Všechny soubory" #: src/gmpv_file_chooser.c:143 msgid "Media Files" msgstr "Soubory médií" #: src/gmpv_file_chooser.c:154 msgid "Audio Files" msgstr "Soubory zvuku" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "Soubory videa" #: src/gmpv_file_chooser.c:170 msgid "Image Files" msgstr "Soubory obrázků" #: src/gmpv_file_chooser.c:180 msgid "Subtitle Files" msgstr "Soubory titulků" #: src/gmpv_menu.c:102 msgid "None" msgstr "Nic" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 msgid "Unknown" msgstr "Neznámý" #: src/gmpv_menu.c:150 msgid "_Load External…" msgstr "_Načíst externí…" #: src/gmpv_menu.c:243 msgid "_File" msgstr "_Soubor" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "_Otevřít umístění" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "_Uložit seznam přehrávání" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "U_končit" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "Up_ravit" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "_Předvolby" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "Stopa _videa" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 msgid "_Audio Track" msgstr "Stopa _zvuku" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 msgid "S_ubtitle Track" msgstr "_Titulky" #: src/gmpv_menu.c:253 msgid "_View" msgstr "Zo_brazit" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "Přepnout ovládání" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 msgid "_Toggle Playlist" msgstr "_Přepnout seznam přehrávání" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "_Celá obrazovka" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "_Normální velikost" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 msgid "_Double Size" msgstr "_Dvojnásobná velikost" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 msgid "_Half Size" msgstr "_Poloviční velikost" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "_Nápověda" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 msgid "_Keyboard Shortcuts" msgstr "_Klávesové zkratky" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "_O aplikaci" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, fuzzy, fuzzy, fuzzy, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "Přehrávání bylo nečekaně ukončeno. Důvod: %s." #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "Umístění:" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "Nebylo možno uplatnit jednu nebo více předvoleb MPV." #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "_Přidat…" #: src/gmpv_playlist_widget.c:537 msgid "Add _Location…" msgstr "Přidat _umístění…" #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "Seznam přehrávání" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "Přidat skript Lua" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 msgid "Lua Scripts" msgstr "Skripty Lua" #: src/gmpv_plugins_manager.c:299 #, fuzzy, fuzzy, fuzzy, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "Selhalo kopírování souboru z ‚%s‘ do ‚%s‘. Důvod: %s" #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "Skript Lua nenalezen" #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "Odstranit" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "Určitě si přejete tento skript odstranit? Akci nelze vrátit zpět." #: src/gmpv_plugins_manager_item.c:184 #, fuzzy, fuzzy, fuzzy, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "Selhalo smazání souboru ‚%s‘. Důvod: %s" #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "Uživatelské rozhraní" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "Povolit dekorace na straně klienta" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "Povolit tmavý motiv" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "Použít v okenním režimu plovoucí ovládání" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "Pamatovat si umístění posledního souboru" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr "Nastavení MPV" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "Načíst konfigurační soubor MPV" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr "Konfigurační soubor MPV:" #: src/gmpv_preferences_dialog.c:314 msgid "Keybindings" msgstr "Klávesové zkratky" #: src/gmpv_preferences_dialog.c:317 msgid "Load MPV input configuration file" msgstr "Načíst vstupní konfigurační soubor MPV" #: src/gmpv_preferences_dialog.c:320 msgid "MPV input configuration file:" msgstr "Vstupní konfigurační soubor MPV:" #: src/gmpv_preferences_dialog.c:323 msgid "Miscellaneous" msgstr "Různé" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "" #: src/gmpv_preferences_dialog.c:335 msgid "Enable media keys support" msgstr "" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "Extra možnosti MPV:" #: src/gmpv_preferences_dialog.c:371 msgid "General" msgstr "Obecné" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "_Uložit" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "Předvolby" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "Otevřít soubor" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "Otevřít umístění" #: src/gmpv_shortcuts_window.c:58 msgid "Add file to playlist" msgstr "Přidat soubory do seznamu přehrávání" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "Přidat umístění do seznamu přehrávání" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "Otevřít předvolby" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "Přepnout ovládání" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "Přepnout seznam přehrávání" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle fullscreen mode" msgstr "Přepnout zobrazení na celou obrazovku" #: src/gmpv_shortcuts_window.c:64 msgid "Leave fullscreen mode" msgstr "Opustit celou obrazovku" #: src/gmpv_shortcuts_window.c:65 msgid "Toggle OSD states between normal and playback time/duration" msgstr "Přepnout zprávy na obrazovce (normální nebo čas přehrávání)" #: src/gmpv_shortcuts_window.c:66 msgid "Show filename on the OSD" msgstr "Ukazovat na obrazovce název souboru" #: src/gmpv_shortcuts_window.c:67 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "Ukazovat na obrazovce postup, uplynulý čas a celkový čas" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 5 seconds" msgstr "Skok zpět o 5 sekund" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 1 second" msgstr "Přesný skok zpět o 1 sekundu" #: src/gmpv_shortcuts_window.c:72 msgid "Seek backward/forward 1 minute" msgstr "Skok zpět/vpřed o 1 minutu" #: src/gmpv_shortcuts_window.c:73 msgid "Exact seek backward/forward 5 seconds" msgstr "Přesný skok zpět/vpřed o 5 sekund" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to previous/next subtitle" msgstr "Skok k předchozím/dalším titulkům" #: src/gmpv_shortcuts_window.c:75 msgid "Step backward/forward a single frame" msgstr "Krok zpět/vpřed po jednotlivém snímku" #: src/gmpv_shortcuts_window.c:76 msgid "Seek to the beginning of the previous/next chapter" msgstr "Skok na začátek předchozí/další kapitoly" #: src/gmpv_shortcuts_window.c:79 msgid "Decrease/increase playback speed by 10%" msgstr "Zpomalit/zrychlit přehrávání o 10 %" #: src/gmpv_shortcuts_window.c:80 msgid "Halve/double current playback speed" msgstr "Snížit na polovinu / zdvojnásobit rychlost přehrávání" #: src/gmpv_shortcuts_window.c:81 msgid "Reset playback speed to normal" msgstr "Obnovit normální rychlost přehrávání" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "Jít v seznamu přehrávání zpět/vpřed" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "Odstranit vybranou položku v seznamu přehrávání" #: src/gmpv_shortcuts_window.c:84 msgid "Save playlist" msgstr "Uložit seznam přehrávání" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "Nastavit/smazat A-B body smyčky" #: src/gmpv_shortcuts_window.c:86 msgid "Toggle infinite looping" msgstr "Přepnout opakování" #: src/gmpv_shortcuts_window.c:87 msgid "Pause or unpause" msgstr "Pozastavit nebo hrát dál" #: src/gmpv_shortcuts_window.c:88 msgid "Quit" msgstr "Ukončit" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "Uložit pozici přehrávání a ukončit" #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "Procházet zvukové stopy" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "Snížit/zvýšit hlasitost" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "Ztlumit nebo obnovit hlasitost" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "Posunout zvukovou stupu o +/- 0,1 sekundy" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "Přepnout viditelnost titulků" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "Procházet načtené titulky" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "Posunout stupu titulků o +/- 0,1 sekundy" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "Přepnout styl titulků SSA/ASS" #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "Posunout titulky nahoru/dolů" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "Přepnout mód kompatibility poměru stran VSFilter" #: src/gmpv_shortcuts_window.c:107 msgid "Cycle through video tracks" msgstr "Procházet stopy videa" #: src/gmpv_shortcuts_window.c:108 msgid "Decrease/increase pan-and-scan range" msgstr "Snížit/zvýšit rozsah ořezávání videa s jiným poměrem stran" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot" msgstr "Pořídit snímek obrazovky" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "Pořídit snímek obrazovky, bez titulků" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "Pořídit snímek obrazovky, tak, jak se okno zobrazuje" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "Zmenšit na poloviční velikost videa" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "Obnovit původní velikost videa" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "Zvětšit na dvojnásobnou velikost videa" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "Upravit konstrast" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "Upravit jas" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "Upravit svítivost (gamma)" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "Upravit sytost" #: src/gmpv_shortcuts_window.c:119 msgid "Activate or deactivate deinterlacer" msgstr "Zapnout nebo vypnout odstranění prokládání" #: src/gmpv_shortcuts_window.c:120 msgid "Cycle aspect ratio override" msgstr "Procházet přepsání poměru stran" #: src/gmpv_shortcuts_window.c:123 msgid "User Interface" msgstr "Uživatelské rozhraní" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "Video" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "Zvuk" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "Titulky" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "Přehrávání" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "Posouvání" #: src/gmpv_view.c:711 msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "" "Aby se projevilo povolení nebo zakázání dekorací na straně klienta, je nutný" " restart aplikace" #: src/gmpv_view.c:1280 msgid "Add File to Playlist" msgstr "_Přidat soubory do seznamu přehrávání" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "Otevřít soubor" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "Přidat umístění do seznamu přehrávání" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "Otevřít umístění" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "Načíst zvukovou stopu…" #: src/gmpv_view.c:1349 msgid "Load Subtitle Track…" msgstr "Načíst stopu titulků…" #: src/gmpv_view.c:1374 msgid "Save Playlist" msgstr "_Uložit seznam přehrávání" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "GTK frontend pro MPV" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "Tomáš Marný" gnome-mpv-0.13/po/de_DE.po000066400000000000000000000523231317030365200152650ustar00rootroot00000000000000# German (de_DE) translations for gnome-mpv package. # gnome-mpv # Copyright (C) 2015 THE gnome-mpv'S COPYRIGHT HOLDER # This file is distributed under the same license as the gnone-mpv package. # Vincent Bermel , 2015. # gnome-mpv , 2015. #zanata # Vincent Bermel , 2016. #zanata # gnome-mpv , 2016. #zanata # Vincent Bermel , 2017. #zanata # gnome-mpv , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: gnome-mpv 0.6\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2015-11-23 10:58-0500\n" "PO-Revision-Date: 2017-08-05 05:05-0400\n" "Last-Translator: Vincent Bermel \n" "Language-Team: German Translations\n" "Language: de-DE\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1);\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "Dunkles Thema verwenden" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 msgid "Enable or disable client-side decorations" msgstr "Kombinierte Titel-/Menüleiste (CSD)" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "Speicherort der zuletzt gespielten Datei merken" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "MPV-Einstellungen" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 msgid "Path to mpv configuration file" msgstr "MPV-Konfigurationsdatei" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 msgid "Load or don't load mpv configuration file" msgstr "MPV-Konfiguration aus Datei laden" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 msgid "Path to mpv input configuration file" msgstr "Datei mit MPV-Tastenbelegungen" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 msgid "Load or don't load mpv input configuration file" msgstr "MPV-Konfiguration aus Datei laden" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 msgid "Width of the window" msgstr "Fensterbreite" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 msgid "Height of the window" msgstr "Fensterhöhe" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 msgid "Volume of player" msgstr "Lautstärke" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "Breite der Wiedergabeliste" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "Wiedergabeliste anzeigen" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "Zuletzt geöffnetes Verzeichnis" #: data/io.github.GnomeMpv.gschema.xml:10 msgid "" "Whether the settings has already been migrated from the previous version" msgstr "Ob Einstellungen schon von der vorherigen Version übernommen wurden" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "" "Ob im Fenstermodus ausblendende Bedienelemente verwendet werden sollen" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "Ob Steuerung über MPRIS aktiviert werden soll" #: data/io.github.GnomeMpv.gschema.xml:82 msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "Ob mittels GNOME-Settings-Daemon Medientasten aktiviert werden sollen" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 msgid "Show or not show the controls" msgstr "Wiedergabesteuerung anzeigen" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "Eine GTK-Oberfläche für den Medienspieler mpv" #: data/io.github.GnomeMpv.appdata.xml.in:12 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" "GNOME MPV ist eine einfache auf GTK+ basierende Oberfläche für den mpv " "Mediaplayer. Mittels mpv können so gut wie alle Video- und Audioformate " "abgespielt werden. GNOME MPV ist gemäß der GNOME HIG gestaltet, hat jedoch " "keine Abhängigkeiten zu GNOME-Bibliotheken. Weiterhin kann die CSD-" "Titelleiste für bessere Integration in Nicht-GNOME-Systeme deaktiviert " "werden." #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "Funktionen:" #: data/io.github.GnomeMpv.appdata.xml.in:21 msgid "Drag and drop playlist" msgstr "Wiedergabeliste mit Drag and Drop-Unterstützung" #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "Loading external mpv configuration files" msgstr "Laden externer mpv-Konfigurationsdateien" #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "MPRIS2 D-Bus Schnittstelle" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "Das Hauptfenster ohne CSD-Titelleiste" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "Das Hauptfenster mit Wiedergabeliste" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "Neues Fenster" #: src/gmpv_application.c:370 #, fuzzy msgid "Playing" msgstr "Wiedergabe" #: src/gmpv_application.c:415 msgid "Show release version" msgstr "Release-Version anzeigen" #: src/gmpv_application.c:423 msgid "Enqueue" msgstr "In Warteschlange aufnehmen" #: src/gmpv_application.c:431 msgid "Create a new window" msgstr "Neues Fenster aufrufen" #: src/gmpv_application.c:439 msgid "Don't connect to an already-running instance" msgstr "Nicht mit einer bereits laufenden Instanz verbinden" #: src/gmpv_control_box.c:286 msgid "Pause" msgstr "Pause" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 msgid "Play" msgstr "Abspielen" #: src/gmpv_control_box.c:436 msgid "Stop" msgstr "Stoppen" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "Vorspulen" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "Zurückspulen" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "Weiterspringen" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "Zurückspringen" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 msgid "Toggle Fullscreen" msgstr "Vollbild" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 msgid "Error" msgstr "Fehler" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "_Abbrechen" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "Ö_ffnen" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 msgid "All Files" msgstr "Alle Dateien" #: src/gmpv_file_chooser.c:143 msgid "Media Files" msgstr "Mediendateien" #: src/gmpv_file_chooser.c:154 msgid "Audio Files" msgstr "Audiodateien" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "Videodateien" #: src/gmpv_file_chooser.c:170 msgid "Image Files" msgstr "Bilddateien" #: src/gmpv_file_chooser.c:180 msgid "Subtitle Files" msgstr "Untertiteldateien" #: src/gmpv_menu.c:102 msgid "None" msgstr "Keine" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 msgid "Unknown" msgstr "Originalspur" #: src/gmpv_menu.c:150 msgid "_Load External…" msgstr "_Importieren" #: src/gmpv_menu.c:243 msgid "_File" msgstr "_Datei" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "_Adresse öffnen" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "Wiedergabeliste _speichern" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "_Beenden" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "_Bearbeiten" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "_Einstellungen" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "_Videospur" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 msgid "_Audio Track" msgstr "_Tonspur" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 msgid "S_ubtitle Track" msgstr "_Untertitel" #: src/gmpv_menu.c:253 msgid "_View" msgstr "_Ansicht" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "Wiedergabe_steuerung ein/aus" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 msgid "_Toggle Playlist" msgstr "_Wiedergabeliste ein/aus" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "_Vollbild" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "_Ursprüngliche Videogröße" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 msgid "_Double Size" msgstr "_Doppelte Videogröße" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 msgid "_Half Size" msgstr "_Halbe Videogröße" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "_Hilfe" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 msgid "_Keyboard Shortcuts" msgstr "_Tastenkürzel" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "_Info" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, fuzzy, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "Wiedergabe wurde abgebrochen. Grund: %s." #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "Adresse (lokal oder Web):" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "MPV-Optionen konnten nicht angewendet werden." #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "_Hinzufügen" #: src/gmpv_playlist_widget.c:537 msgid "Add _Location…" msgstr "Verzeichnis oder URL hinzufügen" #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "_Zufällige Wiedergabe" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "_Wiederholen" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "Wiedergabeliste" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "Lua-Skript hinzufügen" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 msgid "Lua Scripts" msgstr "Lua-Skripte" #: src/gmpv_plugins_manager.c:299 #, fuzzy, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "Datei konnte nicht von '%s' nach '%s' kopiert werden. Grund: %s." #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "Es wurde kein Lua-Skript gefunden." #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "Entfernen" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "Wollen Sie dieses Skript unwiderruflich entfernen?" #: src/gmpv_plugins_manager_item.c:184 #, fuzzy, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "Datei '%s' konnte nicht gelöscht werden. Grund: %s." #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "Benutzeroberfläche" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "Kombinierte Titel-/Menüleiste (CSD)" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "Dunkles Thema verwenden" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "Ausblendende Bedienelemente in Fenstermodus" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "Speicherort der zuletzt gespielten Datei merken" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr "MPV-Einstellungen" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "MPV-Konfiguration aus Datei laden" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr "MPV-Konfigurationsdatei" #: src/gmpv_preferences_dialog.c:314 msgid "Keybindings" msgstr "Tastenbelegungen" #: src/gmpv_preferences_dialog.c:317 msgid "Load MPV input configuration file" msgstr "MPV-Tastenbelegung aus Datei laden" #: src/gmpv_preferences_dialog.c:320 msgid "MPV input configuration file:" msgstr "Datei mit MPV-Tastenbelegungen" #: src/gmpv_preferences_dialog.c:323 msgid "Miscellaneous" msgstr "Sonstiges" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "MPRIS-Unterstützung aktivieren" #: src/gmpv_preferences_dialog.c:335 msgid "Enable media keys support" msgstr "Medientasten unterstützen" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "Weitere Optionen für MPV" #: src/gmpv_preferences_dialog.c:371 msgid "General" msgstr "Allgemein" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "_Speichern" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "Einstellungen" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "Öffnen" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "Adresse öffnen" #: src/gmpv_shortcuts_window.c:58 msgid "Add file to playlist" msgstr "Datei zur Widergabeliste hinzufügen" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "Ort zur Wiedergabeliste hinzufügen" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "Einstellungen anzeigen" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "Wiedergabesteuerung ein/aus" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "Wiedergabeliste ein/aus" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle fullscreen mode" msgstr "Vollbild" #: src/gmpv_shortcuts_window.c:64 msgid "Leave fullscreen mode" msgstr "Vollbildmodus verlassen" #: src/gmpv_shortcuts_window.c:65 msgid "Toggle OSD states between normal and playback time/duration" msgstr "Wiedergabeposition einblenden/ausblenden" #: src/gmpv_shortcuts_window.c:66 msgid "Show filename on the OSD" msgstr "Dateiname kurzzeitig einblenden" #: src/gmpv_shortcuts_window.c:67 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "Wiedergabeposition kurzzeitig einblenden" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 5 seconds" msgstr "15 Sekunden zurück/vorwärts springen" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 1 second" msgstr "Eine Sekunde zurück/vorwärts springen" #: src/gmpv_shortcuts_window.c:72 msgid "Seek backward/forward 1 minute" msgstr "Eine Minute zurück/vorwärts springen" #: src/gmpv_shortcuts_window.c:73 msgid "Exact seek backward/forward 5 seconds" msgstr "5 Sekunden zurück/vorwärts springen" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to previous/next subtitle" msgstr "Zum vorherigen/nächsten Untertitel springen" #: src/gmpv_shortcuts_window.c:75 msgid "Step backward/forward a single frame" msgstr "Einzelnen Frame zurück/nach vorne springen" #: src/gmpv_shortcuts_window.c:76 msgid "Seek to the beginning of the previous/next chapter" msgstr "Zum vorherigen/nächsten Kapitel springen" #: src/gmpv_shortcuts_window.c:79 msgid "Decrease/increase playback speed by 10%" msgstr "Wiedergabegeschwindigkeit um 10% verringern/erhöhen" #: src/gmpv_shortcuts_window.c:80 msgid "Halve/double current playback speed" msgstr "Wiedergabegeschwindigkeit halbieren/verdoppeln" #: src/gmpv_shortcuts_window.c:81 msgid "Reset playback speed to normal" msgstr "Wiedergabegeschwindigkeit auf Normalwert zurücksetzen" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "Vorheriger/nächster Titel der Wiedergabeliste" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "Ausgewählten Titel aus Wiedergabeliste entfernen" #: src/gmpv_shortcuts_window.c:84 msgid "Save playlist" msgstr "Wiedergabeliste speichern" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "Loop-Begrenzungen setzen/entfernen" #: src/gmpv_shortcuts_window.c:86 msgid "Toggle infinite looping" msgstr "Endloses Loopen aktivieren" #: src/gmpv_shortcuts_window.c:87 msgid "Pause or unpause" msgstr "Pause oder Fortsetzen" #: src/gmpv_shortcuts_window.c:88 msgid "Quit" msgstr "Beenden" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "Wiedergabeposition merken und beenden" #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "Zwischen verfügbaren Tonspuren springen" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "Lautstärke verringern/erhöhen" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "Stummschalten" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "Tonspur in Schritten von 0.1 Sekunden vor/zurück verschieben" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "Untertitel anzeigen/ausblenden" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "Zwischen verfügbaren Untertiteln springen" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "Untertitel in Schritten von 0.1 Sekunden verschieben" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "ASS-Untertitelstil erzwingen" #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "Untertitel höher/tiefer anzeigen" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "Streckungskorrektor für Untertiteldarstellung ein/aus" #: src/gmpv_shortcuts_window.c:107 msgid "Cycle through video tracks" msgstr "Zwischen verfügbaren Videospuren springen" #: src/gmpv_shortcuts_window.c:108 msgid "Decrease/increase pan-and-scan range" msgstr "Videoformat schrittweise einpassen (Pan & Scan)" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot" msgstr "Bildschirmfoto aufnehmen" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "Bildschirmfoto ohne Untertitel aufnehmen" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "Foto des Fensterinhalts aufnehmen" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "Halbe Videogröße" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "Ursprüngliche Videogröße" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "Doppelte Videogröße" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "Kontrast anpassen" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "Helligkeit anpassen" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "Gammawert anpassen" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "Farbsättigung anpassen" #: src/gmpv_shortcuts_window.c:119 msgid "Activate or deactivate deinterlacer" msgstr "Deinterlacing (de)aktivieren" #: src/gmpv_shortcuts_window.c:120 msgid "Cycle aspect ratio override" msgstr "Seitenverhältnis umschalten" #: src/gmpv_shortcuts_window.c:123 msgid "User Interface" msgstr "Benutzeroberfläche" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "Videowiedergabe" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "Audiowiedergabe" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "Untertitel" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "Wiedergabesteuerung" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "Wiedergabeposition" #: src/gmpv_view.c:711 msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "Die Änderung der Fensterdekoration erfordert einen Neustart." #: src/gmpv_view.c:1280 msgid "Add File to Playlist" msgstr "Datei zur _Wiedergabeliste hinzufügen" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "Datei öffnen" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "Verzeichnis oder URL zur Wiedergabeliste hinzufügen" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "Adresse öffnen" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "Audiospur laden..." #: src/gmpv_view.c:1349 msgid "Load Subtitle Track…" msgstr "Untertitel laden..." #: src/gmpv_view.c:1374 msgid "Save Playlist" msgstr "Wiedergabeliste speichern" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "Eine GTK-Oberfläche für MPV" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "Vincent Bermel" gnome-mpv-0.13/po/es.po000066400000000000000000000526431317030365200147410ustar00rootroot00000000000000# SOME DESCRIPTIVE TITLE. # Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER # This file is distributed under the same license as the PACKAGE package. # FIRST AUTHOR , YEAR. # Eddy Castillo , 2017. #zanata # Sergio M , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2016-08-16 23:25+0700\n" "PO-Revision-Date: 2017-09-22 03:40-0400\n" "Last-Translator: Sergio M \n" "Language-Team: Spanish\n" "Language: es\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1)\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "Habilitar el tema oscuro" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 msgid "Enable or disable client-side decorations" msgstr "Habilitar decoraciones del lado del cliente" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "Recordar la localización del último archivo abierto" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "Opciones extra de MPV" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 msgid "Path to mpv configuration file" msgstr "Archivo de configuración de MPV:" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 msgid "Load or don't load mpv configuration file" msgstr "Cargar archivo de configuración de MPV" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 msgid "Path to mpv input configuration file" msgstr "Archivo de configuración de entrada de MPV:" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 msgid "Load or don't load mpv input configuration file" msgstr "Cargar archivo de configuración de entrada de MPV" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 msgid "Width of the window" msgstr "Ancho de la ventana" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 msgid "Height of the window" msgstr "Altura de la ventan" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 msgid "Volume of player" msgstr "Volumen del reproductor" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "Ancho de la lista de reproducción" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "Mostrar la lista de reproducción" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "Dirección de la ultima carpeta accedida" #: data/io.github.GnomeMpv.gschema.xml:10 msgid "" "Whether the settings has already been migrated from the previous version" msgstr "Se ha efectuado una migración de preferencias de la última version" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "Usar controles flotantes en modo ventana" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "Habilitar soporte MPRIS" #: data/io.github.GnomeMpv.gschema.xml:82 msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "Habilitar teclas multimedia de Gnome" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 msgid "Show or not show the controls" msgstr "Mostrar los controles" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "Frontend de GTK+ para MPV" #: data/io.github.GnomeMpv.appdata.xml.in:12 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" "GNOME MPV es un frontend simple de GTK+ para MPV, un poderoso reproductor " "multimedia capaz de reproducir virtualmente todos los formatos de audio y " "video. El diseño de MPV esta basado en GNOME HIG, aunque no depende de " "ninguna librería de GNOME. Además, GNOME MPV ofrece una opción para " "deshabilitar decoraciones del lado del cliente (CSD) para mejorar la " "compatibilidad para sistemas no basados en GNOME. " #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "Características:" #: data/io.github.GnomeMpv.appdata.xml.in:21 msgid "Drag and drop playlist" msgstr "Arrastrar y soltar a la playlist" #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "Loading external mpv configuration files" msgstr "Cargar archivos de configuración externos de MPV" #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "Interfaz MPRIS2 D-Bus" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "" "La ventana principal con decoraciones del lado del cliente deshabilitadas" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "La ventana principal con la lista de reproducción abierta" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "gnome-mpv" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "Nueva Ventana" #: src/gmpv_application.c:370 msgid "Playing" msgstr "Reproduciendo" #: src/gmpv_application.c:415 msgid "Show release version" msgstr "Mostrar versión" #: src/gmpv_application.c:423 msgid "Enqueue" msgstr "Encolar" #: src/gmpv_application.c:431 msgid "Create a new window" msgstr "Crear nueva ventana" #: src/gmpv_application.c:439 msgid "Don't connect to an already-running instance" msgstr "No conectarse a una instancia que ya se está ejecutando" #: src/gmpv_control_box.c:286 msgid "Pause" msgstr "Pausa" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 msgid "Play" msgstr "Reproducir" #: src/gmpv_control_box.c:436 msgid "Stop" msgstr "Deneter" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "Adelantar" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "Rebobinar" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "Capítulo siguiente" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "Capítulo anterior" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 msgid "Toggle Fullscreen" msgstr "Pantalla completa" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 msgid "Error" msgstr "Error" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "_Cancelar" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "_Abrir" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 msgid "All Files" msgstr "Todos los archivos" #: src/gmpv_file_chooser.c:143 msgid "Media Files" msgstr "Archivos multimedia" #: src/gmpv_file_chooser.c:154 msgid "Audio Files" msgstr "Archivos de Audio" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "Archivos de video" #: src/gmpv_file_chooser.c:170 msgid "Image Files" msgstr "Archivos de imágen" #: src/gmpv_file_chooser.c:180 msgid "Subtitle Files" msgstr "Archivos de subtítulo" #: src/gmpv_menu.c:102 msgid "None" msgstr "Ninguno" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 msgid "Unknown" msgstr "Desconocido" #: src/gmpv_menu.c:150 msgid "_Load External…" msgstr "Cargar externo..." #: src/gmpv_menu.c:243 msgid "_File" msgstr "Archivo" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "Abrir _Localización" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "Abrir lista de reproducción" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "Salir" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "_Editar" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "_Preferencias" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "Pista de _video" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 msgid "_Audio Track" msgstr "Pista de _audio" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 msgid "S_ubtitle Track" msgstr "Pista de S_ubtítulo" #: src/gmpv_menu.c:253 msgid "_View" msgstr "_Vista" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "Habilitar con_troles" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 msgid "_Toggle Playlist" msgstr "Habilitar lista de reproducción" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "Pantalla completa" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "Tamaño _normal" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 msgid "_Double Size" msgstr "Tamaño _doble" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 msgid "_Half Size" msgstr "Mitad de tamaño" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "Ayuda" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 msgid "_Keyboard Shortcuts" msgstr "Atajos de teclado" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "_Acerda de" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, fuzzy, fuzzy, fuzzy, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "La reproducción ha terminado abruptamente. Razón: %s." #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "Localización:" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "Fallo al aplicar uno o más opciones de MPV." #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "_Agregar..." #: src/gmpv_playlist_widget.c:537 msgid "Add _Location…" msgstr "Agregar _Localización" #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "_Mezclar" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "Repetir" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "Lista de reproducción" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "Agregar Script Lua" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 msgid "Lua Scripts" msgstr "Scripts de Lua" #: src/gmpv_plugins_manager.c:299 #, fuzzy, fuzzy, fuzzy, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "Fallo al copiar de '%s' a '%s'. Razón: %s" #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "No se encontró Lua Script" #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "Quitar" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "" "Seguro que quieres quitar este script? Esta acción no se puede deshacer." #: src/gmpv_plugins_manager_item.c:184 #, fuzzy, fuzzy, fuzzy, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "Fallo en eliminar archivo '%s'. Razón: %s" #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "Interfaz de usuario" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "Habilitar decoraciones del lado del cliente" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "Habilitar tema oscuro" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "Usar controles flotantes en modo ventana" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "Recordar ubicación del último archivo" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr "Configuración de MPV" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "Cargar archivo de configuración de MPV:" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr "Archivo de configuración de MPV:" #: src/gmpv_preferences_dialog.c:314 msgid "Keybindings" msgstr "Atajos" #: src/gmpv_preferences_dialog.c:317 msgid "Load MPV input configuration file" msgstr "Cargar archivo de configuración de entrada de MVP" #: src/gmpv_preferences_dialog.c:320 msgid "MPV input configuration file:" msgstr "Archivo de configuración de entrada de MPV" #: src/gmpv_preferences_dialog.c:323 msgid "Miscellaneous" msgstr "Misceláneo" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "Habilitar soporte MPRIS" #: src/gmpv_preferences_dialog.c:335 msgid "Enable media keys support" msgstr "Habilitar teclas multimedia" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "Opciones extra de MPV:" #: src/gmpv_preferences_dialog.c:371 msgid "General" msgstr "General" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "Guardar" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "Preferencias" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "Abrir archivo" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "Abrir ubicación" #: src/gmpv_shortcuts_window.c:58 msgid "Add file to playlist" msgstr "Agregar archivo a la lista de reproducción" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "Añadir ubicación a la lista de reproducción" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "Mostrar diálogo de preferencias" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "Habilitar controles" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "Habilitar lista de reproducción" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle fullscreen mode" msgstr "Habitlitar pantalla completa" #: src/gmpv_shortcuts_window.c:64 msgid "Leave fullscreen mode" msgstr "Dejar pantalla completa" #: src/gmpv_shortcuts_window.c:65 msgid "Toggle OSD states between normal and playback time/duration" msgstr "Habilitar estados del OSD entre normal y tiempo/duraciónreproducción " #: src/gmpv_shortcuts_window.c:66 msgid "Show filename on the OSD" msgstr "Mostrar nombre de archivo en el OSD" #: src/gmpv_shortcuts_window.c:67 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "Mostrar progreso, tiempo transcurrido y duración en el OSD" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 5 seconds" msgstr "Desplazarse atrás/adelante 5 segundos" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 1 second" msgstr "Desplazarse atrás/adelante exactamente 1 segundo" #: src/gmpv_shortcuts_window.c:72 msgid "Seek backward/forward 1 minute" msgstr "Desplazarse atrás/adelante 1 minuto" #: src/gmpv_shortcuts_window.c:73 msgid "Exact seek backward/forward 5 seconds" msgstr "Desplazarse atrás/adelante exactamente 5 segundos" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to previous/next subtitle" msgstr "Desplazarse al subtítulo previo/siguiente" #: src/gmpv_shortcuts_window.c:75 msgid "Step backward/forward a single frame" msgstr "Desplazarse atrás/adelante un solo cuadro" #: src/gmpv_shortcuts_window.c:76 msgid "Seek to the beginning of the previous/next chapter" msgstr "Ir al principio del siguiente/anterior capítulo" #: src/gmpv_shortcuts_window.c:79 msgid "Decrease/increase playback speed by 10%" msgstr "Aumentar/Disminuir velocidad de reproducción un 10%" #: src/gmpv_shortcuts_window.c:80 msgid "Halve/double current playback speed" msgstr "Reducir a la mitad/Duplicar velocidad de reproducción" #: src/gmpv_shortcuts_window.c:81 msgid "Reset playback speed to normal" msgstr "Normalizar velocidad de reproducción" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "Ir atrás/adelante en la lista de reproducción" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "Quitar item seleccionado de lista de reproducción" #: src/gmpv_shortcuts_window.c:84 msgid "Save playlist" msgstr "Guardar lista de reproducción" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "Fijar/eliminar puntos A-B de la repetición" #: src/gmpv_shortcuts_window.c:86 msgid "Toggle infinite looping" msgstr "Habilitar repetición infinita" #: src/gmpv_shortcuts_window.c:87 msgid "Pause or unpause" msgstr "Pausar o despausar" #: src/gmpv_shortcuts_window.c:88 msgid "Quit" msgstr "Quitar" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "Guardar posición actual de reproducción y salir" #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "Ciclar a través de las pistas de audio" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "Disminuir/aumentar volumen" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "Silenciar/No silenciar" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "Ajustar retraso de audio +/- 0.1 segundos" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "Habilitar visibilidad del subtítulo" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "Ciclar a través de los subtitulos disponibles" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "Ajustar retraso de subtitulos +/- 0.1 segundos" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "Habilitar soreescritura de estilo de subtitulos SSA/ASS " #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "Mover subtitulos arriba/abajo" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "Habilitar modo de compatibilidad de aspecto de VSFilter" #: src/gmpv_shortcuts_window.c:107 msgid "Cycle through video tracks" msgstr "Ciclar a traves de las pistas de video" #: src/gmpv_shortcuts_window.c:108 msgid "Decrease/increase pan-and-scan range" msgstr "Disminuir/aumentar rango de pan-and-scan" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot" msgstr "Tomar una captura de pantalla" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "Tomar una captura de pantalla, sin subtitulos" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "Tomar una captura de pantalla, tal como se muestra en la ventana" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "Cambiar tamaño de video a la mitad del original" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "Cambiar tamaño de video a su tamaño original" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "Cambiar tamaño de video a l doble del original" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "Ajustar contraste" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "Ajustar brillo" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "Ajustar gamma" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "Ajustar saturación" #: src/gmpv_shortcuts_window.c:119 msgid "Activate or deactivate deinterlacer" msgstr "Activar/Desactivar interlacer" #: src/gmpv_shortcuts_window.c:120 msgid "Cycle aspect ratio override" msgstr "Ciclar relación de aspecto" #: src/gmpv_shortcuts_window.c:123 msgid "User Interface" msgstr "Interfaz de usuario" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "Video" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "Audio" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "Subtítulo" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "Reproducción" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "Buscando" #: src/gmpv_view.c:711 msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "" "Habilitar o deshabilitar decoraciones del lado de cliente requiere reiniciar" " para tomar efecto " #: src/gmpv_view.c:1280 msgid "Add File to Playlist" msgstr "Agregar archivo a la lista de reproducción" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "Abrir archivo" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "Agregar ubicación de la lista de reproducción" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "Abrir ubicación" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "Cargar Pista de Audio..." #: src/gmpv_view.c:1349 msgid "Load Subtitle Track…" msgstr "Cargar Pista de Subtitulos..." #: src/gmpv_view.c:1374 msgid "Save Playlist" msgstr "Guardar lista de reproducción" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "Una interfaz GTK para MPV" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "Sergio D. Márquez " gnome-mpv-0.13/po/fr.po000066400000000000000000000455471317030365200147460ustar00rootroot00000000000000# French translations for gnome-mpv package # gnome-mpvパッケージに対する日本語翻訳. # Copyright (C) 2015 The gnome-mpv'u copyright holder # This file is distributed under the same license as the gnome-mpv package. # Harenome Ranaivorarivony Razanajato , 2015. # gnome-mpv , 2015. #zanata # gnome-mpv , 2016. #zanata # gnome-mpv , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: gnome-mpv 0.5\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2015-11-23 10:58-0500\n" "PO-Revision-Date: 2017-08-02 12:10-0400\n" "Last-Translator: Copied by Zanata \n" "Language-Team: Français\n" "Language: fr\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n > 1);\n" "X-Generator: Zanata 3.9.6\n" "X-Poedit-Basepath: ../src\n" "X-Poedit-SearchPath-0: .\n" "X-Poedit-SearchPathExcluded-0: mpv.c\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "Activer le thème sombre" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 msgid "Enable or disable client-side decorations" msgstr "" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 msgid "Path to mpv configuration file" msgstr "" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 msgid "Load or don't load mpv configuration file" msgstr "" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 msgid "Path to mpv input configuration file" msgstr "" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 msgid "Load or don't load mpv input configuration file" msgstr "" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 msgid "Width of the window" msgstr "Largeur de la fenêtre" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 msgid "Height of the window" msgstr "Hauteur de la fenêtre" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 msgid "Volume of player" msgstr "" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "Afficher ou cacher la liste de lecture" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:10 msgid "" "Whether the settings has already been migrated from the previous version" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:82 msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 msgid "Show or not show the controls" msgstr "Afficher ou cacher les contrôles" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "Interface en GTK+ pour mpv" #: data/io.github.GnomeMpv.appdata.xml.in:12 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "Fonctionnalités" #: data/io.github.GnomeMpv.appdata.xml.in:21 msgid "Drag and drop playlist" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "Loading external mpv configuration files" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "" #: src/gmpv_application.c:370 msgid "Playing" msgstr "En cours de lecture" #: src/gmpv_application.c:415 msgid "Show release version" msgstr "" #: src/gmpv_application.c:423 msgid "Enqueue" msgstr "" #: src/gmpv_application.c:431 msgid "Create a new window" msgstr "" #: src/gmpv_application.c:439 msgid "Don't connect to an already-running instance" msgstr "" #: src/gmpv_control_box.c:286 msgid "Pause" msgstr "Pause" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 msgid "Play" msgstr "Lecture" #: src/gmpv_control_box.c:436 msgid "Stop" msgstr "Arret" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "Avancer" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "Reculer" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "Chapitre suivant" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "Chapitre précédant" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 msgid "Toggle Fullscreen" msgstr "Plein écran" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 msgid "Error" msgstr "Erreur" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "_Annuler" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "_Ouvrir" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 msgid "All Files" msgstr "" #: src/gmpv_file_chooser.c:143 msgid "Media Files" msgstr "" #: src/gmpv_file_chooser.c:154 msgid "Audio Files" msgstr "" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "" #: src/gmpv_file_chooser.c:170 msgid "Image Files" msgstr "" #: src/gmpv_file_chooser.c:180 msgid "Subtitle Files" msgstr "" #: src/gmpv_menu.c:102 msgid "None" msgstr "Vide" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 msgid "Unknown" msgstr "Inconnu" #: src/gmpv_menu.c:150 msgid "_Load External…" msgstr "" #: src/gmpv_menu.c:243 msgid "_File" msgstr "_Fichier" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "Ouvrir un _répertoire" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "_Enregistrer la liste de lecture" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "_Quitter" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "É_diter" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "_Préférences" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "Piste _vidéo" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 msgid "_Audio Track" msgstr "Piste _audio" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 msgid "S_ubtitle Track" msgstr "Sous-titres" #: src/gmpv_menu.c:253 msgid "_View" msgstr "_Vue" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "Afficher les contrôles" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 msgid "_Toggle Playlist" msgstr "_Afficher la liste de lecture" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "_Plein écran" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "Taille _Normale" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 msgid "_Double Size" msgstr "Taille _Double" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 msgid "_Half Size" msgstr "Taille _Moitié" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "_Aide" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 msgid "_Keyboard Shortcuts" msgstr "_Raccourcis clavier" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "À _propos" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "La lecture a été interrompue pour la raison suivante : %s" #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "Emplacement:" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "" #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "_Ajouter" #: src/gmpv_playlist_widget.c:537 msgid "Add _Location…" msgstr "Ajouter un _Emplacement" #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "Liste de lecture" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "Ajouter un script Lua" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 msgid "Lua Scripts" msgstr "Scripts Lua" #: src/gmpv_plugins_manager.c:299 #, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "" "Impossible de copier le fichier de '%s' vers '%s' pour la raison suivante : " "%s" #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "Aucun script Lua trouvé" #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "Supprimer" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "" "Êtes vous sur de vouloir supprimer ce script ? Cette action est irréversible" #: src/gmpv_plugins_manager_item.c:184 #, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "Impossible de supprimer le fichier '%s' pour la raison suivante : %s" #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "Interface utilisateur" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "Activer les décorations fenêtre" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "Activer le thème sombre" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "Se souvenir de l'emplacement du dernier fichier ouvert" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr "Configuration MPV" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "Charger un fichier de configuration MPV" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr "Fichier de configuration MPV:" #: src/gmpv_preferences_dialog.c:314 msgid "Keybindings" msgstr "Raccourcis clavier" #: src/gmpv_preferences_dialog.c:317 msgid "Load MPV input configuration file" msgstr "Charger un fichier de configuration des raccourcis clavier MPV" #: src/gmpv_preferences_dialog.c:320 msgid "MPV input configuration file:" msgstr "Fichier de configuration des raccourcis clavier MPV:" #: src/gmpv_preferences_dialog.c:323 msgid "Miscellaneous" msgstr "Divers" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "" #: src/gmpv_preferences_dialog.c:335 msgid "Enable media keys support" msgstr "" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "Options supplémentaires pour MPV" #: src/gmpv_preferences_dialog.c:371 msgid "General" msgstr "Général" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "_Enregistrer" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "Préférences" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "Ouvrir un fichier" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "Ouvrir un emplacement" #: src/gmpv_shortcuts_window.c:58 msgid "Add file to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "Afficher les préférences" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "Afficher les contrôles" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "Afficher la liste de lecture" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle fullscreen mode" msgstr "Plein écran" #: src/gmpv_shortcuts_window.c:64 msgid "Leave fullscreen mode" msgstr "Quitter le mode plein écran" #: src/gmpv_shortcuts_window.c:65 msgid "Toggle OSD states between normal and playback time/duration" msgstr "" #: src/gmpv_shortcuts_window.c:66 msgid "Show filename on the OSD" msgstr "" #: src/gmpv_shortcuts_window.c:67 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 5 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 1 second" msgstr "" #: src/gmpv_shortcuts_window.c:72 msgid "Seek backward/forward 1 minute" msgstr "" #: src/gmpv_shortcuts_window.c:73 msgid "Exact seek backward/forward 5 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to previous/next subtitle" msgstr "" #: src/gmpv_shortcuts_window.c:75 msgid "Step backward/forward a single frame" msgstr "" #: src/gmpv_shortcuts_window.c:76 msgid "Seek to the beginning of the previous/next chapter" msgstr "" #: src/gmpv_shortcuts_window.c:79 msgid "Decrease/increase playback speed by 10%" msgstr "Reduire/Augmenter la vitesse de lecture de 10%" #: src/gmpv_shortcuts_window.c:80 msgid "Halve/double current playback speed" msgstr "Reduire de moitié ou doubler la vitesse de lecture actuelle" #: src/gmpv_shortcuts_window.c:81 msgid "Reset playback speed to normal" msgstr "Réinitialiser la vitesse de lecture" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "Aller en arrière/en avant dans la liste de lecture" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "Supprimer l'élément sélectionné de la liste de lecture" #: src/gmpv_shortcuts_window.c:84 msgid "Save playlist" msgstr "Sauvegarder la liste de lecture" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "Définir/enlever les repères de boucle A-B" #: src/gmpv_shortcuts_window.c:86 msgid "Toggle infinite looping" msgstr "" #: src/gmpv_shortcuts_window.c:87 msgid "Pause or unpause" msgstr "Pause/reprendre" #: src/gmpv_shortcuts_window.c:88 msgid "Quit" msgstr "Quitter" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "" #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "Diminuer/augmenter le volume" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "Muet" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "" #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "Déplacer les sous titres en haut/bas" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "" #: src/gmpv_shortcuts_window.c:107 msgid "Cycle through video tracks" msgstr "" #: src/gmpv_shortcuts_window.c:108 msgid "Decrease/increase pan-and-scan range" msgstr "" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot" msgstr "Prendre une capture d'écran" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "Prendre une capture d'écran, sans les sous-titres" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "Réduire de moitié la taille de la vidéo" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "Redimensionner la vidéo à sa taille d'origine" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "Doubler la taille de la vidéo" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "Ajuster le contraste" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "Ajuster la luminosité" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "Ajuster la saturation" #: src/gmpv_shortcuts_window.c:119 msgid "Activate or deactivate deinterlacer" msgstr "" #: src/gmpv_shortcuts_window.c:120 msgid "Cycle aspect ratio override" msgstr "" #: src/gmpv_shortcuts_window.c:123 msgid "User Interface" msgstr "Interface de l'utilisateur" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "Vidéo" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "Audio" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "Sous-titre" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "Lecture" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "" #: src/gmpv_view.c:711 msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "" #: src/gmpv_view.c:1280 #, fuzzy msgid "Add File to Playlist" msgstr "_Afficher la liste de lecture" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "Ouvrir un fichier" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "Ajouter l'emplacement à la liste de lecture" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "Ouvrir un emplacement" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "" #: src/gmpv_view.c:1349 msgid "Load Subtitle Track…" msgstr "" #: src/gmpv_view.c:1374 #, fuzzy msgid "Save Playlist" msgstr "_Enregistrer la liste de lecture" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "Une interface GTK pour MPV" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "Harenome Ranaivorarivony Razanajato" gnome-mpv-0.13/po/hu.po000066400000000000000000000513551317030365200147450ustar00rootroot00000000000000# Bendegúz Gyönki , 2016. #zanata # gnome-mpv , 2016. #zanata # Bendegúz Gyönki , 2017. #zanata # gnome-mpv , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2016-08-16 23:25+0700\n" "PO-Revision-Date: 2017-08-02 12:11-0400\n" "Last-Translator: Copied by Zanata \n" "Language-Team: Hungarian\n" "Language: hu\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1)\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "Sötét téma engedélyezése/tiltása" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 msgid "Enable or disable client-side decorations" msgstr "Kliensoldali díszítések engedélyezése/tiltása" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "Az mpv-nek átadandó opciók" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 msgid "Path to mpv configuration file" msgstr "Az mpv konfigurációs fájl útvonala" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 msgid "Load or don't load mpv configuration file" msgstr "" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 msgid "Path to mpv input configuration file" msgstr "Az mpv bemeneti konfigurációs fájl útvonala" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 msgid "Load or don't load mpv input configuration file" msgstr "" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 msgid "Width of the window" msgstr "Az ablak szélessége" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 msgid "Height of the window" msgstr "Az ablak magassága" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 msgid "Volume of player" msgstr "A lejátszó hangereje" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "A lejátszási lista szélessége" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:10 msgid "" "Whether the settings has already been migrated from the previous version" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:82 msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 msgid "Show or not show the controls" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "GTK+ felület az mpv-hez" #: data/io.github.GnomeMpv.appdata.xml.in:12 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" "A GNOME MPV egy egyszerű GTK+ felület az mpv-hez, egy rendkívül erőteljes " "médialejátszóhoz, amely gyakorlatilag az összes videó- és hangformátum " "lejátszására képes. A GNOME MPV dizájnja a GNOME HIG-en alapszik, habár nem " "függ egyetlen GNOME könyvtártól sem. A GNOME MPV továbbá lehetővé teszi a " "kliensoldali díszítések letiltását a GNOME-tól eltérő rendszerekkel való " "jobb kompatibilitás érdekében." #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "Funkciók:" #: data/io.github.GnomeMpv.appdata.xml.in:21 msgid "Drag and drop playlist" msgstr "Fogd és vidd lejátszási lista" #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "Loading external mpv configuration files" msgstr "Külső mpv konfigurációs fájlok betöltése" #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "MPRIS2 D-Bus interfész" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "A főablak letiltott díszítésekkel" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "A főablak megnyitott lejátszási listával" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "" #: src/gmpv_application.c:370 msgid "Playing" msgstr "" #: src/gmpv_application.c:415 #, fuzzy msgid "Show release version" msgstr "Kiadási verzió megjelenítése" #: src/gmpv_application.c:423 #, fuzzy msgid "Enqueue" msgstr "Sorba állítás" #: src/gmpv_application.c:431 msgid "Create a new window" msgstr "" #: src/gmpv_application.c:439 msgid "Don't connect to an already-running instance" msgstr "Ne csatlakozzon egy már futó példányhoz" #: src/gmpv_control_box.c:286 msgid "Pause" msgstr "Szünet" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 msgid "Play" msgstr "Lejátszás" #: src/gmpv_control_box.c:436 msgid "Stop" msgstr "Megállítás" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "Előretekerés" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "Visszatekerés" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "Következő fejezet" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "Előző fejezet" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 msgid "Toggle Fullscreen" msgstr "Átváltás teljes képernyőre" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 msgid "Error" msgstr "Hiba" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "_Mégse" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "_Megnyitás" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 msgid "All Files" msgstr "" #: src/gmpv_file_chooser.c:143 msgid "Media Files" msgstr "" #: src/gmpv_file_chooser.c:154 msgid "Audio Files" msgstr "" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "" #: src/gmpv_file_chooser.c:170 msgid "Image Files" msgstr "" #: src/gmpv_file_chooser.c:180 msgid "Subtitle Files" msgstr "" #: src/gmpv_menu.c:102 msgid "None" msgstr "Egyik sem" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 msgid "Unknown" msgstr "Ismeretlen" #: src/gmpv_menu.c:150 msgid "_Load External…" msgstr "_Külső betöltése..." #: src/gmpv_menu.c:243 msgid "_File" msgstr "_Fájl" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "_Hely megnyitása" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "Lejátszási lista _mentése" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "_Kilépés" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "_Szerkesztés" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "_Beállítások" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "_Videósáv" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 msgid "_Audio Track" msgstr "_Hangsáv" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 msgid "S_ubtitle Track" msgstr "F_eliratsáv" #: src/gmpv_menu.c:253 msgid "_View" msgstr "_Nézet" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "_Vezérlők be-/kikapcsolása" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 msgid "_Toggle Playlist" msgstr "_Lejátszási lista be-/kikapcsolása" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "_Teljes képernyő" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "_Normál méret" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 msgid "_Double Size" msgstr "_Kétszeres méret" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 msgid "_Half Size" msgstr "_Fele méret" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "_Súgó" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 msgid "_Keyboard Shortcuts" msgstr "_Billentyűkombinációk" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "_Névjegy" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, fuzzy, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "A lejátszás nem megfelelően lett leállítva. Ok: %s." #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "Hely:" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "Egy vagy több MPV beállítás alkalmazása nem sikerült" #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "_Hozzáadás..." #: src/gmpv_playlist_widget.c:537 msgid "Add _Location…" msgstr "_Hely hozzáadása..." #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "Lejátszási lista" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "Lua parancsfájl hozzáadása" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 msgid "Lua Scripts" msgstr "Lua parancsfájlok" #: src/gmpv_plugins_manager.c:299 #, fuzzy, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "A fájl másolása innen: „%s\", ide: „%s\" nem sikerült. Ok: %s" #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "Nem található Lua parancsfájl" #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "Eltávolítás" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "" "Biztosan el akarja távolítani ezt a parancsfájlt? Ez a művelet nem vonható " "vissza." #: src/gmpv_plugins_manager_item.c:184 #, fuzzy, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "„%s\" fájl törlése nem sikerült. Ok: %s" #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "Felhasználói felület" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "Kliensoldali díszítések engedélyezése" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "Sötét téma engedélyezése" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "Az utolsó fájl pozíciójának megjegyzése" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr "MPV konfiguráció" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "MPV konfigurációs fájl betöltése" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr "MPV konfigurációs fájl:" #: src/gmpv_preferences_dialog.c:314 msgid "Keybindings" msgstr "Gyorsbillentyűk" #: src/gmpv_preferences_dialog.c:317 msgid "Load MPV input configuration file" msgstr "MPV beviteli konfigurációs fájl betöltése" #: src/gmpv_preferences_dialog.c:320 msgid "MPV input configuration file:" msgstr "MPV beviteli konfigurációs fájl:" #: src/gmpv_preferences_dialog.c:323 msgid "Miscellaneous" msgstr "Egyéb" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "" #: src/gmpv_preferences_dialog.c:335 msgid "Enable media keys support" msgstr "" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "Extra MPV beállítások:" #: src/gmpv_preferences_dialog.c:371 msgid "General" msgstr "Általános" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "_Mentés" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "Beállítások" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "Fájl megnyitása" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "Hely megnyitása" #: src/gmpv_shortcuts_window.c:58 msgid "Add file to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "Beállítások párbeszédablak mutatása" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "Vezérlők be-/kikapcsolása" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "Lejátszási lista be-/kikapcsolása" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle fullscreen mode" msgstr "Teljes képernyős mód be-/kikapcsolása" #: src/gmpv_shortcuts_window.c:64 msgid "Leave fullscreen mode" msgstr "Kilépés a teljes képernyős módból" #: src/gmpv_shortcuts_window.c:65 msgid "Toggle OSD states between normal and playback time/duration" msgstr "Váltás a normál és a lejátszási idő/hossz OSD között" #: src/gmpv_shortcuts_window.c:66 msgid "Show filename on the OSD" msgstr "Fájlnév megjelenítése az OSD-n" #: src/gmpv_shortcuts_window.c:67 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "" #: src/gmpv_shortcuts_window.c:70 #, fuzzy msgid "Seek backward/forward 5 seconds" msgstr "Visszatekerés/előretekerés 5 másodperccel" #: src/gmpv_shortcuts_window.c:71 #, fuzzy msgid "Exact seek backward/forward 1 second" msgstr "Visszatekerés/előretekerés pontosan 1 másodperccel" #: src/gmpv_shortcuts_window.c:72 #, fuzzy msgid "Seek backward/forward 1 minute" msgstr "Visszatekerés/előretekerés 1 perccel" #: src/gmpv_shortcuts_window.c:73 #, fuzzy msgid "Exact seek backward/forward 5 seconds" msgstr "Visszatekerés/előretekerés pontosan 5 másodperccel" #: src/gmpv_shortcuts_window.c:74 #, fuzzy msgid "Seek to previous/next subtitle" msgstr "Ugrás az előző/következő felirathoz" #: src/gmpv_shortcuts_window.c:75 #, fuzzy msgid "Step backward/forward a single frame" msgstr "Visszalépés/előrelépés egy képkockával" #: src/gmpv_shortcuts_window.c:76 #, fuzzy msgid "Seek to the beginning of the previous/next chapter" msgstr "Ugrás az előző/következő fejezet elejére" #: src/gmpv_shortcuts_window.c:79 #, fuzzy msgid "Decrease/increase playback speed by 10%" msgstr "Lejátszási sebesség csökkentése/növelése 10%-kal" #: src/gmpv_shortcuts_window.c:80 #, fuzzy msgid "Halve/double current playback speed" msgstr "Jelenlegi lejátszási sebesség felezése/duplázása" #: src/gmpv_shortcuts_window.c:81 #, fuzzy msgid "Reset playback speed to normal" msgstr "Normál lejátszási sebesség visszaállítása" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "Ugrás előre/hátra a lejátszási listában" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "Kiválasztott lejátszási elem eltávolítása" #: src/gmpv_shortcuts_window.c:84 msgid "Save playlist" msgstr "Lejátszási lista mentése" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "A-B ismétlési szakasz beállítása/törlése" #: src/gmpv_shortcuts_window.c:86 msgid "Toggle infinite looping" msgstr "Végtelen ismétlés be-/kikapcsolása" #: src/gmpv_shortcuts_window.c:87 msgid "Pause or unpause" msgstr "Szünet vagy folytatás" #: src/gmpv_shortcuts_window.c:88 msgid "Quit" msgstr "Kilépés" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "Jelenlegi lejátszási pozíció mentése és kilépés" #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "Váltás a hangsávok között" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "Hangerő csökkentése/növelése" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "Némítás be-/kikapcsolása" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "Hangsáv eltolásának beállítása 0,1 mp időközökkel" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "Felirat láthatóságának be-/kikapcsolása" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "Váltás az elérhető feliratok között" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "Feliratok eltolásának beállítása 0,1 mp időközökkel" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "SSA/ASS feliratstílus felülbírálásának be-/kikapcsolása" #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "Feliratok mozgatása fel/le" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "VSFilter képarány-kompatibilitási mód be-/kikapcsolása" #: src/gmpv_shortcuts_window.c:107 msgid "Cycle through video tracks" msgstr "Váltás a videósávok között" #: src/gmpv_shortcuts_window.c:108 msgid "Decrease/increase pan-and-scan range" msgstr "Pan-and-scan tartomány csökkentése/növelése" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot" msgstr "Képernyőkép készítése" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "Képernyőkép készítése feliratok nélkül" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "Képernyőkép készítése az ablak tartalmáról" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "Videó átméretezése az eredeti méret felére" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "Videó átméretezése az eredeti méretre" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "Videó átméretezése az eredeti méret kétszeresére" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "Kontraszt beállítása" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "Világosság beállítása" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "Gamma beállítása" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "Telítettség beállítása" #: src/gmpv_shortcuts_window.c:119 msgid "Activate or deactivate deinterlacer" msgstr "Váltottsorosság-mentesítés be-/kikapcsolása" #: src/gmpv_shortcuts_window.c:120 msgid "Cycle aspect ratio override" msgstr "" #: src/gmpv_shortcuts_window.c:123 msgid "User Interface" msgstr "Felhasználói felület" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "Videó" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "Hang" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "Felirat" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "Lejátszás" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "Tekerés" #: src/gmpv_view.c:711 msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "" #: src/gmpv_view.c:1280 msgid "Add File to Playlist" msgstr "Fájl hozzáadása a lejátszási listához" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "Fájl megnyitása" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "Hely hozzáadása a lejátszási listához" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "Hely megnyitása" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "" #: src/gmpv_view.c:1349 msgid "Load Subtitle Track…" msgstr "" #: src/gmpv_view.c:1374 msgid "Save Playlist" msgstr "Lejátszási lista mentése" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "Egy GTK felület az MPV-hez" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "" gnome-mpv-0.13/po/it.po000066400000000000000000000511071317030365200147400ustar00rootroot00000000000000# Dino Trevisani , 2016. #zanata # Luca , 2017. #zanata # gnome-mpv , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2016-08-16 23:25+0700\n" "PO-Revision-Date: 2017-08-02 12:11-0400\n" "Last-Translator: Copied by Zanata \n" "Language-Team: Italian\n" "Language: it\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1)\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "Attiva o disattiva il tema scuro" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 msgid "Enable or disable client-side decorations" msgstr "Attiva o disattiva le decorazioni client-side" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "Ricorda o meno l'ultima cartella visualizzata" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "Opzioni da inserire in MPV" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 msgid "Path to mpv configuration file" msgstr "Percorso del file di configurazione di MPV" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 msgid "Load or don't load mpv configuration file" msgstr "Carica il file di configurazione di MPV" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 msgid "Path to mpv input configuration file" msgstr "Percorso del file di configurazione dell'input di MPV" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 msgid "Load or don't load mpv input configuration file" msgstr "Carica il file di configurazione dell'input di MPV" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 msgid "Width of the window" msgstr "Larghezza finestra" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 msgid "Height of the window" msgstr "Altezza finestra" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 msgid "Volume of player" msgstr "Volume" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "Larghezza della playlist" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "Mostra o meno la playlist" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "Percorso dell'ultima cartella visualizzata" #: data/io.github.GnomeMpv.gschema.xml:10 msgid "" "Whether the settings has already been migrated from the previous version" msgstr "" "È stata gia effettuata la migrazione delle preferenze da una versione " "precedente" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "Mostra o meno i controlli fluttuanti in modalità finestra" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:82 msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 msgid "Show or not show the controls" msgstr "Mostra o meno i controlli" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "Un frontend in GTK+ per MPV" #: data/io.github.GnomeMpv.appdata.xml.in:12 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" "GNOME MPV è un semplice frontend in GTK+ per MPV, un potente media player " "capace di riprodurre potenzialmente ogni tipo di formato audio e video. Il " "design di GNOME MPV è basato sulle HIG di GNOME, tuttavia non dipende da " "nessuna delle sue librerie. GNOME MPV offre anche un'opzione per disattivare" " le decorazioni client-side (CSD) per una migliore compatibilità con i " "sistemi che non usano GNOME." #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "Caratteristiche:" #: data/io.github.GnomeMpv.appdata.xml.in:21 msgid "Drag and drop playlist" msgstr "Drag and drop della playlist" #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "Loading external mpv configuration files" msgstr "Carica un file di configurazione di MPV esterno" #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "Interfaccia MPRIS2 D-Bus" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "La finestra principale con le decorazioni client-side disattivate" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "La finestra principale con la playlist visualizzata" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "" #: src/gmpv_application.c:370 msgid "Playing" msgstr "In riproduzione" #: src/gmpv_application.c:415 msgid "Show release version" msgstr "Mostra versione della release" #: src/gmpv_application.c:423 msgid "Enqueue" msgstr "Accoda" #: src/gmpv_application.c:431 msgid "Create a new window" msgstr "" #: src/gmpv_application.c:439 msgid "Don't connect to an already-running instance" msgstr "Non usare un'istanza già in esecuzione" #: src/gmpv_control_box.c:286 msgid "Pause" msgstr "Pausa" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 msgid "Play" msgstr "Riproduci" #: src/gmpv_control_box.c:436 msgid "Stop" msgstr "Ferma" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "Vai avanti" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "Torna indietro" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "Capitolo successivo" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "Capitolo precedente" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 msgid "Toggle Fullscreen" msgstr "Attiva la modalità a schermo intero" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 msgid "Error" msgstr "Errore" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "Annulla" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "Apri" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 msgid "All Files" msgstr "Tutti i file" #: src/gmpv_file_chooser.c:143 msgid "Media Files" msgstr "" #: src/gmpv_file_chooser.c:154 msgid "Audio Files" msgstr "" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "" #: src/gmpv_file_chooser.c:170 msgid "Image Files" msgstr "" #: src/gmpv_file_chooser.c:180 msgid "Subtitle Files" msgstr "" #: src/gmpv_menu.c:102 msgid "None" msgstr "Nessuno" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 msgid "Unknown" msgstr "Sconosciuto" #: src/gmpv_menu.c:150 msgid "_Load External…" msgstr "Importa..." #: src/gmpv_menu.c:243 msgid "_File" msgstr "File" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "Apri posizione" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "Salva la playlist" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "Esci" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "Modifica" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "Preferenze" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "Traccia video" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 msgid "_Audio Track" msgstr "Traccia audio" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 msgid "S_ubtitle Track" msgstr "Traccia sottotitoli" #: src/gmpv_menu.c:253 msgid "_View" msgstr "Visualizza" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "Mostra o meno i controlli" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 msgid "_Toggle Playlist" msgstr "Mostra o meno la playlist" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "Modalità a schermo intero" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "Dimensioni normali" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 msgid "_Double Size" msgstr "Dimensioni raddoppiate" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 msgid "_Half Size" msgstr "Dimensioni dimezzate" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "Aiuto" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 msgid "_Keyboard Shortcuts" msgstr "Scorciatoie da tastiera" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "Informazioni" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, fuzzy, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "La riproduzione si è interrota in modo anomalo. Motivo: %s" #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "Posizione:" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "Impossibile applicare una o più opzioni di MPV" #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "Aggiungi" #: src/gmpv_playlist_widget.c:537 msgid "Add _Location…" msgstr "Aggiungi posizione" #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "Playlist" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "Aggiungi script in Lua" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 msgid "Lua Scripts" msgstr "Scritps in Lua" #: src/gmpv_plugins_manager.c:299 #, fuzzy, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "Impossibile copiare file da '%s' a '%s'. Motivo: %s" #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "Nessuno script in Lua trovato" #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "Rimuovi" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "" "Sei sicuro di voler cancellare questo script? Questa azione non può essere " "annullata." #: src/gmpv_plugins_manager_item.c:184 #, fuzzy, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "Impossible cancellare '%s'. Motivo: %s" #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "Interfaccia utente" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "Attiva le decorazioni client-side" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "Attiva tema scuro" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "Mostra i controlli fluttuanti in modalità finestra" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "Ricorda l'ultimo percorso dei file" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr "Configurazione di MPV" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "Carica il file di configurazione di MPV" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr "File di configurazione di MPV" #: src/gmpv_preferences_dialog.c:314 msgid "Keybindings" msgstr "Scorciatoie da tastiera" #: src/gmpv_preferences_dialog.c:317 msgid "Load MPV input configuration file" msgstr "Carica il file di configurazione dell'input di MPV" #: src/gmpv_preferences_dialog.c:320 msgid "MPV input configuration file:" msgstr "File di configurazione dell'input di MPV" #: src/gmpv_preferences_dialog.c:323 msgid "Miscellaneous" msgstr "Varie" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "" #: src/gmpv_preferences_dialog.c:335 msgid "Enable media keys support" msgstr "" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "Opzioni extra per MPV" #: src/gmpv_preferences_dialog.c:371 msgid "General" msgstr "Generale" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "Salva" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "Preferenze" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "Apri file" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "Apri posizione" #: src/gmpv_shortcuts_window.c:58 msgid "Add file to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "Mostra la finestra della preferenze" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "Mostra o meno i controlli" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "Mostra o meno la playlist" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle fullscreen mode" msgstr "Attiva la modalità a schermo intero" #: src/gmpv_shortcuts_window.c:64 msgid "Leave fullscreen mode" msgstr "Disattiva la modalità a schermo intero" #: src/gmpv_shortcuts_window.c:65 msgid "Toggle OSD states between normal and playback time/duration" msgstr "Attiva la visualizzazione in sovraimpressione" #: src/gmpv_shortcuts_window.c:66 msgid "Show filename on the OSD" msgstr "Mostra il nome del file in sovraimpressione" #: src/gmpv_shortcuts_window.c:67 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "Mostra tempo trascorso e durata in sovraimpressione" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 5 seconds" msgstr "Vai indietro/avanti di 5 secondi" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 1 second" msgstr "Vai indietro/avanti di 1 secondo preciso" #: src/gmpv_shortcuts_window.c:72 msgid "Seek backward/forward 1 minute" msgstr "Vai indietro/avanti di un 1 minuto" #: src/gmpv_shortcuts_window.c:73 msgid "Exact seek backward/forward 5 seconds" msgstr "Vai indietro/avanti di 5 secondi precisi" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to previous/next subtitle" msgstr "Vai ai sottotitoli precendenti/prossimi" #: src/gmpv_shortcuts_window.c:75 msgid "Step backward/forward a single frame" msgstr "Vai indietro/avanti di un singolo fotogramma" #: src/gmpv_shortcuts_window.c:76 msgid "Seek to the beginning of the previous/next chapter" msgstr "Vai all'inizio del capitolo precente/prossimo" #: src/gmpv_shortcuts_window.c:79 msgid "Decrease/increase playback speed by 10%" msgstr "Diminuisci/aumenta la velocità di riproduzione del 10%" #: src/gmpv_shortcuts_window.c:80 msgid "Halve/double current playback speed" msgstr "Dimezza/raddoppia la velocità di riproduzione corrente" #: src/gmpv_shortcuts_window.c:81 msgid "Reset playback speed to normal" msgstr "Ripristina la velocità di riproduzione normale" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "Vai indietro/avanti nella playlist" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "Rimuovi dalla playlist" #: src/gmpv_shortcuts_window.c:84 msgid "Save playlist" msgstr "Salva playlist" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "Imposta/rimuovi A-B loop" #: src/gmpv_shortcuts_window.c:86 msgid "Toggle infinite looping" msgstr "Attiva il loop continuo" #: src/gmpv_shortcuts_window.c:87 msgid "Pause or unpause" msgstr "Pausa o meno" #: src/gmpv_shortcuts_window.c:88 msgid "Quit" msgstr "Esci" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "Salva la posizione di riproduzione corrente ed esci " #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "Scegli fra le tracce audio avviabili" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "Diminusci/aumenta il volume" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "Muto o meno" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "Aggiusta il ritardo dell'audio di +/- 0.1 secondi" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "Attiva visualizzazione sottotitoli" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "Scegli fra i sottotitoli disponibili" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "Aggiusta il ritardo dei sottotitoli di +/- 0.1 secondi" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "Attiva la sovrascrittura dello stile dei sottotitoli SSA/ASS" #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "Sposta i sottotitoli su/giu" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "Attiva la modalità di compatibilità di aspetto per VSFilter" #: src/gmpv_shortcuts_window.c:107 msgid "Cycle through video tracks" msgstr "Scegli fra le tracce video disponibili" #: src/gmpv_shortcuts_window.c:108 msgid "Decrease/increase pan-and-scan range" msgstr "Diminuisci/aumenta il range pan-and-scan" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot" msgstr "Fai uno screenshot" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "Fai uno screenshot, senza sottotitoli" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "Fai uno screenshot, così come è la finestra" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "Dimezza la dimensione originale del video" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "Ripristina la dimensione originale del video" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "Raddoppia la dimensione originale del video" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "Modifica contrasto" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "Modifica luminosità" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "Modifica gamma" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "Modifica saturazione" #: src/gmpv_shortcuts_window.c:119 msgid "Activate or deactivate deinterlacer" msgstr "Attiva o disattiva il deinterlacciatore" #: src/gmpv_shortcuts_window.c:120 msgid "Cycle aspect ratio override" msgstr "Scegli fra le proporzioni di aspetto disponibili" #: src/gmpv_shortcuts_window.c:123 msgid "User Interface" msgstr "Interfaccia Utente" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "Video" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "Audio" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "Sottotitoli" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "Riproduzione" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "Ricerca" #: src/gmpv_view.c:711 msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "" #: src/gmpv_view.c:1280 msgid "Add File to Playlist" msgstr "Aggiungi file alla playlist" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "Apri file" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "Aggiungi posizione alla playlist" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "Apri posizione" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "" #: src/gmpv_view.c:1349 msgid "Load Subtitle Track…" msgstr "" #: src/gmpv_view.c:1374 msgid "Save Playlist" msgstr "Salva la playlist" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "Un frontend in GTK+ per MPV" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "Dino Trevisani" gnome-mpv-0.13/po/ja.po000066400000000000000000000444701317030365200147230ustar00rootroot00000000000000# Japanese translations for gnome-mpv package # gnome-mpvパッケージに対する日本語翻訳. # Copyright (C) 2015 THE gnome-mpv'S COPYRIGHT HOLDER # This file is distributed under the same license as the gnome-mpv package. # Tista , 2015. # gnome-mpv , 2015. #zanata # gnome-mpv , 2016. #zanata # gnome-mpv , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: gnome-mpv 0.2\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2015-11-23 10:58-0500\n" "PO-Revision-Date: 2017-10-08 08:36-0400\n" "Last-Translator: gnome-mpv \n" "Language-Team: Japanese <>\n" "Language: ja\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=1; plural=0;\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 #, fuzzy msgid "Enable or disable dark theme" msgstr "暗いテーマを有効または無効にする" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 #, fuzzy msgid "Enable or disable client-side decorations" msgstr "CSDを有効または無効にする" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 #, fuzzy msgid "Options to pass to mpv" msgstr "mpvに渡すオプション" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 #, fuzzy msgid "Path to mpv configuration file" msgstr "MPV設定ファイル" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 msgid "Load or don't load mpv configuration file" msgstr "" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 #, fuzzy msgid "Path to mpv input configuration file" msgstr "MPV入力設定ファイル" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 msgid "Load or don't load mpv input configuration file" msgstr "" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 #, fuzzy msgid "Width of the window" msgstr "ウィンドウの横幅" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 #, fuzzy msgid "Height of the window" msgstr "ウィンドウの高さ" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 msgid "Volume of player" msgstr "" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:10 msgid "" "Whether the settings has already been migrated from the previous version" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:82 msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 msgid "Show or not show the controls" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "MPVのGTKフロントエンド" #: data/io.github.GnomeMpv.appdata.xml.in:12 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:21 msgid "Drag and drop playlist" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "Loading external mpv configuration files" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "新しいウィンドウ" #: src/gmpv_application.c:370 #, fuzzy msgid "Playing" msgstr "プレイ中" #: src/gmpv_application.c:415 msgid "Show release version" msgstr "" #: src/gmpv_application.c:423 msgid "Enqueue" msgstr "" #: src/gmpv_application.c:431 #, fuzzy msgid "Create a new window" msgstr "新しいウィンドウを開きます" #: src/gmpv_application.c:439 msgid "Don't connect to an already-running instance" msgstr "" #: src/gmpv_control_box.c:286 #, fuzzy msgid "Pause" msgstr "一時停止" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 #, fuzzy msgid "Play" msgstr "プレー" #: src/gmpv_control_box.c:436 #, fuzzy msgid "Stop" msgstr "停止" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 #, fuzzy msgid "Toggle Fullscreen" msgstr "全面表示を切換える" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 #, fuzzy msgid "Error" msgstr "エラー" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "キャンセル(_C)" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "開く(_O)" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 #, fuzzy msgid "All Files" msgstr "全てのファイル" #: src/gmpv_file_chooser.c:143 #, fuzzy msgid "Media Files" msgstr "メディア" #: src/gmpv_file_chooser.c:154 #, fuzzy msgid "Audio Files" msgstr "音声" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "動画" #: src/gmpv_file_chooser.c:170 #, fuzzy msgid "Image Files" msgstr "画像" #: src/gmpv_file_chooser.c:180 #, fuzzy msgid "Subtitle Files" msgstr "字幕" #: src/gmpv_menu.c:102 #, fuzzy msgid "None" msgstr "なし" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 #, fuzzy msgid "Unknown" msgstr "不明" #: src/gmpv_menu.c:150 msgid "_Load External…" msgstr "" #: src/gmpv_menu.c:243 msgid "_File" msgstr "ファイル(_F)" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "開く場所(_L)" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "プレイリストの保存(_S)" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "終了(_Q)" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "編集(_E)" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "設定(_P)" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 #, fuzzy msgid "_Audio Track" msgstr "音声トラック (_A)" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 msgid "S_ubtitle Track" msgstr "" #: src/gmpv_menu.c:253 msgid "_View" msgstr "表示(_V)" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 msgid "_Toggle Playlist" msgstr "プレイリストの表示・非表示(_T)" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "全画面表示(_F)" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "通常のサイズ(_N)" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 msgid "_Double Size" msgstr "2倍のサイズ(_D)" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 msgid "_Half Size" msgstr "半分のサイズ(_H)" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "ヘルプ(_H)" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 #, fuzzy msgid "_Keyboard Shortcuts" msgstr "ショートカット" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "このアプリケーションについて(_A)" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, fuzzy, fuzzy, fuzzy, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "" #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "場所:" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "" #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "" #: src/gmpv_playlist_widget.c:537 msgid "Add _Location…" msgstr "" #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "プレイリスト" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 #, fuzzy msgid "Lua Scripts" msgstr "lua スクリプト" #: src/gmpv_plugins_manager.c:299 #, fuzzy, fuzzy, fuzzy, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "" #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "" #: src/gmpv_plugins_manager_item.c:69 #, fuzzy msgid "Remove" msgstr "削除" #: src/gmpv_plugins_manager_item.c:163 #, fuzzy msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "このスクリプトを削除してもよろしいですか?このアクションを元に戻すことはできません。" #: src/gmpv_plugins_manager_item.c:184 #, fuzzy, fuzzy, fuzzy, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "" #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "CSDを有効にする" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "暗いテーマを有効にする" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr "MPVの設定" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "MPV設定ファイルをロードする" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr "MPV設定ファイル:" #: src/gmpv_preferences_dialog.c:314 msgid "Keybindings" msgstr "キーバインド" #: src/gmpv_preferences_dialog.c:317 msgid "Load MPV input configuration file" msgstr "MPV入力設定ファイルをロードする" #: src/gmpv_preferences_dialog.c:320 msgid "MPV input configuration file:" msgstr "MPV入力設定ファイル:" #: src/gmpv_preferences_dialog.c:323 msgid "Miscellaneous" msgstr "その他" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "" #: src/gmpv_preferences_dialog.c:335 msgid "Enable media keys support" msgstr "" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "その他のMPVオプション:" #: src/gmpv_preferences_dialog.c:371 #, fuzzy msgid "General" msgstr "全般" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "保存(_S)" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "設定" #: src/gmpv_shortcuts_window.c:56 #, fuzzy msgid "Open file" msgstr "ファイルを開く" #: src/gmpv_shortcuts_window.c:57 #, fuzzy msgid "Open location" msgstr "場所を開く" #: src/gmpv_shortcuts_window.c:58 #, fuzzy msgid "Add file to playlist" msgstr "プレイリストにファイルを追加" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "" #: src/gmpv_shortcuts_window.c:63 #, fuzzy msgid "Toggle fullscreen mode" msgstr "全面表示を切換える" #: src/gmpv_shortcuts_window.c:64 #, fuzzy msgid "Leave fullscreen mode" msgstr "全画面表示を終了" #: src/gmpv_shortcuts_window.c:65 msgid "Toggle OSD states between normal and playback time/duration" msgstr "" #: src/gmpv_shortcuts_window.c:66 msgid "Show filename on the OSD" msgstr "" #: src/gmpv_shortcuts_window.c:67 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 5 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 1 second" msgstr "" #: src/gmpv_shortcuts_window.c:72 msgid "Seek backward/forward 1 minute" msgstr "" #: src/gmpv_shortcuts_window.c:73 msgid "Exact seek backward/forward 5 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to previous/next subtitle" msgstr "" #: src/gmpv_shortcuts_window.c:75 msgid "Step backward/forward a single frame" msgstr "" #: src/gmpv_shortcuts_window.c:76 msgid "Seek to the beginning of the previous/next chapter" msgstr "" #: src/gmpv_shortcuts_window.c:79 msgid "Decrease/increase playback speed by 10%" msgstr "" #: src/gmpv_shortcuts_window.c:80 msgid "Halve/double current playback speed" msgstr "" #: src/gmpv_shortcuts_window.c:81 msgid "Reset playback speed to normal" msgstr "" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "" #: src/gmpv_shortcuts_window.c:84 #, fuzzy msgid "Save playlist" msgstr "プレイリストを保存" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "" #: src/gmpv_shortcuts_window.c:86 msgid "Toggle infinite looping" msgstr "" #: src/gmpv_shortcuts_window.c:87 msgid "Pause or unpause" msgstr "" #: src/gmpv_shortcuts_window.c:88 #, fuzzy msgid "Quit" msgstr "終了" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "" #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "" #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "" #: src/gmpv_shortcuts_window.c:107 msgid "Cycle through video tracks" msgstr "" #: src/gmpv_shortcuts_window.c:108 msgid "Decrease/increase pan-and-scan range" msgstr "" #: src/gmpv_shortcuts_window.c:109 #, fuzzy msgid "Take a screenshot" msgstr "スクリーンショットを撮る" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "" #: src/gmpv_shortcuts_window.c:119 msgid "Activate or deactivate deinterlacer" msgstr "" #: src/gmpv_shortcuts_window.c:120 msgid "Cycle aspect ratio override" msgstr "" #: src/gmpv_shortcuts_window.c:123 #, fuzzy msgid "User Interface" msgstr "ユーザーインターフェース" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "" #: src/gmpv_view.c:711 #, fuzzy msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "CSDの有効・無効は再起動が必要です。" #: src/gmpv_view.c:1280 msgid "Add File to Playlist" msgstr "プレイリストの表示・非表示" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "ファイルを開く" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "場所を開く" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "" #: src/gmpv_view.c:1349 #, fuzzy msgid "Load Subtitle Track…" msgstr "字幕をロードする" #: src/gmpv_view.c:1374 #, fuzzy msgid "Save Playlist" msgstr "_プレイリストの保存" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "MPVのGTKフロントエンド" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "Tista" gnome-mpv-0.13/po/meson.build000066400000000000000000000000661317030365200161240ustar00rootroot00000000000000i18n.gettext(meson.project_name(), preset: 'glib' ) gnome-mpv-0.13/po/nl.po000066400000000000000000000470761317030365200147470ustar00rootroot00000000000000# gnome-mpv , 2016. #zanata # wb9688 , 2016. #zanata # gnome-mpv , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2016-08-16 23:25+0700\n" "PO-Revision-Date: 2017-08-02 12:10-0400\n" "Last-Translator: Copied by Zanata \n" "Language-Team: Dutch\n" "Language: nl\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1)\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "Schakel donker thema in of uit" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 msgid "Enable or disable client-side decorations" msgstr "Schakel client-side decoraties in of uit" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 #, fuzzy msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "" "Laat de bestandskiezer de laatst geraadpleegde map wel of niet onthouden" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "Opties om door te geven aan mpv" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 msgid "Path to mpv configuration file" msgstr "Pad naar mpv configuratiebestand" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 #, fuzzy msgid "Load or don't load mpv configuration file" msgstr "Laad mpv configuratiebestand wel of niet" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 #, fuzzy msgid "Path to mpv input configuration file" msgstr "Pad naar mpv input configuratiebestand" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 #, fuzzy msgid "Load or don't load mpv input configuration file" msgstr "Laad mpv input configuratiebestand wel of niet" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 msgid "Width of the window" msgstr "Breedte van het venster" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 msgid "Height of the window" msgstr "Hoogte van het venster" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 #, fuzzy msgid "Volume of player" msgstr "Volume van de speler" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "Breedte van de afspeellijst" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "Geef de afspeellijst wel of niet weer" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "URI van de map die het laatst is geraadpleegd" #: data/io.github.GnomeMpv.gschema.xml:10 #, fuzzy msgid "" "Whether the settings has already been migrated from the previous version" msgstr "Of de instellingen al gemigreerd zijn van een vorige versie" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:82 msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 #, fuzzy msgid "Show or not show the controls" msgstr "Geef de controls wel of niet weer" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "GTK+ frontend voor mpv" #: data/io.github.GnomeMpv.appdata.xml.in:12 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" "GNOME MPV is een simpele GTK+ frontend voor mpv, wat een erg krachtige " "mediaspeler is die eigenlijk alle video en audio formaten kan afspelen. Het " "design van GNOME MPV is gebaseerd op GNOME HIG, maar het gebruikt geen GNOME" " bibliotheken. GNOME MPV heeft ook een optie om client-side decoraties (CSD)" " uit te zetten voor betere compatibiliteit met niet-GNOME systemen" #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "Functies:" #: data/io.github.GnomeMpv.appdata.xml.in:21 #, fuzzy msgid "Drag and drop playlist" msgstr "Drag and drop afspeellijst" #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "Loading external mpv configuration files" msgstr "Externe mpv configuratiebestanden laden" #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "Het hoofdvenster met CSD uitgeschakeld" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "Het hoofdvenster met een afspeellijst open" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "" #: src/gmpv_application.c:370 msgid "Playing" msgstr "Afspelen" #: src/gmpv_application.c:415 msgid "Show release version" msgstr "Toon release versie" #: src/gmpv_application.c:423 #, fuzzy msgid "Enqueue" msgstr "Voeg toe aan wachtrij" #: src/gmpv_application.c:431 msgid "Create a new window" msgstr "" #: src/gmpv_application.c:439 #, fuzzy msgid "Don't connect to an already-running instance" msgstr "Verbind niet met instanties die al draaien" #: src/gmpv_control_box.c:286 msgid "Pause" msgstr "Pauze" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 msgid "Play" msgstr "Speel af" #: src/gmpv_control_box.c:436 msgid "Stop" msgstr "Stop" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "Voorwaards" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "Achterwaards" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "Volgend Hoofdstuk" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "Vorig Hoofdstuk" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 msgid "Toggle Fullscreen" msgstr "" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 msgid "Error" msgstr "Fout" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "_Annuleren" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "_Open" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 msgid "All Files" msgstr "" #: src/gmpv_file_chooser.c:143 msgid "Media Files" msgstr "" #: src/gmpv_file_chooser.c:154 msgid "Audio Files" msgstr "" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "" #: src/gmpv_file_chooser.c:170 msgid "Image Files" msgstr "" #: src/gmpv_file_chooser.c:180 msgid "Subtitle Files" msgstr "" #: src/gmpv_menu.c:102 msgid "None" msgstr "Geen" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 msgid "Unknown" msgstr "Onbekend" #: src/gmpv_menu.c:150 msgid "_Load External…" msgstr "_Laad Externe…" #: src/gmpv_menu.c:243 msgid "_File" msgstr "_Bestand" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "Open _Locatie" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "_Sla Afspeellijst op" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "_Afsluiten" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "_Bewerken" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "_Instellingen" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 msgid "_Audio Track" msgstr "" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 msgid "S_ubtitle Track" msgstr "" #: src/gmpv_menu.c:253 msgid "_View" msgstr "" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 msgid "_Toggle Playlist" msgstr "" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "_Volledig Scherm" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "_Normale Grootte" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 msgid "_Double Size" msgstr "_Dubbele Grootte" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 msgid "_Half Size" msgstr "_Halve Grootte" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "_Help" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 msgid "_Keyboard Shortcuts" msgstr "" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "_Over" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, fuzzy, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "Afspelen werd abnormaal beëindigd. Reden: %s." #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "Locatie:" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "Het toepassen van een of meerdere MPV opties is mislukt." #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "_Voeg Toe…" #: src/gmpv_playlist_widget.c:537 msgid "Add _Location…" msgstr "" #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "Afspeellijst" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "Voeg Lua Script toe" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 msgid "Lua Scripts" msgstr "Lua Scripts" #: src/gmpv_plugins_manager.c:299 #, fuzzy, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "Bestand van '%s' naar '%s' kopiëren mislukt. Reden: %s" #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "Geen Lua script gevonden" #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "Verwijderen" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "" "Weet je het zeker dat je dit script wil verwijderen? Deze actie kan niet " "ongedaan worden gemaakt." #: src/gmpv_plugins_manager_item.c:184 #, fuzzy, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "Bestand '%s' verwijderen mislukt. Reden: %s" #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "Gebruikersomgeving" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "Schakel client-side decoratie in" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "Schakel donker thema in" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "Onthoud de locatie van het laatste bestand" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr "MPV Configuratie" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "Laad MPV configuratiebestand" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr "MPV configuratiebestand:" #: src/gmpv_preferences_dialog.c:314 msgid "Keybindings" msgstr "Sneltoetsen" #: src/gmpv_preferences_dialog.c:317 #, fuzzy msgid "Load MPV input configuration file" msgstr "Laad MPV input configuratiebestand" #: src/gmpv_preferences_dialog.c:320 #, fuzzy msgid "MPV input configuration file:" msgstr "MPV input configuratiebestand:" #: src/gmpv_preferences_dialog.c:323 msgid "Miscellaneous" msgstr "Diversen" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "" #: src/gmpv_preferences_dialog.c:335 msgid "Enable media keys support" msgstr "" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "Extra MPV opties:" #: src/gmpv_preferences_dialog.c:371 msgid "General" msgstr "Algemeen" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "_Opslaan" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "Instellingen" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "Open bestand" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "Open locatie" #: src/gmpv_shortcuts_window.c:58 msgid "Add file to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "Toon instellingen dialoog" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle fullscreen mode" msgstr "" #: src/gmpv_shortcuts_window.c:64 msgid "Leave fullscreen mode" msgstr "Verlaat volledig scherm-modus" #: src/gmpv_shortcuts_window.c:65 msgid "Toggle OSD states between normal and playback time/duration" msgstr "" #: src/gmpv_shortcuts_window.c:66 msgid "Show filename on the OSD" msgstr "Geef bestandsnaam weer op de OSD" #: src/gmpv_shortcuts_window.c:67 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "Geef vooruitgang, verstreken tijd en duratie weer op de OSD" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 5 seconds" msgstr "Zoek 5 seconden achter- of voorwaards" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 1 second" msgstr "Zoek exact 1 seconde achter- of voorwaards" #: src/gmpv_shortcuts_window.c:72 msgid "Seek backward/forward 1 minute" msgstr "Zoek 1 minuut achter- of voorwaards" #: src/gmpv_shortcuts_window.c:73 msgid "Exact seek backward/forward 5 seconds" msgstr "Zoek exact 5 seconden achter- of voorwaards" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to previous/next subtitle" msgstr "" #: src/gmpv_shortcuts_window.c:75 msgid "Step backward/forward a single frame" msgstr "Ga een frame achter- of voorwaards" #: src/gmpv_shortcuts_window.c:76 msgid "Seek to the beginning of the previous/next chapter" msgstr "" #: src/gmpv_shortcuts_window.c:79 msgid "Decrease/increase playback speed by 10%" msgstr "Verlaag of verhoog afspeelsnelheid met 10%" #: src/gmpv_shortcuts_window.c:80 msgid "Halve/double current playback speed" msgstr "Halveer of verdubbel de huidige afspeelsnelheid" #: src/gmpv_shortcuts_window.c:81 msgid "Reset playback speed to normal" msgstr "Reset afspeelsnelheid naar normaal" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "Ga achter- of voorwaards in de afspeellijst" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "Verwijder geselecteerde item van de afspeellijst" #: src/gmpv_shortcuts_window.c:84 msgid "Save playlist" msgstr "Sla afspeellijst op" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "" #: src/gmpv_shortcuts_window.c:86 msgid "Toggle infinite looping" msgstr "" #: src/gmpv_shortcuts_window.c:87 msgid "Pause or unpause" msgstr "Pauzeren of hervatten" #: src/gmpv_shortcuts_window.c:88 msgid "Quit" msgstr "Afsluiten" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "Sla huidige afspeelpositie op en sluit af" #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "Doorloop audiotracks" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "Verlaag of verhoog volume" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "Verander audiovertraging met ±0.1 seconden" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "Verander ondertitelingvertraging met ±0.1 seconden" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "" #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "Verplaats ondertiteling omhoog of omlaag" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "" #: src/gmpv_shortcuts_window.c:107 #, fuzzy msgid "Cycle through video tracks" msgstr "Doorloop videotracks" #: src/gmpv_shortcuts_window.c:108 msgid "Decrease/increase pan-and-scan range" msgstr "" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot" msgstr "Maak een schermafbeelding" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "Maak een schermafbeelding zonder ondertiteling" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "Maak een schermafbeelding zoals het venster het toont" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "Verander contrast" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "Verander helderheid" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "Verander gamma" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "Verander verzadiging" #: src/gmpv_shortcuts_window.c:119 #, fuzzy msgid "Activate or deactivate deinterlacer" msgstr "Activeer of deactiveer de deinterlacer" #: src/gmpv_shortcuts_window.c:120 #, fuzzy msgid "Cycle aspect ratio override" msgstr "Doorloop beeldverhouding override" #: src/gmpv_shortcuts_window.c:123 msgid "User Interface" msgstr "Gebruikersomgeving" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "Video" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "Audio" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "Ondertiteling" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "Afspelen" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "Zoeken" #: src/gmpv_view.c:711 msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "" #: src/gmpv_view.c:1280 msgid "Add File to Playlist" msgstr "Voeg Bestand toe aan Afspeellijst" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "Open Bestand" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "Open Locatie" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "" #: src/gmpv_view.c:1349 msgid "Load Subtitle Track…" msgstr "" #: src/gmpv_view.c:1374 msgid "Save Playlist" msgstr "Sla Afspeellijst op" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "Een GTK frontend voor MPV" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "" gnome-mpv-0.13/po/pl.po000066400000000000000000000526061317030365200147440ustar00rootroot00000000000000# Piotr Sokół , 2016. # Piotr Sokół , 2016. #zanata # gnome-mpv , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: gnome-mpv 0.12\n" "Report-Msgid-Bugs-To: https://github.com/gnome-mpv/gnome-mpv/issues\n" "POT-Creation-Date: 2017-10-08 17:16-0700\n" "PO-Revision-Date: 2017-08-02 12:11-0400\n" "Last-Translator: Copied by Zanata \n" "Language-Team: polski <>\n" "Language: pl\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=3; plural=n==1 ? 0 : n%10>=2 && n%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2;\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "Przełącza ciemny styl" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 msgid "Enable or disable client-side decorations" msgstr "Przełącza wyświetlanie obramowania po stronie klienta" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "" "Przełącza przechowywanie ścieżki ostatnio używanego katalogu przez okno " "wyboru pliku" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "Określa opcje przekazywane do mpv" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 msgid "Path to mpv configuration file" msgstr "Wskazuje ścieżkę pliku konfiguracyjnego mpv" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 msgid "Load or don't load mpv configuration file" msgstr "Przełącza wczytywanie pliku konfiguracyjnego mpv" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 msgid "Path to mpv input configuration file" msgstr "Wskazuje ścieżkę pliku konfiguracyjnego skrótów programu mpv" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 msgid "Load or don't load mpv input configuration file" msgstr "Przełącza wczytywanie pliku konfiguracyjnego skrótów programu mpv" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 msgid "Width of the window" msgstr "Określa szerokość okna" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 msgid "Height of the window" msgstr "Określa wysokość okna" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 msgid "Volume of player" msgstr "Ustala głośność odtwarzania dźwięku" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "Określa szerokość listy odtwarzania" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "Przełącza wyświetlanie listy odtwarzania" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "Przechowuje adres URI ostatnio używanego katalogu" #: data/io.github.GnomeMpv.gschema.xml:10 msgid "" "Whether the settings has already been migrated from the previous version" msgstr "" "Określa czy ustawienia zostały zaimportowane z poprzedniej wersji programu" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:82 msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 msgid "Show or not show the controls" msgstr "Przełącza wyświetlanie przycisków sterujących" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "Wykorzystuje interfejs GTK do obsługi programu MPV" #: data/io.github.GnomeMpv.appdata.xml.in:12 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" "GNOME MPV jest prostym interfejsem GTK+ programu mpv - potężnego odtwarzacza" " obsługującego wszystkie formaty nagrań dźwięku i wideo. Projekt interfejsu" " jest zgodny z wytycznymi GNOME HIG, choć sam program nie jest zależy od " "bibliotek GNOME. GNOME MPV umożliwia wyłączenie wyświetlania obramowań po " "stronie klienta (CDS) dla lepszej integracji z systemami bez środowiska " "GNOME." #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "Cechy:" #: data/io.github.GnomeMpv.appdata.xml.in:21 msgid "Drag and drop playlist" msgstr "lista odtwarzania obsługująca przeciąganie plików," #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "Loading external mpv configuration files" msgstr "wczytywanie zewnętrznych plików konfiguracyjnych programu mpv," #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "obsluga interfejsu D-Bus MPRIS2." #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "Głowne okno programu z wyłączonym obramowaniem po stronie klienta" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "Główne okno programu z listą odtwarzania" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "" #: src/gmpv_application.c:370 msgid "Playing" msgstr "Odtwarzanie" #: src/gmpv_application.c:415 msgid "Show release version" msgstr "Wypisuje informacje o wersji" #: src/gmpv_application.c:423 msgid "Enqueue" msgstr "Dodaje do kolejki odtwarzania" #: src/gmpv_application.c:431 msgid "Create a new window" msgstr "" #: src/gmpv_application.c:439 msgid "Don't connect to an already-running instance" msgstr "Nie łączy z uruchomionym wystąpieniem programu" #: src/gmpv_control_box.c:286 msgid "Pause" msgstr "Wstrzymuje odtwarzanie" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 msgid "Play" msgstr "Rozpoczyna odtwarznie" #: src/gmpv_control_box.c:436 msgid "Stop" msgstr "Zatrzymuje odtwarzanie" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "Przechodzi naprzód" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "Przechodzi wstecz" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "Następny rozdział" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "Poprzedni rozdział" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 msgid "Toggle Fullscreen" msgstr "Przełącza wyświetlanie na pełnym ekranie" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 msgid "Error" msgstr "Błąd" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "_Anuluj" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "_Otwórz" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 msgid "All Files" msgstr "" #: src/gmpv_file_chooser.c:143 msgid "Media Files" msgstr "" #: src/gmpv_file_chooser.c:154 msgid "Audio Files" msgstr "" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "" #: src/gmpv_file_chooser.c:170 msgid "Image Files" msgstr "" #: src/gmpv_file_chooser.c:180 msgid "Subtitle Files" msgstr "" #: src/gmpv_menu.c:102 msgid "None" msgstr "Brak" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 msgid "Unknown" msgstr "Nieznana" #: src/gmpv_menu.c:150 msgid "_Load External…" msgstr "_Wczytaj zewnętrzną..." #: src/gmpv_menu.c:243 msgid "_File" msgstr "_Plik" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "Otwórz położe_nie" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "Z_apisz listę odtwarzania" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "Za_kończ" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "_Edycja" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "P_referencje" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "Ścieżka _wideo" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 msgid "_Audio Track" msgstr "Ścieżka _dźwiękowa" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 msgid "S_ubtitle Track" msgstr "Ścieżka _napisów" #: src/gmpv_menu.c:253 msgid "_View" msgstr "_Widok" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "P_rzyciski sterujące" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 msgid "_Toggle Playlist" msgstr "_Lista odtwarzania" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "_Pełny ekran" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "_Zwykły rozmiar" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 msgid "_Double Size" msgstr "Dwukrotnie _większy rozmiar" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 msgid "_Half Size" msgstr "Dwukrotnie _mniejszy rozmiar" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "Pomo_c" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 msgid "_Keyboard Shortcuts" msgstr "_Skróty klawiszowe" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "_O programie" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, fuzzy, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "Zakończono odtwarzanie w nieprawidłowy sposób. Powód: %s" #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "Położenie:" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "Nie udało się wprowadzić jednej lub więcej opcji MPV." #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "_Dodaj..." #: src/gmpv_playlist_widget.c:537 msgid "Add _Location…" msgstr "Dodaj p_ołożenie…" #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "Lista odtwarzania" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "Dodawanie skryptu Lua" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 msgid "Lua Scripts" msgstr "Skrypty Lua" #: src/gmpv_plugins_manager.c:299 #, fuzzy, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "Nie udało się skopiować pliku z położenia „%s” do „%s”. Powód: %s" #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "Nie odnaleziono skryptów Lua" #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "Usuń" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "Usunąć ten skrypt? Tej czynności nie można cofnąć." #: src/gmpv_plugins_manager_item.c:184 #, fuzzy, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "Nie można usunąć pliku „%s”. Powód: %s" #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "Interfejs użytkownika" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "Obramowania okien po stronie klienta" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "Ciemny styl" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "Przechowywanie położenia ostatnich plików" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr "Konfiguracja MPV" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "Wczytywanie pliku konfiguracji MPV" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr "Plik konfiguracji MPV:" #: src/gmpv_preferences_dialog.c:314 msgid "Keybindings" msgstr "Skróty klawiszowe" #: src/gmpv_preferences_dialog.c:317 msgid "Load MPV input configuration file" msgstr "Wczytywanie pliku konfiguracji skrótów MPV" #: src/gmpv_preferences_dialog.c:320 msgid "MPV input configuration file:" msgstr "Plik konfiguracji skrótów MPV:" #: src/gmpv_preferences_dialog.c:323 msgid "Miscellaneous" msgstr "Różne" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "" #: src/gmpv_preferences_dialog.c:335 msgid "Enable media keys support" msgstr "" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "Dodatkowe opcje MPV:" #: src/gmpv_preferences_dialog.c:371 msgid "General" msgstr "Ogólne" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "_Zapisz" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "Preferencje" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "Otwarcie pliku" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "Otwarcie położenia" #: src/gmpv_shortcuts_window.c:58 msgid "Add file to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "Wyświetlenie okna preferencji" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "Przełączenie wyświetlania przycisków sterujących" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "Przełączenie wyświetlania listy odtwarzania" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle fullscreen mode" msgstr "Przełączenie trybu pełnoekranowego" #: src/gmpv_shortcuts_window.c:64 msgid "Leave fullscreen mode" msgstr "Opuszczenie trybu pełnoekranowego" #: src/gmpv_shortcuts_window.c:65 msgid "Toggle OSD states between normal and playback time/duration" msgstr "Przełączenie wyświetlania czasu odtwarzania/trwania w menu ekranowym" #: src/gmpv_shortcuts_window.c:66 msgid "Show filename on the OSD" msgstr "Wyświetlenie nazwy pliku w menu ekranowym" #: src/gmpv_shortcuts_window.c:67 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "Wyświetlenie postępu, czasu odtwarzania i trwania w menu ekranowym" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 5 seconds" msgstr "Przejście 5 sekund wstecz/naprzód" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 1 second" msgstr "Dokładne przejście 1 sekundę wstecz/naprzód" #: src/gmpv_shortcuts_window.c:72 msgid "Seek backward/forward 1 minute" msgstr "Przejście 1 minutę wstecz/naprzód" #: src/gmpv_shortcuts_window.c:73 msgid "Exact seek backward/forward 5 seconds" msgstr "Dokładne przejście 5 sekund wstecz/naprzód" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to previous/next subtitle" msgstr "Przejście do poprzedniego/następnego napisu dialogowego" #: src/gmpv_shortcuts_window.c:75 msgid "Step backward/forward a single frame" msgstr "Przejście pojedynczą klatkę wstecz/naprzód" #: src/gmpv_shortcuts_window.c:76 msgid "Seek to the beginning of the previous/next chapter" msgstr "Przejście do początku poprzedniego/następnego rozdziału" #: src/gmpv_shortcuts_window.c:79 msgid "Decrease/increase playback speed by 10%" msgstr "Zmniejszenie/zwiększenie prędkości odtwarzania o 10%" #: src/gmpv_shortcuts_window.c:80 msgid "Halve/double current playback speed" msgstr "Dwukrotne zmniejszenie/zwiększenie aktualnej prędkości odtwarzania" #: src/gmpv_shortcuts_window.c:81 msgid "Reset playback speed to normal" msgstr "Przywrócenie zwykłej prędkości odtwarzania" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "Przejście wstecz/naprzód na liście odtwarzania" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "Usunięcie zaznaczonego elementu listy odtwarzania" #: src/gmpv_shortcuts_window.c:84 msgid "Save playlist" msgstr "Zapisanie listy odtwarzania" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "Ustalenie/wyczyszczenie punktów zapętlenia A-B" #: src/gmpv_shortcuts_window.c:86 msgid "Toggle infinite looping" msgstr "Przełączenia zapętlonego odtwarzania" #: src/gmpv_shortcuts_window.c:87 msgid "Pause or unpause" msgstr "Przełączenie wstrzymania odtwarzania" #: src/gmpv_shortcuts_window.c:88 msgid "Quit" msgstr "Zakończenie działania" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "Zapisanie aktualnego położenia i zakończenie działania" #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "Przełączenie ścieżki dźwiękowej" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "Zmniejszenie/zwiększenie głośności" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "Przełączenie wyciszenia dźwięku" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "Dostosowanie opóźnienia dźwięku o +/- 0,1 s" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "Przełączenie widoczności napisów" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "Przełączenie ścieżki napisów" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "Dostosowanie opóźnienia napisów o +/- 0,1 s" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "Przełączenie zastępowania stylów napisów SSA/ASS" #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "Przemieszczenie napisów w górę/dół" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "Przełączenie tryby kompatybilności proporcji VSFilter" #: src/gmpv_shortcuts_window.c:107 msgid "Cycle through video tracks" msgstr "Przełączenie ścieżki wideo" #: src/gmpv_shortcuts_window.c:108 msgid "Decrease/increase pan-and-scan range" msgstr "Zmniejszenie/zwiększenie zasięgu pan-and-scan" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot" msgstr "Przechwycenie obrazu" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "Przechwycenie obrazu bez napisów" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "Przechwycenie obrazu wyświetlanego w oknie" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "Ustalenie rozmiaru obrazu dwukrotnie mniejszego niż pierwotny" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "Przywrócenie pierwotnego rozmiaru obrazu" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "Ustalenie rozmiaru obrazu dwukrotnie większego niż pierwotny" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "Dostosowanie kontrastu" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "Dostosowanie jasności" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "Dostosowanie gamma" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "Dostosowanie nasycenia" #: src/gmpv_shortcuts_window.c:119 msgid "Activate or deactivate deinterlacer" msgstr "Przełączenie usuwania przeplotu" #: src/gmpv_shortcuts_window.c:120 msgid "Cycle aspect ratio override" msgstr "Przełączenie proporcji obrazu" #: src/gmpv_shortcuts_window.c:123 msgid "User Interface" msgstr "Interfejs użytkownika" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "Wideo" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "Dźwięk" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "Napisy dialogowe" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "Odtwarzanie" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "Przeszukiwanie" #: src/gmpv_view.c:711 msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "" #: src/gmpv_view.c:1280 msgid "Add File to Playlist" msgstr "Dodawanie pliku do listy odtwarzania" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "Wybór pliku" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "Dodawanie położenia do listy odtwarzania" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "Otwieranie położenia" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "" #: src/gmpv_view.c:1349 msgid "Load Subtitle Track…" msgstr "" #: src/gmpv_view.c:1374 msgid "Save Playlist" msgstr "Zapisywanie listy odtwarzania" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "Wykorzystuje interfejs GTK do obsługi programu MPV" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "Piotr Sokół , 2016" gnome-mpv-0.13/po/pt_BR.po000066400000000000000000000502571317030365200153370ustar00rootroot00000000000000# SOME DESCRIPTIVE TITLE. # Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER # This file is distributed under the same license as the PACKAGE package. # FIRST AUTHOR , YEAR. # gnome-mpv , 2016. #zanata # Israel Faustino , 2017. #zanata # gnome-mpv , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2016-08-16 23:25+0700\n" "PO-Revision-Date: 2017-09-11 05:49-0400\n" "Last-Translator: Israel Faustino \n" "Language-Team: Portuguese (Brazil)\n" "Language: pt-BR\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1)\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "Ativar ou desativar tema escuro" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 #, fuzzy msgid "Enable or disable client-side decorations" msgstr "Ativar ou desativar decorações de janela" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 #, fuzzy msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "" "Se deseja ou não fazer o seletor de arquivos lembrar a última página " "acessada" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 #, fuzzy msgid "Path to mpv configuration file" msgstr "Caminho para o arquivo de configuração do mpv" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 #, fuzzy msgid "Load or don't load mpv configuration file" msgstr "Carregar ou não carregar o arquivo de configuração do mpv" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 msgid "Path to mpv input configuration file" msgstr "Caminho para o arquivo de atalhos do mpv" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 #, fuzzy msgid "Load or don't load mpv input configuration file" msgstr "Carregar ou não carregar o arquivo de atalhos do mpv" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 msgid "Width of the window" msgstr "Largura da janela" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 msgid "Height of the window" msgstr "Altura da janela" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 msgid "Volume of player" msgstr "Volume do reprodutor" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "Largura da lista de reprodução" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "Mostrar ou não mostrar a lista de reprodução" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "URI da última pasta acessada" #: data/io.github.GnomeMpv.gschema.xml:10 #, fuzzy msgid "" "Whether the settings has already been migrated from the previous version" msgstr "Se as configurações já migraram da versão anterior" #: data/io.github.GnomeMpv.gschema.xml:28 #, fuzzy msgid "Whether or not to use floating controls in windowed mode" msgstr "Usar ou não usar controles flutuantes no modo janela" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "Ativar ou desativar suporte para MPRIS" #: data/io.github.GnomeMpv.gschema.xml:82 #, fuzzy msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "" "Ativar ou desativar suporte para comandos de mídia do GNOME-Settings-Daemon" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 msgid "Show or not show the controls" msgstr "Mostrar ou não mostrar os controles" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 #, fuzzy msgid "GTK+ frontend for mpv" msgstr "Interface em GTK+ para o mpv" #: data/io.github.GnomeMpv.appdata.xml.in:12 #, fuzzy msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" "GNOME MPV é uma interface simples em GTK+ para o mpv, que é um poderoso " "reprodutor de mídia capaz de reproduzir praticamente todos os formatos de " "audio e vídeo. O design do GNOME MPV é baseado no GNOME HIG, mas não " "depende de nenhuma biblioteca GNOME. GNOME MPV também oferece a opção de " "desativar as decorações de janelas independentes (client-side " "decorations[CSD]) para uma melhor compatibiidade com sistemas que não usam " "GNOME." #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "Funcionalidades:" #: data/io.github.GnomeMpv.appdata.xml.in:21 #, fuzzy msgid "Drag and drop playlist" msgstr "Arrastar e largar lista de reprodução" #: data/io.github.GnomeMpv.appdata.xml.in:22 #, fuzzy msgid "Loading external mpv configuration files" msgstr "Carregar arquivos de configuração externos do mpv" #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "Janela principal com a lista de reprodução aberta" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "gnome-mpv" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "Nova Janela" #: src/gmpv_application.c:370 msgid "Playing" msgstr "Reproduzindo" #: src/gmpv_application.c:415 #, fuzzy msgid "Show release version" msgstr "Mostrar versão" #: src/gmpv_application.c:423 msgid "Enqueue" msgstr "Enfileirar" #: src/gmpv_application.c:431 msgid "Create a new window" msgstr "Criar uma nova janela" #: src/gmpv_application.c:439 #, fuzzy msgid "Don't connect to an already-running instance" msgstr "Não conectar a uma instância já em execução" #: src/gmpv_control_box.c:286 msgid "Pause" msgstr "Pausar" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 msgid "Play" msgstr "reproduzir" #: src/gmpv_control_box.c:436 msgid "Stop" msgstr "Parar" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "Avançar" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "Retroceder" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "Próximo Capítulo" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "Capítulo Anterior" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 #, fuzzy msgid "Toggle Fullscreen" msgstr "Alternar Tela Cheia" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 msgid "Error" msgstr "Erro" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "_Cancelar" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "_Abrir" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 msgid "All Files" msgstr "Todos os Arquivos" #: src/gmpv_file_chooser.c:143 msgid "Media Files" msgstr "Arquivos de mídia" #: src/gmpv_file_chooser.c:154 msgid "Audio Files" msgstr "Arquivos de Áudio" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "Arquivos de Vídeo" #: src/gmpv_file_chooser.c:170 msgid "Image Files" msgstr "Arquivos de Imagem" #: src/gmpv_file_chooser.c:180 msgid "Subtitle Files" msgstr "Arquivos de Legendas" #: src/gmpv_menu.c:102 msgid "None" msgstr "Nenhum" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 msgid "Unknown" msgstr "Desconhecido" #: src/gmpv_menu.c:150 #, fuzzy msgid "_Load External…" msgstr "Carregar Externo..." #: src/gmpv_menu.c:243 msgid "_File" msgstr "_Arquivo" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "Abrir_Pasta" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "_Salvar Lista de Reprodução" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "_Sair" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "_Editar" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "_Preferências" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "_Faixa de Vídeo" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 msgid "_Audio Track" msgstr "_Faixa de Áudio" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 #, fuzzy msgid "S_ubtitle Track" msgstr "_Legendas" #: src/gmpv_menu.c:253 msgid "_View" msgstr "_Exibir" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "_Exibir Controles" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 #, fuzzy msgid "_Toggle Playlist" msgstr "_Exibir Lista de Reprodução" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "_Tela Cheia" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "_Tamanho Normal" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 #, fuzzy msgid "_Double Size" msgstr "_Dobro" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 #, fuzzy msgid "_Half Size" msgstr "_Metade" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "_Ajuda" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 #, fuzzy msgid "_Keyboard Shortcuts" msgstr "_Teclas de Atalho" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "_Sobre" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, fuzzy, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "A reprodução foi encerrada de forma inesperada. Motivo: %s." #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "Local:" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "Falha ao aplicar uma ou mais opções do MPV." #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "_Adicionar..." #: src/gmpv_playlist_widget.c:537 #, fuzzy msgid "Add _Location…" msgstr "Adicionar _Pasta" #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "_Aleatório" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "Repetir" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "Lista de Reprodução" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "Adicionar Script em Lua" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 msgid "Lua Scripts" msgstr "Scripts Lua" #: src/gmpv_plugins_manager.c:299 #, fuzzy, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "Falha ao copiar arquivo de '%s' para '%s'. Motivo: %s" #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "nenhum script Lua encontrado" #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "Remover" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "" "Tem certeza que deseja remover este script? Esta ação não poderá ser " "desfeita." #: src/gmpv_plugins_manager_item.c:184 #, fuzzy, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "Falha au deletar o arquivo %s. Motivo: %s" #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "Interface de Usuário" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "Ativar decorações de janela independentes" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "Ativar tema escuro" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "Usar controles flutuantes no modo janela" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "Lembrar o local do último arquivo" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr "Configurações MPV" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "Carregar arquivo de configuração MPV" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr "Arquivo de configuração MPV:" #: src/gmpv_preferences_dialog.c:314 #, fuzzy msgid "Keybindings" msgstr "Atalhos" #: src/gmpv_preferences_dialog.c:317 msgid "Load MPV input configuration file" msgstr "Carregar arquivo de comandos MPV" #: src/gmpv_preferences_dialog.c:320 msgid "MPV input configuration file:" msgstr "Arquivo de configuração MPV:" #: src/gmpv_preferences_dialog.c:323 #, fuzzy msgid "Miscellaneous" msgstr "Diversos" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "Ativar suporte para MPRIS" #: src/gmpv_preferences_dialog.c:335 #, fuzzy msgid "Enable media keys support" msgstr "Ativar suporte para atalhos de mídia" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "Opções MPV" #: src/gmpv_preferences_dialog.c:371 msgid "General" msgstr "Geral" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "_Salvar" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "Preferências" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "Abrir arquivo" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "Abrir pasta" #: src/gmpv_shortcuts_window.c:58 msgid "Add file to playlist" msgstr "Adicionar arquivo à lista de reprodução" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "Adicionar pasta à lista de reprodução" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "Mostrar janela de preferências" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "_Exibir controles" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "_Mostrar lista de reprodução" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle fullscreen mode" msgstr "Alternar modo tela cheia" #: src/gmpv_shortcuts_window.c:64 msgid "Leave fullscreen mode" msgstr "Sair do modo tela cheia" #: src/gmpv_shortcuts_window.c:65 #, fuzzy msgid "Toggle OSD states between normal and playback time/duration" msgstr "" "Aternar modos de sobreposição de tela (OSD) entre normal e tempo " "decorrido/duração" #: src/gmpv_shortcuts_window.c:66 #, fuzzy msgid "Show filename on the OSD" msgstr "Exibir o nome do arquivo na tela (OSD)" #: src/gmpv_shortcuts_window.c:67 #, fuzzy msgid "Show progress, elapsed time, and duration on the OSD" msgstr "Mostrar progresso, tempo decorrido, e a duração na tela (OSD)" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 5 seconds" msgstr "Avançar/retroceder 5 segundos" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 1 second" msgstr "Avançar/retroceder exatamente 1 segundo" #: src/gmpv_shortcuts_window.c:72 msgid "Seek backward/forward 1 minute" msgstr "Avançar/retroceder 1 minuto" #: src/gmpv_shortcuts_window.c:73 msgid "Exact seek backward/forward 5 seconds" msgstr "Avançar/retroceder 5 minutos" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to previous/next subtitle" msgstr "Alternar" #: src/gmpv_shortcuts_window.c:75 msgid "Step backward/forward a single frame" msgstr "Avançar/retroceder um único quadro" #: src/gmpv_shortcuts_window.c:76 msgid "Seek to the beginning of the previous/next chapter" msgstr "" #: src/gmpv_shortcuts_window.c:79 msgid "Decrease/increase playback speed by 10%" msgstr "Aumentar/diminuir a velocidade de reprodução em 10%" #: src/gmpv_shortcuts_window.c:80 msgid "Halve/double current playback speed" msgstr "" #: src/gmpv_shortcuts_window.c:81 msgid "Reset playback speed to normal" msgstr "" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "Avançar/retroceder na lista de reprodução" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "Remover item selecionado da lista de reprodução" #: src/gmpv_shortcuts_window.c:84 msgid "Save playlist" msgstr "Salvar lista de reprodução" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "" #: src/gmpv_shortcuts_window.c:86 #, fuzzy msgid "Toggle infinite looping" msgstr "Alternar modo de repetição infinita" #: src/gmpv_shortcuts_window.c:87 #, fuzzy msgid "Pause or unpause" msgstr "Pausar" #: src/gmpv_shortcuts_window.c:88 msgid "Quit" msgstr "Sair" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "Salvar posição de reprodução e sair" #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "Aumentar/diminuir volume" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "" #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "" #: src/gmpv_shortcuts_window.c:107 msgid "Cycle through video tracks" msgstr "" #: src/gmpv_shortcuts_window.c:108 msgid "Decrease/increase pan-and-scan range" msgstr "" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot" msgstr "" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "" #: src/gmpv_shortcuts_window.c:119 msgid "Activate or deactivate deinterlacer" msgstr "" #: src/gmpv_shortcuts_window.c:120 msgid "Cycle aspect ratio override" msgstr "" #: src/gmpv_shortcuts_window.c:123 msgid "User Interface" msgstr "" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "" #: src/gmpv_view.c:711 msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "" #: src/gmpv_view.c:1280 msgid "Add File to Playlist" msgstr "" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "" #: src/gmpv_view.c:1349 msgid "Load Subtitle Track…" msgstr "" #: src/gmpv_view.c:1374 msgid "Save Playlist" msgstr "" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "" gnome-mpv-0.13/po/pt_PT.po000066400000000000000000000454501317030365200153560ustar00rootroot00000000000000# Bruno Guerreiro , 2016. # Bruno Guerreiro , 2016. #zanata # gnome-mpv , 2016. #zanata # gnome-mpv , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: gnome-mpv 0.12\n" "Report-Msgid-Bugs-To: https://github.com/gnome-mpv/gnome-mpv/issues\n" "POT-Creation-Date: 2017-10-08 17:16-0700\n" "PO-Revision-Date: 2017-08-02 12:10-0400\n" "Last-Translator: Copied by Zanata \n" "Language-Team: Portuguese\n" "Language: pt-PT\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1);\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "Ativar ou desativar tema escuro" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 msgid "Enable or disable client-side decorations" msgstr "Ativar ou desativar decorações do lado do cliente" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "Se deve ou não fazer diálogo de seleção lembrar ultima pasta acedida" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "Opções de mpv adicionais" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 msgid "Path to mpv configuration file" msgstr "Localização do ficheiro de configuração mpv" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 msgid "Load or don't load mpv configuration file" msgstr "Carregar ou não o ficheiro de configuração mpv" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 msgid "Path to mpv input configuration file" msgstr "Localização do ficheiro input mpv" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 msgid "Load or don't load mpv input configuration file" msgstr "Carregar ou não ficheiro input mpv" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 msgid "Width of the window" msgstr "Largura da janela" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 msgid "Height of the window" msgstr "Altura da janela" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 msgid "Volume of player" msgstr "Volume da aplicação" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "Largura da lista de reprodução" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "Mostrar ou não lista de reprodução" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "URI da última pasta acedida" #: data/io.github.GnomeMpv.gschema.xml:10 msgid "" "Whether the settings has already been migrated from the previous version" msgstr "Se as configurações já foi migrado da versão anterior" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:82 msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 msgid "Show or not show the controls" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "Interface GTK+ para mpv" #: data/io.github.GnomeMpv.appdata.xml.in:12 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" "GNOME MPV é um interface simples em GTK+ para mpv, que é um poderoso " "reprodutor multimédia capaz de reproduzir praticamente todos os formatos de " "vídeo e áudio. O projeto do GNOME MPV é baseada em GNOME HIG, embora não " "seja dependente de todas as bibliotecas do GNOME. GNOME MPV também oferece " "uma opção para desativar decorações do lado do cliente (CSD) para melhor " "compatibilidade com os sistemas não-GNOME." #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "Características:" #: data/io.github.GnomeMpv.appdata.xml.in:21 msgid "Drag and drop playlist" msgstr "Arrastar e soltar lista de reprodução" #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "Loading external mpv configuration files" msgstr "A carregar ficheiros de configuração mpv externos" #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "Interface MPRIS2 D-Bus" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "Janela principal com CSD desativada" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "Janela principal com lista de reprodução aberta" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "" #: src/gmpv_application.c:370 msgid "Playing" msgstr "A reproduzir" #: src/gmpv_application.c:415 msgid "Show release version" msgstr "" #: src/gmpv_application.c:423 msgid "Enqueue" msgstr "" #: src/gmpv_application.c:431 msgid "Create a new window" msgstr "" #: src/gmpv_application.c:439 msgid "Don't connect to an already-running instance" msgstr "" #: src/gmpv_control_box.c:286 msgid "Pause" msgstr "Pausa" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 msgid "Play" msgstr "Reproduzir" #: src/gmpv_control_box.c:436 msgid "Stop" msgstr "Parar" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "Avançar" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "Recuar" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "Próximo capítulo" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "Capítulo anterior" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 msgid "Toggle Fullscreen" msgstr "Alternar ecrã completo" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 msgid "Error" msgstr "Erro" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "_Cancelar" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "_Abrir" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 msgid "All Files" msgstr "" #: src/gmpv_file_chooser.c:143 msgid "Media Files" msgstr "" #: src/gmpv_file_chooser.c:154 msgid "Audio Files" msgstr "" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "" #: src/gmpv_file_chooser.c:170 msgid "Image Files" msgstr "" #: src/gmpv_file_chooser.c:180 msgid "Subtitle Files" msgstr "" #: src/gmpv_menu.c:102 msgid "None" msgstr "Nenhum" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 msgid "Unknown" msgstr "Desconhecido" #: src/gmpv_menu.c:150 msgid "_Load External…" msgstr "_Abrir Externo…" #: src/gmpv_menu.c:243 msgid "_File" msgstr "_Ficheiro" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "Abrir _Localização" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "_Guardar Lista de Reprodução" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "_Sair" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "_Editar" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "_Preferências" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "_Faixa de vídeo" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 msgid "_Audio Track" msgstr "_Faixa de áudio" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 msgid "S_ubtitle Track" msgstr "Faixa de legendas" #: src/gmpv_menu.c:253 msgid "_View" msgstr "_Ver" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 msgid "_Toggle Playlist" msgstr "_Alternar Lista de Reprodução" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "_Ecrã completo" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "_Tamanho Normal" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 msgid "_Double Size" msgstr "_Duplo Tamanho" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 msgid "_Half Size" msgstr "_Metade do tamanho" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "_Ajuda" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 msgid "_Keyboard Shortcuts" msgstr "" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "_Sobre" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, fuzzy, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "A reprodução foi terminada de forma anormal. Motivo: %s." #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "Localização:" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "Falha ao aplicar uma ou mais opções de MPV." #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "_Adicionar…" #: src/gmpv_playlist_widget.c:537 msgid "Add _Location…" msgstr "" #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "Lista de reprodução" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 msgid "Lua Scripts" msgstr "Scripts Lua" #: src/gmpv_plugins_manager.c:299 #, fuzzy, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "Falha ao copiar ficheiro de '%s' para '%s'. Motivo: %s" #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "Nenhum script lua encontrado" #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "Remover" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "" "Tem certeza que deseja remover este script? Essa ação não pode ser desfeita." #: src/gmpv_plugins_manager_item.c:184 #, fuzzy, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "Falha ao excluir ficheiro '%s'. Motivo: %s" #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "Interface de Utilizador" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "Ativar decorações do lado do cliente" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "Ativar tema escuro" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "Lembrar localizações dos últimos ficheiros" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr "Configuração do MPV" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "Carregar ficheiro de configuração do MPV" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr "Ficheiro de configuração do MPV:" #: src/gmpv_preferences_dialog.c:314 msgid "Keybindings" msgstr "Teclas de atalho" #: src/gmpv_preferences_dialog.c:317 msgid "Load MPV input configuration file" msgstr "Carregar ficheiro input do MPV" #: src/gmpv_preferences_dialog.c:320 msgid "MPV input configuration file:" msgstr "Ficheiro input do MPV:" #: src/gmpv_preferences_dialog.c:323 msgid "Miscellaneous" msgstr "Outras" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "" #: src/gmpv_preferences_dialog.c:335 msgid "Enable media keys support" msgstr "" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "Opções extra do MPV:" #: src/gmpv_preferences_dialog.c:371 msgid "General" msgstr "Geral" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "_Gravar" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "Preferências" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "Abrir ficheiro" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "Abrir localização" #: src/gmpv_shortcuts_window.c:58 msgid "Add file to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "Mostrar dialogo de preferências" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "Alternar lista de reprodução" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle fullscreen mode" msgstr "Alternar modo ecrã completo" #: src/gmpv_shortcuts_window.c:64 msgid "Leave fullscreen mode" msgstr "Deixa modo ecrã completo" #: src/gmpv_shortcuts_window.c:65 msgid "Toggle OSD states between normal and playback time/duration" msgstr "" #: src/gmpv_shortcuts_window.c:66 msgid "Show filename on the OSD" msgstr "" #: src/gmpv_shortcuts_window.c:67 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 5 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 1 second" msgstr "" #: src/gmpv_shortcuts_window.c:72 msgid "Seek backward/forward 1 minute" msgstr "" #: src/gmpv_shortcuts_window.c:73 msgid "Exact seek backward/forward 5 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to previous/next subtitle" msgstr "" #: src/gmpv_shortcuts_window.c:75 msgid "Step backward/forward a single frame" msgstr "" #: src/gmpv_shortcuts_window.c:76 msgid "Seek to the beginning of the previous/next chapter" msgstr "" #: src/gmpv_shortcuts_window.c:79 msgid "Decrease/increase playback speed by 10%" msgstr "" #: src/gmpv_shortcuts_window.c:80 msgid "Halve/double current playback speed" msgstr "" #: src/gmpv_shortcuts_window.c:81 msgid "Reset playback speed to normal" msgstr "" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "Remover item de lista de reprodução selecionada" #: src/gmpv_shortcuts_window.c:84 msgid "Save playlist" msgstr "Guardar lista de reprodução" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "" #: src/gmpv_shortcuts_window.c:86 msgid "Toggle infinite looping" msgstr "" #: src/gmpv_shortcuts_window.c:87 msgid "Pause or unpause" msgstr "" #: src/gmpv_shortcuts_window.c:88 msgid "Quit" msgstr "Sair" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "" #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "" #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "" #: src/gmpv_shortcuts_window.c:107 msgid "Cycle through video tracks" msgstr "" #: src/gmpv_shortcuts_window.c:108 msgid "Decrease/increase pan-and-scan range" msgstr "" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot" msgstr "" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "" #: src/gmpv_shortcuts_window.c:119 msgid "Activate or deactivate deinterlacer" msgstr "" #: src/gmpv_shortcuts_window.c:120 msgid "Cycle aspect ratio override" msgstr "" #: src/gmpv_shortcuts_window.c:123 msgid "User Interface" msgstr "" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "" #: src/gmpv_view.c:711 msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "" #: src/gmpv_view.c:1280 msgid "Add File to Playlist" msgstr "Adicionar ficheiro a lista de reprodução" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "Abrir Ficheiro" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "Abrir Localização" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "" #: src/gmpv_view.c:1349 msgid "Load Subtitle Track…" msgstr "" #: src/gmpv_view.c:1374 msgid "Save Playlist" msgstr "Guardar Lista de Reprodução" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "Uma interface GTK para MPV" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "Bruno Guerreiro" gnome-mpv-0.13/po/ro.po000066400000000000000000000367731317030365200147600ustar00rootroot00000000000000# Romanian (ro_RO) translations for gnome-mpv package. # gnome-mpv # Copyright (C) 2015 THE gnome-mpv'S COPYRIGHT HOLDER # This file is distributed under the same license as the gnone-mpv package. # Robert Datcu , 2015. # gnome-mpv , 2015. #zanata # gnome-mpv , 2016. #zanata msgid "" msgstr "" "Project-Id-Version: gnome-mpv 0.11\n" "Report-Msgid-Bugs-To: https://github.com/gnome-mpv/gnome-mpv/issues\n" "POT-Creation-Date: 2017-02-19 22:47+0700\n" "PO-Revision-Date: 2016-11-03 05:24-0400\n" "Last-Translator: Copied by Zanata \n" "Language-Team: Romanian Translations\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Language: ro\n" "Plural-Forms: nplurals=2; plural=(n != 1);\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 msgid "Enable or disable client-side decorations" msgstr "" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 msgid "Path to mpv configuration file" msgstr "" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 msgid "Load or don't load mpv configuration file" msgstr "" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 msgid "Path to mpv input configuration file" msgstr "" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 msgid "Load or don't load mpv input configuration file" msgstr "" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:80 msgid "Width of the window" msgstr "" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:86 msgid "Height of the window" msgstr "" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:93 msgid "Volume of player" msgstr "" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:99 msgid "Width of the playlist" msgstr "" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:111 msgid "Show or not show the playlist" msgstr "" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:117 msgid "URI of the last folder accessed" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:10 msgid "" "Whether the settings has already been migrated from the previous version" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:40 src/gmpv_pref_dialog.c:367 msgid "Allow multiple instances" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:105 msgid "Show or not show the controls" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:245 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:11 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:18 msgid "Features:" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:20 msgid "Drag and drop playlist" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:21 msgid "Loading external mpv configuration files" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "MPRIS2 D-Bus interface" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:32 msgid "The main window with CSD disabled" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with playlist open" msgstr "" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "" #: src/gmpv_actionctl.c:252 #, c-format msgid "" "Enabling or disabling client-side decorations requires restarting %s to take" " effect." msgstr "" "Activarea sau dezactivarea decorațiilor ferestrelor (CSD) necesită " "repornirea %s." #: src/gmpv_actionctl.c:291 msgid "Add File to Playlist" msgstr "Adaugă un fișier Listei de Redare" #: src/gmpv_actionctl.c:292 msgid "Open File" msgstr "Deschide Fișier" #: src/gmpv_actionctl.c:325 msgid "Add Location to Playlist" msgstr "" #: src/gmpv_actionctl.c:326 msgid "Open Location" msgstr "Deschide Adresa" #: src/gmpv_actionctl.c:405 msgid "Save Playlist" msgstr "Salvează Lista de Redare" #: src/gmpv_actionctl.c:433 src/gmpv_application.c:822 msgid "Error" msgstr "" #: src/gmpv_actionctl.c:528 msgid "Load External…" msgstr "" #: src/gmpv_actionctl.c:620 msgid "A GTK frontend for MPV" msgstr "O interfață GTK pentru MPV" #: src/gmpv_actionctl.c:630 msgid "translator-credits" msgstr "Robert Datcu" #: src/gmpv_application.c:963 msgid "Playing" msgstr "" #: src/gmpv_application.c:1081 msgid "Show release version" msgstr "" #: src/gmpv_application.c:1089 msgid "Enqueue" msgstr "" #: src/gmpv_application.c:1097 msgid "Don't connect to an already-running instance" msgstr "" #: src/gmpv_control_box.c:192 src/gmpv_control_box.c:365 msgid "Play" msgstr "" #: src/gmpv_control_box.c:193 msgid "Stop" msgstr "" #: src/gmpv_control_box.c:194 msgid "Forward" msgstr "" #: src/gmpv_control_box.c:195 msgid "Rewind" msgstr "" #: src/gmpv_control_box.c:196 msgid "Next Chapter" msgstr "" #: src/gmpv_control_box.c:197 msgid "Previous Chapter" msgstr "" #: src/gmpv_control_box.c:198 src/gmpv_header_bar.c:93 msgid "Toggle Fullscreen" msgstr "" #: src/gmpv_control_box.c:365 msgid "Pause" msgstr "" #: src/gmpv_menu.c:56 msgid "None" msgstr "" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:71 msgid "Unknown" msgstr "" #: src/gmpv_menu.c:106 msgid "_Load External…" msgstr "" #: src/gmpv_menu.c:192 msgid "_File" msgstr "_Fișier" #: src/gmpv_menu.c:193 src/gmpv_menu.c:257 src/gmpv_open_loc_dialog.c:85 msgid "_Open" msgstr "_Deschide" #: src/gmpv_menu.c:194 src/gmpv_menu.c:258 msgid "Open _Location" msgstr "_Deschide Adresa" #: src/gmpv_menu.c:195 src/gmpv_menu.c:235 msgid "_Save Playlist" msgstr "_Salvează Lista Redare" #: src/gmpv_menu.c:196 src/gmpv_menu.c:272 msgid "_Quit" msgstr "Î_nchide" #: src/gmpv_menu.c:197 msgid "_Edit" msgstr "_Modifică" #: src/gmpv_menu.c:198 src/gmpv_menu.c:268 msgid "_Preferences" msgstr "_Preferințe" #: src/gmpv_menu.c:199 src/gmpv_menu.c:237 msgid "_Video Track" msgstr "" #: src/gmpv_menu.c:200 src/gmpv_menu.c:238 msgid "_Audio Track" msgstr "" #: src/gmpv_menu.c:201 src/gmpv_menu.c:239 msgid "S_ubtitle Track" msgstr "" #: src/gmpv_menu.c:202 msgid "_View" msgstr "_Vizualizare" #: src/gmpv_menu.c:203 src/gmpv_menu.c:232 msgid "_Toggle Controls" msgstr "" #: src/gmpv_menu.c:204 src/gmpv_menu.c:234 msgid "_Toggle Playlist" msgstr "_Afișează Lista Redare" #: src/gmpv_menu.c:205 msgid "_Fullscreen" msgstr "_Tot ecranul" #: src/gmpv_menu.c:206 src/gmpv_menu.c:241 msgid "_Normal Size" msgstr "_Dimensiune Normală" #: src/gmpv_menu.c:207 src/gmpv_menu.c:242 msgid "_Double Size" msgstr "_Dimensiune Dublă" #: src/gmpv_menu.c:208 src/gmpv_menu.c:243 msgid "_Half Size" msgstr "_Dimensiune Înjumătățită" #: src/gmpv_menu.c:209 msgid "_Help" msgstr "_Ajutor" #: src/gmpv_menu.c:210 src/gmpv_menu.c:270 msgid "_Keyboard Shortcuts" msgstr "" #: src/gmpv_menu.c:211 src/gmpv_menu.c:271 msgid "_About" msgstr "_Despre" #: src/gmpv_mpv.c:256 #, fuzzy, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "" #: src/gmpv_mpv.c:917 msgid "Failed to apply one or more MPV options." msgstr "" #: src/gmpv_open_loc_dialog.c:79 msgid "Location:" msgstr "Adresă:" #: src/gmpv_open_loc_dialog.c:83 src/gmpv_pref_dialog.c:410 msgid "_Cancel" msgstr "_Anulează" #: src/gmpv_playlist_widget.c:508 msgid "_Add…" msgstr "" #: src/gmpv_playlist_widget.c:512 msgid "Add _Location…" msgstr "" #: src/gmpv_playlist_widget.c:514 msgid "Loop" msgstr "Buclă" #: src/gmpv_playlist_widget.c:612 msgid "Playlist" msgstr "Listă de redare" #: src/gmpv_plugins_manager.c:142 src/gmpv_plugins_manager.c:373 msgid "Add Lua Script" msgstr "" #: src/gmpv_plugins_manager.c:149 src/gmpv_pref_dialog.c:204 msgid "All Files" msgstr "" #: src/gmpv_plugins_manager.c:154 src/gmpv_pref_dialog.c:407 msgid "Lua Scripts" msgstr "" #: src/gmpv_plugins_manager.c:300 #, fuzzy, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "" #: src/gmpv_plugins_manager.c:349 msgid "No Lua script found" msgstr "" #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "" #: src/gmpv_plugins_manager_item.c:184 #, fuzzy, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "" #: src/gmpv_pref_dialog.c:209 msgid "Configuration Files" msgstr "" #: src/gmpv_pref_dialog.c:331 msgid "User Interface" msgstr "" #: src/gmpv_pref_dialog.c:334 msgid "Enable client-side decorations" msgstr "Activează decorațiile ferestrelor (CSD)" #: src/gmpv_pref_dialog.c:337 msgid "Enable dark theme" msgstr "Activează tema întunecată" #: src/gmpv_pref_dialog.c:340 msgid "Use floating controls in windowed mode" msgstr "" #: src/gmpv_pref_dialog.c:343 msgid "Remember last file's location" msgstr "Ține minte adresa ultimului fișier" #: src/gmpv_pref_dialog.c:346 msgid "MPV Configuration" msgstr "Configurare MPV" #: src/gmpv_pref_dialog.c:349 msgid "Load MPV configuration file" msgstr "Încarcă fișierul de configurare MPV" #: src/gmpv_pref_dialog.c:352 msgid "MPV configuration file:" msgstr "fișier configurare MPV:" #: src/gmpv_pref_dialog.c:355 msgid "Keybindings" msgstr "Combinații Taste" #: src/gmpv_pref_dialog.c:358 msgid "Load MPV input configuration file" msgstr "Încarcă fișierul MPV de combinații taste" #: src/gmpv_pref_dialog.c:361 msgid "MPV input configuration file:" msgstr "fișier MPV configurare combinații taste:" #: src/gmpv_pref_dialog.c:364 msgid "Miscellaneous" msgstr "Diverse" #: src/gmpv_pref_dialog.c:370 msgid "Extra MPV options:" msgstr "Extraopțiuni MPV:" #: src/gmpv_pref_dialog.c:403 msgid "General" msgstr "" #: src/gmpv_pref_dialog.c:412 msgid "_Save" msgstr "_Salvează" #: src/gmpv_pref_dialog.c:429 msgid "Preferences" msgstr "Preferințe" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "" #: src/gmpv_shortcuts_window.c:58 msgid "Show preferences dialog" msgstr "" #: src/gmpv_shortcuts_window.c:59 msgid "Toggle controls" msgstr "" #: src/gmpv_shortcuts_window.c:60 msgid "Toggle playlist" msgstr "" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle fullscreen mode" msgstr "" #: src/gmpv_shortcuts_window.c:62 msgid "Leave fullscreen mode" msgstr "" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle OSD states between normal and playback time/duration" msgstr "" #: src/gmpv_shortcuts_window.c:64 msgid "Show filename on the OSD" msgstr "" #: src/gmpv_shortcuts_window.c:65 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "" #: src/gmpv_shortcuts_window.c:68 msgid "Seek backward/forward 5 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:69 msgid "Exact seek backward/forward 1 second" msgstr "" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 1 minute" msgstr "" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 5 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:72 msgid "Seek to previous/next subtitle" msgstr "" #: src/gmpv_shortcuts_window.c:73 msgid "Step backward/forward a single frame" msgstr "" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to the beginning of the previous/next chapter" msgstr "" #: src/gmpv_shortcuts_window.c:77 msgid "Decrease/increase playback speed by 10%" msgstr "" #: src/gmpv_shortcuts_window.c:78 msgid "Halve/double current playback speed" msgstr "" #: src/gmpv_shortcuts_window.c:79 msgid "Reset playback speed to normal" msgstr "" #: src/gmpv_shortcuts_window.c:80 msgid "Go backward/forward in the playlist" msgstr "" #: src/gmpv_shortcuts_window.c:81 msgid "Remove selected playlist item" msgstr "" #: src/gmpv_shortcuts_window.c:82 msgid "Save playlist" msgstr "" #: src/gmpv_shortcuts_window.c:83 msgid "Set/clear A-B loop points" msgstr "" #: src/gmpv_shortcuts_window.c:84 msgid "Toggle infinite looping" msgstr "" #: src/gmpv_shortcuts_window.c:85 msgid "Pause or unpause" msgstr "" #: src/gmpv_shortcuts_window.c:86 msgid "Quit" msgstr "" #: src/gmpv_shortcuts_window.c:87 msgid "Save current playback position and quit" msgstr "" #: src/gmpv_shortcuts_window.c:90 msgid "Cycle through audio tracks" msgstr "" #: src/gmpv_shortcuts_window.c:91 src/gmpv_shortcuts_window.c:92 msgid "Decrease/increase volume" msgstr "" #: src/gmpv_shortcuts_window.c:93 msgid "Mute or unmute" msgstr "" #: src/gmpv_shortcuts_window.c:94 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:97 msgid "Toggle subtitle visibility" msgstr "" #: src/gmpv_shortcuts_window.c:98 msgid "Cycle through available subtitles" msgstr "" #: src/gmpv_shortcuts_window.c:99 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:100 msgid "Toggle SSA/ASS subtitles style override" msgstr "" #: src/gmpv_shortcuts_window.c:101 msgid "Move subtitles up/down" msgstr "" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle VSFilter aspect compatibility mode" msgstr "" #: src/gmpv_shortcuts_window.c:105 msgid "Cycle through video tracks" msgstr "" #: src/gmpv_shortcuts_window.c:106 msgid "Decrease/increase pan-and-scan range" msgstr "" #: src/gmpv_shortcuts_window.c:107 msgid "Take a screenshot" msgstr "" #: src/gmpv_shortcuts_window.c:108 msgid "Take a screenshot, without subtitles" msgstr "" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot, as the window shows it" msgstr "" #: src/gmpv_shortcuts_window.c:110 msgid "Resize video to half its original size" msgstr "" #: src/gmpv_shortcuts_window.c:111 msgid "Resize video to its original size" msgstr "" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to double its original size" msgstr "" #: src/gmpv_shortcuts_window.c:113 msgid "Adjust contrast" msgstr "" #: src/gmpv_shortcuts_window.c:114 msgid "Adjust brightness" msgstr "" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust gamma" msgstr "" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust saturation" msgstr "" #: src/gmpv_shortcuts_window.c:117 msgid "Activate or deactivate deinterlacer" msgstr "" #: src/gmpv_shortcuts_window.c:118 msgid "Cycle aspect ratio override" msgstr "" #: src/gmpv_shortcuts_window.c:121 msgid "User Interface" msgstr "" #: src/gmpv_shortcuts_window.c:122 msgid "Video" msgstr "" #: src/gmpv_shortcuts_window.c:123 msgid "Audio" msgstr "" #: src/gmpv_shortcuts_window.c:124 msgid "Subtitle" msgstr "" #: src/gmpv_shortcuts_window.c:125 msgid "Playback" msgstr "" #: src/gmpv_shortcuts_window.c:126 msgid "Seeking" msgstr "" gnome-mpv-0.13/po/ru.po000066400000000000000000000602721317030365200147550ustar00rootroot00000000000000# Maxim Orlov , 2016. #zanata # gnome-mpv , 2016. #zanata # Maxim Orlov , 2017. #zanata # gnome-mpv , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: 0.6\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2016-01-04 00:00+0700\n" "PO-Revision-Date: 2017-08-02 12:10-0400\n" "Last-Translator: Copied by Zanata \n" "Language-Team: Russian\n" "Language: ru\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=3; plural=(n%10==1 && n%100!=11 ? 0 : n%10>=2 && n%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2)\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "Включить или отключить тёмную тему" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 msgid "Enable or disable client-side decorations" msgstr "Включить или отключить декорирование на стороне клиента" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "Запомнить или нет последнее расположение в диалоге открытия файла" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "Перейти к опциям MPV" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 msgid "Path to mpv configuration file" msgstr "Путь к файлу конфигурации MPV" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 msgid "Load or don't load mpv configuration file" msgstr "Загрузить файл конфигурации MPV" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 msgid "Path to mpv input configuration file" msgstr "Путь к файлу конфигурации ввода MPV" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 msgid "Load or don't load mpv input configuration file" msgstr "Загрузить файл конфигурации ввода MPV" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 msgid "Width of the window" msgstr "Ширина окна" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 msgid "Height of the window" msgstr "Высота окна" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 msgid "Volume of player" msgstr "Громкость плеера" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "Ширина списка воспроизведения" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "Показать или скрыть список воспроизведения" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "Адрес последнего открытого файла" #: data/io.github.GnomeMpv.gschema.xml:10 msgid "" "Whether the settings has already been migrated from the previous version" msgstr "Перенос (миграция) пользовательских настроек из предыдущей версии" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:82 msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 msgid "Show or not show the controls" msgstr "Показать или не показывать элементы управления" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "GTK+ интерфейс для MPV" #: data/io.github.GnomeMpv.appdata.xml.in:12 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" "GNOME MPV - это простая GTK+ оболочка для MPV, поэтому является очень мощным" " медиаплеером, который способен воспроизводить практически все видео и аудио" " форматы. Дизайн GNOME MPV соответствует GNOME HIG. GNOME MPV также " "предлагает опцию, чтобы отключить декорирование на стороне клиента (CSD) для" " лучшей совместимости с системами, отличными от GNOME." #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "Возможности:" #: data/io.github.GnomeMpv.appdata.xml.in:21 msgid "Drag and drop playlist" msgstr "Поддержка Drag'n'Drop" #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "Loading external mpv configuration files" msgstr "Загрузка внешних конфигурационных файлов MPV" #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "Интерфейс MPRIS2 D-Bus" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "Главное окно с отключённым CSD" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "Главное окно с открытым списком воспроизведения" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "gnome-mpv" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "" #: src/gmpv_application.c:370 msgid "Playing" msgstr "Воспроизводится" #: src/gmpv_application.c:415 msgid "Show release version" msgstr "Показать версию релиза" #: src/gmpv_application.c:423 msgid "Enqueue" msgstr "Поставить в очередь" #: src/gmpv_application.c:431 msgid "Create a new window" msgstr "" #: src/gmpv_application.c:439 msgid "Don't connect to an already-running instance" msgstr "Не подключаться к уже работающему экземпляру" #: src/gmpv_control_box.c:286 msgid "Pause" msgstr "Приостановить" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 msgid "Play" msgstr "Воспроизвести" #: src/gmpv_control_box.c:436 msgid "Stop" msgstr "Остановить" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "Перемотать вперёд" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "Перемотать назад" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "Следующая глава" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "Предыдущая глава" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 msgid "Toggle Fullscreen" msgstr "Переход в полноэкранный режим и обратно" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 msgid "Error" msgstr "Ошибка" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "_Отмена" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "_Открыть" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 msgid "All Files" msgstr "Все файлы" #: src/gmpv_file_chooser.c:143 msgid "Media Files" msgstr "Медиафайлы" #: src/gmpv_file_chooser.c:154 msgid "Audio Files" msgstr "Аудиофайлы" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "Видеофайлы" #: src/gmpv_file_chooser.c:170 msgid "Image Files" msgstr "Файлы изображений" #: src/gmpv_file_chooser.c:180 msgid "Subtitle Files" msgstr "Файлы субтитров" #: src/gmpv_menu.c:102 msgid "None" msgstr "Ничего" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 msgid "Unknown" msgstr "Неизвестный" #: src/gmpv_menu.c:150 msgid "_Load External…" msgstr "_Загрузить внешние…" #: src/gmpv_menu.c:243 msgid "_File" msgstr "_Файл" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "Открыть _адрес" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "_Сохранить список воспроизведения" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "_Выйти" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "_Правка" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "_Настройки" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "_Видео дорожка" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 msgid "_Audio Track" msgstr "_Аудио дорожка" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 msgid "S_ubtitle Track" msgstr "Дорожка с_убтитров" #: src/gmpv_menu.c:253 msgid "_View" msgstr "_Вид" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "_Показать/Скрыть элементы управления" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 msgid "_Toggle Playlist" msgstr "_Показать/Скрыть список воспроизведения" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "_Полноэкранный режим" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "_Нормальный размер" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 msgid "_Double Size" msgstr "_Двойной размер" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 msgid "_Half Size" msgstr "_Половинный размер" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "_Справка" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 msgid "_Keyboard Shortcuts" msgstr "Комбинации клавиш" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "_О программе" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "Воспроизведение было прекращено. Причина: %s." #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "Адрес:" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "Не удалось применить одну или несколько опций MPV." #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "_Добавить…" #: src/gmpv_playlist_widget.c:537 msgid "Add _Location…" msgstr "Добавить _Адрес…" #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "Список воспроизведения" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "Добавить Lua скрипт" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 msgid "Lua Scripts" msgstr "Lua скрипты" #: src/gmpv_plugins_manager.c:299 #, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "Не удалось скопировать файл из '%s' в '%s'. Причина: %s" #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "Пусто" #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "Удалить" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "" "Вы уверены, что хотите удалить этот скрипт? Это действие не может быть " "отменено." #: src/gmpv_plugins_manager_item.c:184 #, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "Не удалось удалить файл '%s'. Причина: %s" #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "Пользовательский интерфейс" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "Включить декорирование на стороне клиента" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "Использовать тёмный вариант темы" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "Запомнить последнее расположение файла(ов)" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr "Конфигурация MPV" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "Загрузить файл конфигурации MPV" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr "Файл конфигурации MPV:" #: src/gmpv_preferences_dialog.c:314 msgid "Keybindings" msgstr "Комбинации клавиш" #: src/gmpv_preferences_dialog.c:317 msgid "Load MPV input configuration file" msgstr "Загрузить файл конфигурации ввода MPV" #: src/gmpv_preferences_dialog.c:320 msgid "MPV input configuration file:" msgstr "Файл конфигурации ввода MPV:" #: src/gmpv_preferences_dialog.c:323 msgid "Miscellaneous" msgstr "Разное" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "" #: src/gmpv_preferences_dialog.c:335 msgid "Enable media keys support" msgstr "" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "Дополнительные опции MPV:" #: src/gmpv_preferences_dialog.c:371 msgid "General" msgstr "Общие" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "_Сохранить" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "Настройки" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "Открыть файл" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "Открыть адрес" #: src/gmpv_shortcuts_window.c:58 msgid "Add file to playlist" msgstr "Добавить файл в список воспроизведения" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "Показать диалог настройки" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "Показать/Скрыть элементы управления" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "Показать/Скрыть список воспроизведения" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle fullscreen mode" msgstr "Перейти в полноэкранный режим" #: src/gmpv_shortcuts_window.c:64 msgid "Leave fullscreen mode" msgstr "Покинуть полноэкранный режим" #: src/gmpv_shortcuts_window.c:65 msgid "Toggle OSD states between normal and playback time/duration" msgstr "Показать время воспроизведения/продолжительность" #: src/gmpv_shortcuts_window.c:66 msgid "Show filename on the OSD" msgstr "Показать имя файла" #: src/gmpv_shortcuts_window.c:67 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "Показать прогресс, пройденное время и продолжительность" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 5 seconds" msgstr "Переход назад/вперёд на 5 секунд" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 1 second" msgstr "Точный переход назад/вперёд на 1 секунду" #: src/gmpv_shortcuts_window.c:72 msgid "Seek backward/forward 1 minute" msgstr "Переход назад/вперёд на 1 минуту" #: src/gmpv_shortcuts_window.c:73 msgid "Exact seek backward/forward 5 seconds" msgstr "Точный переход назад/вперёд на 5 секунд" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to previous/next subtitle" msgstr "Переход к предыдущему/следующему субтитру" #: src/gmpv_shortcuts_window.c:75 msgid "Step backward/forward a single frame" msgstr "Шаг назад/вперёд на один кадр" #: src/gmpv_shortcuts_window.c:76 msgid "Seek to the beginning of the previous/next chapter" msgstr "Переход к предыдущей/следующей главе" #: src/gmpv_shortcuts_window.c:79 msgid "Decrease/increase playback speed by 10%" msgstr "Уменьшить/увеличить скорость воспроизведения на 10%" #: src/gmpv_shortcuts_window.c:80 msgid "Halve/double current playback speed" msgstr "" #: src/gmpv_shortcuts_window.c:81 msgid "Reset playback speed to normal" msgstr "Сбросить скорость воспроизведения на нормальную" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "Назад/вперёд по списку воспроизведения" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "Удалить выбранный файл из списка воспроизведения" #: src/gmpv_shortcuts_window.c:84 msgid "Save playlist" msgstr "Сохранить список воспроизведения" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "Установить/очистить A-B точки цикла" #: src/gmpv_shortcuts_window.c:86 msgid "Toggle infinite looping" msgstr "" #: src/gmpv_shortcuts_window.c:87 msgid "Pause or unpause" msgstr "Приостановить или возобновить" #: src/gmpv_shortcuts_window.c:88 msgid "Quit" msgstr "Выйти" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "Сохранить текущую позицию воспроизведения и выйти" #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "Циклически доступные аудио дорожки" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "Уменьшить/увеличить громкость" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "Отключить или включить звук" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "Изменить задержку аудио на + / - 0,1 секунды" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "Переключить видимости субтитров" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "Циклически переключить доступные субтитры" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "Изменить задержку субтитров на + / - 0,1 секунды" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "" #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "Переместить субтитры вверх/вниз" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "" #: src/gmpv_shortcuts_window.c:107 msgid "Cycle through video tracks" msgstr "Циклически доступные видео дорожки" #: src/gmpv_shortcuts_window.c:108 msgid "Decrease/increase pan-and-scan range" msgstr "Уменьшает/увеличивает диапазон панорамирования и сканирования" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot" msgstr "Сделать скриншот" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "Сделать скриншот, без субтитров" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "Сделать скриншот, с субтитрами и OSD, масштабированием" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "Изменить размер видео до половины своего исходного размера" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "Изменить размер видео до исходного размера" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "Регулировка контрастности" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "Регулировка яркости" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "Регулировка гаммы" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "Регулировка насыщенности" #: src/gmpv_shortcuts_window.c:119 msgid "Activate or deactivate deinterlacer" msgstr "Включить или отключить деинтерлейсинг" #: src/gmpv_shortcuts_window.c:120 msgid "Cycle aspect ratio override" msgstr "Цикл коррекции соотношения сторон" #: src/gmpv_shortcuts_window.c:123 msgid "User Interface" msgstr "Пользовательский интерфейс" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "Видео" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "Аудио" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "Субтитры" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "Воспроизведение" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "Переход" #: src/gmpv_view.c:711 msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "" #: src/gmpv_view.c:1280 msgid "Add File to Playlist" msgstr "Добавить файл в список воспроизведения" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "Открыть файл" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "Добавить адрес в список воспроизведения" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "Открыть адрес" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "Загрузить звуковую дорожку…" #: src/gmpv_view.c:1349 msgid "Load Subtitle Track…" msgstr "Загрузить субтитры…" #: src/gmpv_view.c:1374 msgid "Save Playlist" msgstr "Сохранить список воспроизведения" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "GTK интерфейс для MPV" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "Maxim Orlov , 2016." gnome-mpv-0.13/po/sr.po000066400000000000000000000567121317030365200147570ustar00rootroot00000000000000# gnome-mpv , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: gnome-mpv 0.12\n" "Report-Msgid-Bugs-To: https://github.com/gnome-mpv/gnome-mpv/issues\n" "POT-Creation-Date: 2017-07-12 12:38+0700\n" "PO-Revision-Date: 2017-08-02 12:11-0400\n" "Last-Translator: Copied by Zanata \n" "Language-Team: Serbian (Cyrillic)\n" "Language: sr\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=3; plural=(n%10==1 && n%100!=11 ? 0 : n%10>=2 && n%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2)\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "Омогући или онемогући тамну тему" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 msgid "Enable or disable client-side decorations" msgstr "Омогући или онемогући украсе клијента" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "" "Дозвољава дијалогу бирача датотека да упамти последње приступљен " "директоријум" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "Опције које треба пренети на mpv" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 msgid "Path to mpv configuration file" msgstr "Путања до mpv конфигурационе датотеке" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 msgid "Load or don't load mpv configuration file" msgstr "Дозвољава учитавање mpv конфигурационе датотеке" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 msgid "Path to mpv input configuration file" msgstr "Путања до mpv конфигурационе датотеке уноса" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 msgid "Load or don't load mpv input configuration file" msgstr "Дозвољава учитавање mpv конфигурационе датотеке уноса" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 msgid "Width of the window" msgstr "Ширина прозора" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 msgid "Height of the window" msgstr "Висина прозора" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 msgid "Volume of player" msgstr "Јачина звука" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "Ширина листе пуштања" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "Прикажи листу пуштања" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "URI последње приступљеног директоријума" #: data/io.github.GnomeMpv.gschema.xml:10 msgid "" "Whether the settings has already been migrated from the previous version" msgstr "Да ли су поставке већ пренете из претходне верзије" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "Користи пливајуће контроле у режиму прозора" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:82 msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 msgid "Show or not show the controls" msgstr "Дозвољава приказ контрола" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "GTK+ прочеље за mpv" #: data/io.github.GnomeMpv.appdata.xml.in:12 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" "GNOME MPV је једноставно GTK+ прочеље за mpv, који је веома моћан приказивач" " способан да пусти практично све видео и аудио формате. Дизајн GNOME MPV-а " "је базиран на GNOME HIG, али је независтан од било које GNOME библиотеке. " "GNOME MPV такође нуди опцију онемогућавања декорација клијента (CSD) због " "компатибилности с другим окружењима." #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "Могућности:" #: data/io.github.GnomeMpv.appdata.xml.in:21 msgid "Drag and drop playlist" msgstr "Превуци и отпусти листу пуштања" #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "Loading external mpv configuration files" msgstr "Учитавам спољне mpv конфигурационе датотеке" #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "MPRIS2 D-Bus сучеље" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "Главни прозор са онемогућеним CSD-ом" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "Главни прозор са отвореном листом пуштања" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "" #: src/gmpv_application.c:370 msgid "Playing" msgstr "Репродукција" #: src/gmpv_application.c:415 msgid "Show release version" msgstr "Прикажи верзију издања" #: src/gmpv_application.c:423 msgid "Enqueue" msgstr "Нанижи" #: src/gmpv_application.c:431 msgid "Create a new window" msgstr "" #: src/gmpv_application.c:439 msgid "Don't connect to an already-running instance" msgstr "Не повезуј на већ покренут примерак" #: src/gmpv_control_box.c:286 msgid "Pause" msgstr "Паузирај" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 msgid "Play" msgstr "Пусти" #: src/gmpv_control_box.c:436 msgid "Stop" msgstr "Заустави" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "Напред" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "Назад" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "Следеће Поглавље" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "Претходно Поглавље" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 msgid "Toggle Fullscreen" msgstr "Цео Екран" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 msgid "Error" msgstr "Грешка" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "_Откажи" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "_Отвори" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 msgid "All Files" msgstr "Све Датотеке" #: src/gmpv_file_chooser.c:143 msgid "Media Files" msgstr "" #: src/gmpv_file_chooser.c:154 msgid "Audio Files" msgstr "" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "" #: src/gmpv_file_chooser.c:170 msgid "Image Files" msgstr "" #: src/gmpv_file_chooser.c:180 msgid "Subtitle Files" msgstr "" #: src/gmpv_menu.c:102 msgid "None" msgstr "Ниједан" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 msgid "Unknown" msgstr "Непознато" #: src/gmpv_menu.c:150 msgid "_Load External…" msgstr "_Учитај Спољне..." #: src/gmpv_menu.c:243 msgid "_File" msgstr "_Датотека" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "Отвори_Локацију" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "_Сачувај Листу Пуштања" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "_Напусти" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "_Уреди" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "_Поставке" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "_Видео Снимак" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 msgid "_Audio Track" msgstr "_Аудио Снимак" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 msgid "S_ubtitle Track" msgstr "_Превод" #: src/gmpv_menu.c:253 msgid "_View" msgstr "_Преглед" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "_Прикажи Контроле" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 msgid "_Toggle Playlist" msgstr "_Прикажи Листу Пуштања" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "_Цео Екран" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "_Нормална Величина" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 msgid "_Double Size" msgstr "_Двострука Величина" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 msgid "_Half Size" msgstr "_Упола Величине" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "_Помоћ" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 msgid "_Keyboard Shortcuts" msgstr "_Пречице Тастатуре" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "_О Нама" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, fuzzy, fuzzy, fuzzy, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "Репродукција је неправилно окончана. Разлог: %s." #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "Локација:" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "Неуспешна примена једне или више MPV опција." #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "_Додај..." #: src/gmpv_playlist_widget.c:537 msgid "Add _Location…" msgstr "Додај_Локацију..." #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "Листа Пуштања" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "Додај Lua Скрипту" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 msgid "Lua Scripts" msgstr "Lua Скрипте" #: src/gmpv_plugins_manager.c:299 #, fuzzy, fuzzy, fuzzy, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "Неуспешно копирање датотеке из '%s' у '%s'. Разлог: %s" #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "Lua скрипта није нађена" #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "Уклони" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "" "Сигурно желите да уклоните ову скрипту? Овај поступак не може бити опозван." #: src/gmpv_plugins_manager_item.c:184 #, fuzzy, fuzzy, fuzzy, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "Неуспешно брисање датотеке '%s'. Разлог: %s" #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "Корисничко Сучеље" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "Омогући украсе клијента" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "Омогући тамну тему" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "Користи пливајуће контроле у режиму прозора" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "Упамти локацију последње датотеке" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr "MPV Конфигурација" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "Учитај MPV конфигурациону датотеку" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr "MPV конфигурациона датотека:" #: src/gmpv_preferences_dialog.c:314 msgid "Keybindings" msgstr "Поставке Уноса" #: src/gmpv_preferences_dialog.c:317 msgid "Load MPV input configuration file" msgstr "Учитај MPV конфигурациону датотеку уноса" #: src/gmpv_preferences_dialog.c:320 msgid "MPV input configuration file:" msgstr "MPV конфигурациона датотека уноса:" #: src/gmpv_preferences_dialog.c:323 msgid "Miscellaneous" msgstr "Остало" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "" #: src/gmpv_preferences_dialog.c:335 msgid "Enable media keys support" msgstr "" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "Додатне MPV опције:" #: src/gmpv_preferences_dialog.c:371 msgid "General" msgstr "Опште" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "_Сачувај" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "Поставке" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "Отвори датотеку" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "Отвори локацију" #: src/gmpv_shortcuts_window.c:58 msgid "Add file to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "Прикажи дијалог поставки" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "Прикажи контроле" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "Прикажи листу пуштања" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle fullscreen mode" msgstr "Прикажи у режиму целог екрана" #: src/gmpv_shortcuts_window.c:64 msgid "Leave fullscreen mode" msgstr "Напусти режим целог екрана" #: src/gmpv_shortcuts_window.c:65 msgid "Toggle OSD states between normal and playback time/duration" msgstr "Промени OSD приказ између нормалног и време пуштања/дужина" #: src/gmpv_shortcuts_window.c:66 msgid "Show filename on the OSD" msgstr "Прикажи име датотеке у OSD" #: src/gmpv_shortcuts_window.c:67 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "Прикажи напредак, протекло време и дужину на OSD" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 5 seconds" msgstr "Пребаци 5 секунди уназад/унапред" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 1 second" msgstr "Пребаци тачно 1 секунд уназад/унапред" #: src/gmpv_shortcuts_window.c:72 msgid "Seek backward/forward 1 minute" msgstr "Пребаци 1 минут уназад/унапред" #: src/gmpv_shortcuts_window.c:73 msgid "Exact seek backward/forward 5 seconds" msgstr "Пребаци тачно 5 секунди уназад/унапред" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to previous/next subtitle" msgstr "Пребаци на претходни/следећи поднатпис" #: src/gmpv_shortcuts_window.c:75 msgid "Step backward/forward a single frame" msgstr "Корак за једну слику уназад/унапред" #: src/gmpv_shortcuts_window.c:76 msgid "Seek to the beginning of the previous/next chapter" msgstr "Пребаци на почетак претходног/следећег поглавља" #: src/gmpv_shortcuts_window.c:79 msgid "Decrease/increase playback speed by 10%" msgstr "Успори/убрзај репродукцију за 10%" #: src/gmpv_shortcuts_window.c:80 msgid "Halve/double current playback speed" msgstr "Преполови/удвостручи тренутну брзину репродукције" #: src/gmpv_shortcuts_window.c:81 msgid "Reset playback speed to normal" msgstr "Поврати нормалну брзину репродукције" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "Иди уназад/унапред у листи пуштања" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "Избаци означену ставку из листе пуштања" #: src/gmpv_shortcuts_window.c:84 msgid "Save playlist" msgstr "Сачувај листу пуштања" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "Постави/очисти A-B тачке понављања" #: src/gmpv_shortcuts_window.c:86 msgid "Toggle infinite looping" msgstr "Укључи бесконачно понављање" #: src/gmpv_shortcuts_window.c:87 msgid "Pause or unpause" msgstr "Паузирај или настави" #: src/gmpv_shortcuts_window.c:88 msgid "Quit" msgstr "Напусти" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "Сачувај тренутну позицију репродукције и напусти" #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "Кружи кроз аудио снимке" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "Смањи/појачај" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "Искључи или укључи звук" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "Прилагоди кашњење звука за +/- 0.1 секунд" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "Промени видљивост поднатписа" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "Кружи кроз доступне поднатписе" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "Прилагоди кашњење поднатписа за +/- 0.1 секунд" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "Измени SSA/ASS стил поднатписа" #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "Помери поднатписе горе/доле" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "Измени VSFilter режим усклађености" #: src/gmpv_shortcuts_window.c:107 msgid "Cycle through video tracks" msgstr "Кружи кроз видео снимке" #: src/gmpv_shortcuts_window.c:108 #, fuzzy msgid "Decrease/increase pan-and-scan range" msgstr "Повећај/умањи опсег скенирања односа" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot" msgstr "Направи снимак екрана" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "Направи снимак екрана без поднатписа" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "Направи снимак екрана како га прозор приказује" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "Преполови оригиналну величину видео снимка" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "Поврати оригиналну величину видео снимка" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "Удвостручи оригиналну величину видео снимка" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "Прилагоди контраст" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "Прилагоди осветљеност" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "Прилагоди гаму" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "Прилагоди засићење" #: src/gmpv_shortcuts_window.c:119 msgid "Activate or deactivate deinterlacer" msgstr "Омогући или онемогући преплитање" #: src/gmpv_shortcuts_window.c:120 msgid "Cycle aspect ratio override" msgstr "Кружи кроз промену размере" #: src/gmpv_shortcuts_window.c:123 msgid "User Interface" msgstr "Корисничко Сучеље" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "Видео" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "Аудио" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "Поднатпис" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "Репродукција" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "Трагање" #: src/gmpv_view.c:711 msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "" #: src/gmpv_view.c:1280 msgid "Add File to Playlist" msgstr "Додај Датотеку у Листу Пуштања" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "Отвори Датотеку" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "Додај Локацију у Листу Пуштања" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "Отвори Локацију" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "" #: src/gmpv_view.c:1349 msgid "Load Subtitle Track…" msgstr "" #: src/gmpv_view.c:1374 msgid "Save Playlist" msgstr "Сачувај Листу Пуштања" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "GTK прочеље за MPV" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "Срђан С." gnome-mpv-0.13/po/sr@latin.po000066400000000000000000000504231317030365200161000ustar00rootroot00000000000000# gnome-mpv , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: gnome-mpv 0.12\n" "Report-Msgid-Bugs-To: https://github.com/gnome-mpv/gnome-mpv/issues\n" "POT-Creation-Date: 2017-07-12 12:38+0700\n" "PO-Revision-Date: 2017-08-02 12:11-0400\n" "Last-Translator: Copied by Zanata \n" "Language-Team: Serbian (Latin)\n" "Language: sr@latin\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=3; plural=(n%10==1 && n%100!=11 ? 0 : n%10>=2 && n%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2)\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "Omogući ili onemogući tamnu temu" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 msgid "Enable or disable client-side decorations" msgstr "Omogući ili onemogući ukrase klijenta" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "" "Dozvoljava dijalogu birača datoteka da upamti poslednje pristupljen " "direktorijum" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "Opcije koje treba preneti na mpv" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 msgid "Path to mpv configuration file" msgstr "Putanja do mpv konfiguracione datoteke" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 msgid "Load or don't load mpv configuration file" msgstr "Dozvoljava učitavanje mpv konfiguracione datoteke" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 msgid "Path to mpv input configuration file" msgstr "Putanja do mpv konfiguracione datoteke unosa" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 msgid "Load or don't load mpv input configuration file" msgstr "Dozvoljava učitavanje mpv konfiguracione datoteke unosa" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 msgid "Width of the window" msgstr "Širina prozora" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 msgid "Height of the window" msgstr "Visina prozora" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 msgid "Volume of player" msgstr "Jačina zvuka" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "Širina liste puštanja" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "Prikaži listu puštanja" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "URI poslednje pristupljenog direktorijuma" #: data/io.github.GnomeMpv.gschema.xml:10 msgid "" "Whether the settings has already been migrated from the previous version" msgstr "Da li su postavke već prenete iz prethodne verzije" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "Koristiti plivajuće kontrole u režimu prozora" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:82 msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 msgid "Show or not show the controls" msgstr "Dozvoljava prikaz kontrola" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "GTK+ pročelje za mpv" #: data/io.github.GnomeMpv.appdata.xml.in:12 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" "GNOME MPV je jednostavno GTK+ pročelje za mpv, koji je veoma moćan " "prikazivač sposoban da pusti praktično sve video i audio formate. Dizajn " "GNOME MPV-a je baziran na GNOME HIG, ali je nezavistan od bilo koje GNOME " "biblioteke. GNOME MPV takođe nudi opciju onemogućavanja dekoracija klijenta " "(CSD) zbog kompatibilnosti s drugim okruženjima." #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "Mogućnosti:" #: data/io.github.GnomeMpv.appdata.xml.in:21 msgid "Drag and drop playlist" msgstr "Prevuci i otpusti listu puštanja" #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "Loading external mpv configuration files" msgstr "Učitavam spoljne mpv konfiguracione datoteke" #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "MPRIS2 D-Bus sučelje" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "Glavni prozor sa onemogućenim CSD-om" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "Glavni prozor sa otvorenom listom puštanja" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "" #: src/gmpv_application.c:370 msgid "Playing" msgstr "Reprodukcija" #: src/gmpv_application.c:415 msgid "Show release version" msgstr "Prikaži verziju izdanja" #: src/gmpv_application.c:423 msgid "Enqueue" msgstr "Naniži" #: src/gmpv_application.c:431 msgid "Create a new window" msgstr "" #: src/gmpv_application.c:439 msgid "Don't connect to an already-running instance" msgstr "Ne povezuj na već pokrenut primerak" #: src/gmpv_control_box.c:286 msgid "Pause" msgstr "Pauziraj" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 msgid "Play" msgstr "Pusti" #: src/gmpv_control_box.c:436 msgid "Stop" msgstr "Zaustavi" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "Napred" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "Nazad" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "Sledeće Poglavlje" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "Prethodno Poglavlje" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 msgid "Toggle Fullscreen" msgstr "Ceo Ekran" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 msgid "Error" msgstr "Greška" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "_Otkaži" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "_Otvori" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 msgid "All Files" msgstr "Sve Datoteke" #: src/gmpv_file_chooser.c:143 msgid "Media Files" msgstr "" #: src/gmpv_file_chooser.c:154 msgid "Audio Files" msgstr "" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "" #: src/gmpv_file_chooser.c:170 msgid "Image Files" msgstr "" #: src/gmpv_file_chooser.c:180 msgid "Subtitle Files" msgstr "" #: src/gmpv_menu.c:102 msgid "None" msgstr "Nijedan" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 msgid "Unknown" msgstr "Nepoznato" #: src/gmpv_menu.c:150 msgid "_Load External…" msgstr "_Učitaj Spoljne..." #: src/gmpv_menu.c:243 msgid "_File" msgstr "_Datoteka" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "Otvori_Lokaciju" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "_Sačuvaj Listu Puštanja" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "_Napusti" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "_Uredi" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "_Postavke" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "_Video Snimak" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 msgid "_Audio Track" msgstr "_Audio Snimak" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 msgid "S_ubtitle Track" msgstr "_Prevod" #: src/gmpv_menu.c:253 msgid "_View" msgstr "_Pregled" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "_Prikaži Kontrole" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 msgid "_Toggle Playlist" msgstr "_Prikaži Listu Puštanja" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "_Ceo Ekran" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "_Normalna Veličina" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 msgid "_Double Size" msgstr "_Dvostruka Veličina" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 msgid "_Half Size" msgstr "_Upola Veličine" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "_Pomoć" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 msgid "_Keyboard Shortcuts" msgstr "_Prečice Tastature" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "_O Nama" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, fuzzy, fuzzy, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "Reprodukcija je nepravilno okončana. Razlog: %s." #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "Lokacija:" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "Neuspešna primena jedne ili više MPV opcija." #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "_Dodaj..." #: src/gmpv_playlist_widget.c:537 msgid "Add _Location…" msgstr "Dodaj_Lokaciju..." #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "Lista Puštanja" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "Dodaj Lua Skriptu" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 msgid "Lua Scripts" msgstr "Lua Skripte" #: src/gmpv_plugins_manager.c:299 #, fuzzy, fuzzy, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "Neuspešno kopiranje datoteke iz '%s' u '%s'. Razlog: %s" #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "Lua skripta nije nađena" #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "Ukloni" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "" "Sigurno želite da uklonite ovu skriptu? Ovaj postupak ne može biti opozvan." #: src/gmpv_plugins_manager_item.c:184 #, fuzzy, fuzzy, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "Neuspešno brisanje datoteke '%s'. Razlog: %s" #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "Korisničko Sučelje" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "Omogući ukrase klijenta" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "Omogući tamnu temu" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "Koristi plivajuće kontrole u režimu prozora" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "Upamti lokaciju poslednje datoteke" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr "MPV Konfiguracija" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "Učitaj MPV konfiguracionu datoteku" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr "MPV konfiguraciona datoteka:" #: src/gmpv_preferences_dialog.c:314 msgid "Keybindings" msgstr "Postavke Unosa" #: src/gmpv_preferences_dialog.c:317 msgid "Load MPV input configuration file" msgstr "Učitaj MPV konfiguracionu datoteku" #: src/gmpv_preferences_dialog.c:320 msgid "MPV input configuration file:" msgstr "MPV konfiguraciona datoteka unosa:" #: src/gmpv_preferences_dialog.c:323 msgid "Miscellaneous" msgstr "Ostalo" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "" #: src/gmpv_preferences_dialog.c:335 msgid "Enable media keys support" msgstr "" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "Dodatne MPV opcije:" #: src/gmpv_preferences_dialog.c:371 msgid "General" msgstr "Opšte" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "_Sačuvaj" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "Postavke" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "Otvori datoteku" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "Otvori lokaciju" #: src/gmpv_shortcuts_window.c:58 msgid "Add file to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "Prikaži dijalog postavki" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "Prikaži kontrole" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "Prikaži listu puštanja" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle fullscreen mode" msgstr "Prikaži u režimu celog ekrana" #: src/gmpv_shortcuts_window.c:64 msgid "Leave fullscreen mode" msgstr "Napusti režim celog ekrana" #: src/gmpv_shortcuts_window.c:65 msgid "Toggle OSD states between normal and playback time/duration" msgstr "Promeni OSD prikaz između normalnog i vreme puštanja/dužina" #: src/gmpv_shortcuts_window.c:66 msgid "Show filename on the OSD" msgstr "Prikaži ime datoteke u OSD" #: src/gmpv_shortcuts_window.c:67 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "Prikaži napredak, proteklo vreme i dužinu na OSD" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 5 seconds" msgstr "Prebaci 5 sekundi unazad/unapred" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 1 second" msgstr "Prebaci tačno 1 sekund unazad/unapred" #: src/gmpv_shortcuts_window.c:72 msgid "Seek backward/forward 1 minute" msgstr "Prebaci 1 minut unazad/unapred" #: src/gmpv_shortcuts_window.c:73 msgid "Exact seek backward/forward 5 seconds" msgstr "Prebaci tačno 5 sekundi unazad/unapred" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to previous/next subtitle" msgstr "Prebaci na prethodni/sledeći podnatpis" #: src/gmpv_shortcuts_window.c:75 msgid "Step backward/forward a single frame" msgstr "Korak za jednu sliku unazad/unapred" #: src/gmpv_shortcuts_window.c:76 msgid "Seek to the beginning of the previous/next chapter" msgstr "Prebaci na početak prethodnog/sledećeg poglavlja" #: src/gmpv_shortcuts_window.c:79 msgid "Decrease/increase playback speed by 10%" msgstr "Uspori/ubrzaj reprodukciju za 10%" #: src/gmpv_shortcuts_window.c:80 msgid "Halve/double current playback speed" msgstr "Prepolovi/udvostruči trenutnu brzinu reprodukcije" #: src/gmpv_shortcuts_window.c:81 msgid "Reset playback speed to normal" msgstr "Povrati normalnu brzinu reprodukcije" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "Idi unazad/unapred u listi puštanja" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "Izbaci označenu stavku iz liste puštanja" #: src/gmpv_shortcuts_window.c:84 msgid "Save playlist" msgstr "Sačuvaj listu puštanja" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "Postavi/očisti A-B tačke ponavljanja" #: src/gmpv_shortcuts_window.c:86 msgid "Toggle infinite looping" msgstr "Uključi beskonačno ponavljanje" #: src/gmpv_shortcuts_window.c:87 msgid "Pause or unpause" msgstr "Pauziraj ili nastavi" #: src/gmpv_shortcuts_window.c:88 msgid "Quit" msgstr "Napusti" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "Sačuvaj trenutnu poziciju reprodukcije i napusti" #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "Kruži kroz audio snimke" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "Smanji/pojačaj" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "Isključi ili uključi zvuk" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "Prilagodi kašnjenje zvuka za +/- 0.1 sekund" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "Promeni vidljivost podnatpisa" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "Kruži kroz dostupne podnatpise" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "Prilagodi kašnjenje podnatpisa za +/- 0.1 sekund" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "Izmeni SSA/ASS stil podnatpisa" #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "Pomeri podnatpis gore/dole" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "Izmeni VSFilter režim usklađenosti" #: src/gmpv_shortcuts_window.c:107 msgid "Cycle through video tracks" msgstr "Kruži kroz video snimke" #: src/gmpv_shortcuts_window.c:108 #, fuzzy msgid "Decrease/increase pan-and-scan range" msgstr "Povećaj/umanji opseg skeniranja odnosa" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot" msgstr "Napravi snimak ekrana" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "Napravi snimak ekrana bez podnatpisa" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "Napravi snimak ekrana kako ga prozor prikazuje" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "Prepolovi originalnu veličinu video snimka" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "Povrati originalnu veličinu video snimka" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "Udvostruči originalnu veličinu video snimka" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "Prilagodi kontrast" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "Prilagodi osvetljenost" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "Prilagodi gamu" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "Prilagodi zasićenje" #: src/gmpv_shortcuts_window.c:119 msgid "Activate or deactivate deinterlacer" msgstr "Omogući ili onemogući preplitanje" #: src/gmpv_shortcuts_window.c:120 msgid "Cycle aspect ratio override" msgstr "Kruži kroz promenu razmere" #: src/gmpv_shortcuts_window.c:123 msgid "User Interface" msgstr "Korisničko Sučelje" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "Video" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "Audio" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "Podnatpis" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "Reprodukcija" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "Traganje" #: src/gmpv_view.c:711 msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "" #: src/gmpv_view.c:1280 msgid "Add File to Playlist" msgstr "Dodaj Datoteku u Listu Puštanja" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "Otvori Datoteku" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "Dodaj Lokaciju u Listu Puštnja" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "Otvori Lokaciju" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "" #: src/gmpv_view.c:1349 msgid "Load Subtitle Track…" msgstr "" #: src/gmpv_view.c:1374 msgid "Save Playlist" msgstr "Sačuvaj Listu Puštanja" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "GTK pročelje za MPV" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "Srđan S." gnome-mpv-0.13/po/sv.po000066400000000000000000000517211317030365200147560ustar00rootroot00000000000000# Patrik Nilsson , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: gnome-mpv 0.12\n" "Report-Msgid-Bugs-To: https://github.com/gnome-mpv/gnome-mpv/issues\n" "POT-Creation-Date: 2017-10-08 17:16-0700\n" "PO-Revision-Date: 2017-09-14 08:54-0400\n" "Last-Translator: Patrik Nilsson \n" "Language-Team: Swedish\n" "Language: sv\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1)\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "Aktivera eller inaktivera mörkt tema" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 msgid "Enable or disable client-side decorations" msgstr "Aktivera eller inaktivera fönsterdekorationer i klienten" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "" "Om dialogrutan för val av filer ska komma ihåg den senast använda mappen " "eller inte" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "Alternativ att skicka vidare till mpv" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 msgid "Path to mpv configuration file" msgstr "Sökväg till mpv konfigurationsfil" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 msgid "Load or don't load mpv configuration file" msgstr "Läs eller läs ej in mpv konfigurationsfil" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 msgid "Path to mpv input configuration file" msgstr "Sökväg till konfigurationsfil för mpv tangentbindningar" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 msgid "Load or don't load mpv input configuration file" msgstr "Läs eller läs ej in konfigurationsfil för mpv tangentbindningar" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 msgid "Width of the window" msgstr "Fönsterbredd" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 msgid "Height of the window" msgstr "Fönsterhöjd" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 msgid "Volume of player" msgstr "Volym för spelaren" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "Spellistans bredd" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "Visa eller visa ej spellistan" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "URI för den senast använda mappen" #: data/io.github.GnomeMpv.gschema.xml:10 msgid "" "Whether the settings has already been migrated from the previous version" msgstr "Om inställningarna redan har migrerats från den föregående versionen" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "Om flytande kontroller ska aktiveras i fönsterläge eller inte" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "Om stöd för MPRIS ska aktiveras eller inte" #: data/io.github.GnomeMpv.gschema.xml:82 msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "" "Om stöd för GNOME-Settings-Daemon-baserade media knappar ska aktiveras eller" " inte" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 msgid "Show or not show the controls" msgstr "Visa eller visa ej kontrollerna" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "GTK+ gränssnitt för mpv" #: data/io.github.GnomeMpv.appdata.xml.in:12 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" "GNOME MPV är ett enkelt GTK+ drivet gränssnitt för mpv, som är en väldigt " "kraftfull mediaspelare kapabel att spela upp i princip alla video och ljud " "format. Utformningen av GNOME MPV är baserat på GNOME HIG, dock är det inte " "beroende av några GNOME bibliotek. GNOME MPV erbjuder även som alternativ " "att inaktivera fönsterdekorationer i klienten (CSD) för bättre " "kompatibilitet med icke-GNOME system. " #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "Funktioner:" #: data/io.github.GnomeMpv.appdata.xml.in:21 msgid "Drag and drop playlist" msgstr "Dra och släpp spellista" #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "Loading external mpv configuration files" msgstr "Läser in externa mpv konfigurationsfiler" #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "MPRIS2 D-Bus gränssnitt" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "Huvudfönstret med CSD inaktiverat" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "Huvudfönstret med spellista öppen" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "gnome-mpv" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "Nytt fönster" #: src/gmpv_application.c:370 msgid "Playing" msgstr "Spelar" #: src/gmpv_application.c:415 msgid "Show release version" msgstr "Visa utgivningsversion" #: src/gmpv_application.c:423 msgid "Enqueue" msgstr "Lägg till i kö" #: src/gmpv_application.c:431 msgid "Create a new window" msgstr "Skapa ett nytt fönster" #: src/gmpv_application.c:439 msgid "Don't connect to an already-running instance" msgstr "Anslut inte till en instans som redan körs" #: src/gmpv_control_box.c:286 msgid "Pause" msgstr "Paus" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 msgid "Play" msgstr "Spela upp" #: src/gmpv_control_box.c:436 msgid "Stop" msgstr "Stopp" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "Framåt" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "Spola tillbaka" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "Nästa kapitel" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "Föregående kapitel" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 msgid "Toggle Fullscreen" msgstr "Växla helskärm" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 msgid "Error" msgstr "Fel" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "_Avbryt" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "_Öppna" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 msgid "All Files" msgstr "Alla filer" #: src/gmpv_file_chooser.c:143 msgid "Media Files" msgstr "Mediefiler" #: src/gmpv_file_chooser.c:154 msgid "Audio Files" msgstr "Ljudfiler" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "Videofiler" #: src/gmpv_file_chooser.c:170 msgid "Image Files" msgstr "Bildfiler" #: src/gmpv_file_chooser.c:180 msgid "Subtitle Files" msgstr "Undertextfiler" #: src/gmpv_menu.c:102 msgid "None" msgstr "Inga" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 msgid "Unknown" msgstr "Okänd" #: src/gmpv_menu.c:150 msgid "_Load External…" msgstr "_Öppna externt..." #: src/gmpv_menu.c:243 msgid "_File" msgstr "_Fil" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "Öppna _Plats" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "_Spara spellista" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "_Avsluta" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "_Redigera" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "_Inställningar" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "_Videospår" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 msgid "_Audio Track" msgstr "_Ljudspår" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 msgid "S_ubtitle Track" msgstr "_Undertext-spår" #: src/gmpv_menu.c:253 msgid "_View" msgstr "_Visa" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "_Visa/dölj kontroller" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 msgid "_Toggle Playlist" msgstr "Visa/dölj _spellista" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "_Helskärm" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "_Normal storlek" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 msgid "_Double Size" msgstr "_Dubbel storlek" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 msgid "_Half Size" msgstr "_Halv storlek" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "_Hjälp" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 msgid "_Keyboard Shortcuts" msgstr "_Kortkommandon" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "_Om" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, fuzzy, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "Där uppstod ett onormalt avbrott under uppspelningen. Anledning: %s." #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "Plats:" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "Misslyckades att tillämpa en eller flera MPV alternativ." #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "_Lägg till..." #: src/gmpv_playlist_widget.c:537 msgid "Add _Location…" msgstr "Lägg till _plats:" #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "_Blanda" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "_Upprepa" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "Spellista" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "Lägg till lua-skript" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 msgid "Lua Scripts" msgstr "Lua-skript" #: src/gmpv_plugins_manager.c:299 #, fuzzy, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "Misslyckades att kopiera filen från '%s' till '%s'. Anledning: %s" #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "Inget lua-skript hittades" #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "Ta bort" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "" "Är du säker på att du vill ta bort detta skriptet? Denna åtgärden kan inte " "ångras." #: src/gmpv_plugins_manager_item.c:184 #, fuzzy, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "Misslyckades att radera filen '%s'. Anledning: %s" #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "Användargränssnitt" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "Aktivera fönsterdekorationer i klienten" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "Aktivera mörkt tema" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "Använd flytande kontroller i fönsterläge" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "Kom ihåg senaste filens plats" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr "MPV Konfiguration" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "Öppna MPV konfigurationsfil" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr "MPV konfigurationsfil:" #: src/gmpv_preferences_dialog.c:314 msgid "Keybindings" msgstr "Tangentbindningar" #: src/gmpv_preferences_dialog.c:317 msgid "Load MPV input configuration file" msgstr "Öppna MPV konfigurationsfil för tangentbindningar" #: src/gmpv_preferences_dialog.c:320 msgid "MPV input configuration file:" msgstr "MPV konfigurationsfil för tangentbindningar:" #: src/gmpv_preferences_dialog.c:323 msgid "Miscellaneous" msgstr "Diverse" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "Aktivera stöd för MPRIS" #: src/gmpv_preferences_dialog.c:335 msgid "Enable media keys support" msgstr "Aktivera stöd för media knappar" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "Extra MPV alternativ:" #: src/gmpv_preferences_dialog.c:371 msgid "General" msgstr "Allmänt" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "_Spara" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "Inställningar" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "Öppna fil" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "Öppna plats" #: src/gmpv_shortcuts_window.c:58 msgid "Add file to playlist" msgstr "Lägg till fil i spellista" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "Lägg till plats i spellista" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "Visa dialogrutan för alternativ" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "Visa/dölj kontroller" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "Visa/dölj spellista" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle fullscreen mode" msgstr "Växla helskärmsläge" #: src/gmpv_shortcuts_window.c:64 msgid "Leave fullscreen mode" msgstr "Lämna helskärmsläge" #: src/gmpv_shortcuts_window.c:65 msgid "Toggle OSD states between normal and playback time/duration" msgstr "Växla OSD-lägen mellan normal och uppspelningstid/speltid" #: src/gmpv_shortcuts_window.c:66 msgid "Show filename on the OSD" msgstr "Visa filnamn i OSD vyn" #: src/gmpv_shortcuts_window.c:67 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "Visa förlopp, förfluten tid och speltid i OSD vyn" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 5 seconds" msgstr "Sök bakåt/framåt med 5 sekunder" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 1 second" msgstr "Sök exakt bakåt/framåt med 1 sekund" #: src/gmpv_shortcuts_window.c:72 msgid "Seek backward/forward 1 minute" msgstr "Sök bakåt/framåt med 1 minut" #: src/gmpv_shortcuts_window.c:73 msgid "Exact seek backward/forward 5 seconds" msgstr "Sök exakt bakåt/framåt med 5 sekunder" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to previous/next subtitle" msgstr "Sök fram till föregående/nästa undertext" #: src/gmpv_shortcuts_window.c:75 msgid "Step backward/forward a single frame" msgstr "Gå bakåt/framåt med en bildruta" #: src/gmpv_shortcuts_window.c:76 msgid "Seek to the beginning of the previous/next chapter" msgstr "Sök fram till början av föregående/nästa kapitel" #: src/gmpv_shortcuts_window.c:79 msgid "Decrease/increase playback speed by 10%" msgstr "Minska/öka uppspelningshastighet med 10%" #: src/gmpv_shortcuts_window.c:80 msgid "Halve/double current playback speed" msgstr "Halvera/dubbla nuvarande uppspelningshastighet" #: src/gmpv_shortcuts_window.c:81 msgid "Reset playback speed to normal" msgstr "Återställ uppspelningshastighet till normal" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "Gå bakåt/framåt i spellistan" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "Ta bort markerat objekt från spellista" #: src/gmpv_shortcuts_window.c:84 msgid "Save playlist" msgstr "Spara spellista" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "Sätt/rensa A-B punkter för repeterad uppspelning" #: src/gmpv_shortcuts_window.c:86 msgid "Toggle infinite looping" msgstr "Växla oändlig återuppspelning" #: src/gmpv_shortcuts_window.c:87 msgid "Pause or unpause" msgstr "Pausa eller fortsätt" #: src/gmpv_shortcuts_window.c:88 msgid "Quit" msgstr "Avsluta" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "Spara nuvarande uppspelningsposition och avsluta" #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "Cykla igenom ljudspår" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "Sänk/höj volymen" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "Slå på eller av ljud" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "Justera ljudfördröjning med +/- 0,1 sekunder" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "Växla synlighet av undertexter" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "Cykla igenom tillgängliga undertexter" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "Justera undertexters fördröjning med +/- 0,1 sekunder" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "Växla överskridning av SSA/ASS undertexters stil" #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "Flytta undertexter up/ned" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "Växla VSFilter aspekt kompatibilitetsläge" #: src/gmpv_shortcuts_window.c:107 msgid "Cycle through video tracks" msgstr "Cykla igenom videospår" #: src/gmpv_shortcuts_window.c:108 msgid "Decrease/increase pan-and-scan range" msgstr "Sänk/höj panorering och scan omfång" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot" msgstr "Ta en skärmdump" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "Ta en skärmdump, utan undertexter" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "Ta en skärmdump, så som fönstret visar det." #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "Ändra storlek på videon till hälften av originalformatet" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "Återställ videon till sin ursprungliga storlek" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "Ändra storlek på videon till det dubbla av dess original storlek" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "Justera kontrast" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "Justera ljusstyrka" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "Justera gamma" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "Justera färgmättnad" #: src/gmpv_shortcuts_window.c:119 msgid "Activate or deactivate deinterlacer" msgstr "Aktivera eller inaktivera deinterlacer" #: src/gmpv_shortcuts_window.c:120 msgid "Cycle aspect ratio override" msgstr "Cykla överskridning av bildförhållande" #: src/gmpv_shortcuts_window.c:123 msgid "User Interface" msgstr "Användargränssnitt" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "Video" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "Ljud" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "Undertext" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "Uppspelning" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "Söker" #: src/gmpv_view.c:711 msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "" "Aktivering eller inaktivering av fönsterdekorationer i klienten kräver en " "omstart innan det träder i kraft." #: src/gmpv_view.c:1280 msgid "Add File to Playlist" msgstr "Lägg till fil i spellista" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "Öppna fil" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "Lägg till plats till spellista" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "Öppna plats" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "Öppna ljudspår..." #: src/gmpv_view.c:1349 msgid "Load Subtitle Track…" msgstr "Öppna undertext spår..." #: src/gmpv_view.c:1374 msgid "Save Playlist" msgstr "Spara spellista" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "Ett GTK gränssnitt för MPV" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "Patrik Nilsson " gnome-mpv-0.13/po/zh_CN.po000066400000000000000000000503531317030365200153270ustar00rootroot00000000000000# Chinese translations for gnome-mpv package # gnome-mpv 软件包的简体中文翻译. # Copyright (C) 2015 THE GNOME-MPV'S COPYRIGHT HOLDER # This file is distributed under the same license as the gnome-mpv package. # sun , 2015. # Mingye Wang , 2015. # gnome-mpv , 2015. #zanata # Mingye Wang , 2016. #zanata # Huang Jiayao , 2017. #zanata # gnome-mpv , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: gnome-mpv 0.6\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2015-11-16 21:24+0800\n" "PO-Revision-Date: 2017-08-02 12:11-0400\n" "Last-Translator: Copied by Zanata \n" "Language-Team: AOSC zh_CN \n" "Language: zh-CN\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=1; plural=0;\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "启用或禁用暗色主题" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 msgid "Enable or disable client-side decorations" msgstr "启用或禁用客户端装饰" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "是否让文件选择对话框记住最近访问的文件夹" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "要传递给 mpv 的选项" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 msgid "Path to mpv configuration file" msgstr "mpv 配置文件的路径" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 msgid "Load or don't load mpv configuration file" msgstr "是否载入 mpv 配置文件" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 msgid "Path to mpv input configuration file" msgstr "mpv 输入配置文件的路径" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 msgid "Load or don't load mpv input configuration file" msgstr "是否载入 mpv 输入配置文件" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 msgid "Width of the window" msgstr "窗口宽度" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 msgid "Height of the window" msgstr "窗口高度" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 msgid "Volume of player" msgstr "播放器音量" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "播放列表宽度" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "是否显示播放列表" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "最近访问的文件夹 URI" #: data/io.github.GnomeMpv.gschema.xml:10 msgid "" "Whether the settings has already been migrated from the previous version" msgstr "是否已从上一个版本迁移设置" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "是否在窗口模式下启用浮动控制" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:82 msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 msgid "Show or not show the controls" msgstr "是否显示控制栏" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "MPV 的 GTK 前端程序" #: data/io.github.GnomeMpv.appdata.xml.in:12 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" "GNOME MPV 是一个简单的 GTK+ mpv 前端,mpv 是一个功能强大的媒体播放器,可用于播放几乎所有的视频和音频格式。尽管该程序不依赖于任何" " GNOME 库,GNOME MPV 是一个基于 GNOME HIG(人机界面准则)设计的程序。GNOME MPV " "还提供禁用客户端装饰(CSD)的选项以为不运行 GNOME 的系统提供更好的兼容性。" #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "特性:" #: data/io.github.GnomeMpv.appdata.xml.in:21 msgid "Drag and drop playlist" msgstr "拖放播放列表" #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "Loading external mpv configuration files" msgstr "正在载入外部 mpv 配置文件" #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "MPRIS2 D-Bus 界面" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "关闭了 CSD 的主窗口" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "打开了播放列表的主窗口" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "" #: src/gmpv_application.c:370 msgid "Playing" msgstr "正在播放" #: src/gmpv_application.c:415 msgid "Show release version" msgstr "显示发布版本号" #: src/gmpv_application.c:423 msgid "Enqueue" msgstr "加入队列" #: src/gmpv_application.c:431 msgid "Create a new window" msgstr "" #: src/gmpv_application.c:439 msgid "Don't connect to an already-running instance" msgstr "不要连接到已经运行中的实例" #: src/gmpv_control_box.c:286 msgid "Pause" msgstr "暂停" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 msgid "Play" msgstr "播放" #: src/gmpv_control_box.c:436 msgid "Stop" msgstr "停止" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "快进" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "快退" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "下一章节" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "上一章节" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 msgid "Toggle Fullscreen" msgstr "切换全屏" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 msgid "Error" msgstr "错误" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "取消(_C)" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "打开(_O)" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 msgid "All Files" msgstr "所有文件" #: src/gmpv_file_chooser.c:143 msgid "Media Files" msgstr "" #: src/gmpv_file_chooser.c:154 msgid "Audio Files" msgstr "" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "" #: src/gmpv_file_chooser.c:170 msgid "Image Files" msgstr "" #: src/gmpv_file_chooser.c:180 msgid "Subtitle Files" msgstr "" #: src/gmpv_menu.c:102 msgid "None" msgstr "无" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 msgid "Unknown" msgstr "未知" #: src/gmpv_menu.c:150 msgid "_Load External…" msgstr "载入外部(_L)…" #: src/gmpv_menu.c:243 msgid "_File" msgstr "文件(_F)" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "打开位置(_L)" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "保存播放列表(_S)" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "退出(_Q)" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "编辑(_E)" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "首选项(_P)" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "视频轨道(_V)" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 msgid "_Audio Track" msgstr "音轨(_A)" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 msgid "S_ubtitle Track" msgstr "字幕轨道(_U)" #: src/gmpv_menu.c:253 msgid "_View" msgstr "视图(_V)" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "切换控制栏(_T)" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 msgid "_Toggle Playlist" msgstr "切换播放列表(_T)" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "全屏(_F)" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "正常尺寸(_N)" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 msgid "_Double Size" msgstr "两倍尺寸(_D)" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 msgid "_Half Size" msgstr "一半尺寸(_H)" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "帮助(_F)" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 msgid "_Keyboard Shortcuts" msgstr "快捷键(_K)" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "关于(_A)" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, fuzzy, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "回放被异常终止。原因:%s。" #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "位置:" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "应用一个或多个 MPV 选项失败。" #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "添加(_A)…" #: src/gmpv_playlist_widget.c:537 msgid "Add _Location…" msgstr "添加位置(_L)" #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "播放列表" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "添加 Lua 脚本" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 msgid "Lua Scripts" msgstr "Lua 脚本" #: src/gmpv_plugins_manager.c:299 #, fuzzy, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "从 '%s' 拷贝文件到 '%s' 失败。原因:%s" #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "未找到 Lua 脚本" #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "移除" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "您确定移除此脚本吗?该操作无法被撤销。" #: src/gmpv_plugins_manager_item.c:184 #, fuzzy, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "删除文件 '%s' 失败。原因:%s" #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "用户界面" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "启用客户端装饰" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "启用暗色主题" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "在窗口模式下启用浮动控制" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "记住最后一次打开位置" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr "MPV 配置" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "加载 MPV 配置文件" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr "MPV 配置文件:" #: src/gmpv_preferences_dialog.c:314 msgid "Keybindings" msgstr "键绑定" #: src/gmpv_preferences_dialog.c:317 msgid "Load MPV input configuration file" msgstr "加载 MPV 输入配置文件" #: src/gmpv_preferences_dialog.c:320 msgid "MPV input configuration file:" msgstr "MPV 输入配置文件:" #: src/gmpv_preferences_dialog.c:323 msgid "Miscellaneous" msgstr "杂项" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "" #: src/gmpv_preferences_dialog.c:335 msgid "Enable media keys support" msgstr "" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "额外的 MPV 选项:" #: src/gmpv_preferences_dialog.c:371 msgid "General" msgstr "通用" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "保存(_S)" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "首选项" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "打开文件" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "打开位置" #: src/gmpv_shortcuts_window.c:58 msgid "Add file to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "显示首选项对话框" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "切换控制栏" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "切换播放列表" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle fullscreen mode" msgstr "切换全屏模式" #: src/gmpv_shortcuts_window.c:64 msgid "Leave fullscreen mode" msgstr "离开全屏模式" #: src/gmpv_shortcuts_window.c:65 msgid "Toggle OSD states between normal and playback time/duration" msgstr "切换 OSD 状态为“普通”或者“播放时间/总时长”" #: src/gmpv_shortcuts_window.c:66 msgid "Show filename on the OSD" msgstr "在 OSD 上显示文件名" #: src/gmpv_shortcuts_window.c:67 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "在 OSD 上显示进度、已播放时间、总时长" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 5 seconds" msgstr "向后/向前跳转 5 秒" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 1 second" msgstr "向后/向前精确跳转 1 秒" #: src/gmpv_shortcuts_window.c:72 msgid "Seek backward/forward 1 minute" msgstr "向后/向前跳转 1 分钟" #: src/gmpv_shortcuts_window.c:73 msgid "Exact seek backward/forward 5 seconds" msgstr "向后/向前精确跳转 5 秒" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to previous/next subtitle" msgstr "查找上一个/下一个字幕" #: src/gmpv_shortcuts_window.c:75 msgid "Step backward/forward a single frame" msgstr "跳转到上一帧/下一帧" #: src/gmpv_shortcuts_window.c:76 msgid "Seek to the beginning of the previous/next chapter" msgstr "跳转到上一章/下一章的开头" #: src/gmpv_shortcuts_window.c:79 msgid "Decrease/increase playback speed by 10%" msgstr "减少/增加 10% 播放速度" #: src/gmpv_shortcuts_window.c:80 msgid "Halve/double current playback speed" msgstr "减半/加倍当前的播放速度" #: src/gmpv_shortcuts_window.c:81 msgid "Reset playback speed to normal" msgstr "重置播放速度为正常速度" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "跳转到当前播放列表中的前一项/后一项" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "移除选定的播放列表项" #: src/gmpv_shortcuts_window.c:84 msgid "Save playlist" msgstr "保存播放列表" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "设置/清除 A-B 循环点" #: src/gmpv_shortcuts_window.c:86 msgid "Toggle infinite looping" msgstr "开启或关闭无限循环" #: src/gmpv_shortcuts_window.c:87 msgid "Pause or unpause" msgstr "暂停/播放" #: src/gmpv_shortcuts_window.c:88 msgid "Quit" msgstr "退出" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "保存当前播放进度并退出" #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "循环播放音轨" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "减少/增大音量" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "静音/取消静音" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "将音频延迟调整为 +/- 0.1 秒" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "切换字幕可见性" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "循环播放当前字幕范围" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "将字幕延迟调整为 +/- 0.1 秒" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "切换 SSA/ASS 字幕样式覆盖" #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "移动到上一行/下一行字幕" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "切换 VSFilter aspect 兼容模式" #: src/gmpv_shortcuts_window.c:107 msgid "Cycle through video tracks" msgstr "循环播放视频轨道" #: src/gmpv_shortcuts_window.c:108 msgid "Decrease/increase pan-and-scan range" msgstr "减小/增加 pan-and-scan 范围" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot" msgstr "截取屏幕截图" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "截取屏幕截图,不包含字幕" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "截取屏幕截图,并在窗口中显示截图" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "调整视频大小为其原始大小的一半" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "调整视频大小为其原始大小" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "调整视频大小为其原始大小的两倍" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "调整对比度" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "调整亮度" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "调整伽玛值" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "调整饱和度" #: src/gmpv_shortcuts_window.c:119 msgid "Activate or deactivate deinterlacer" msgstr "激活/取消激活去隔行扫描器" #: src/gmpv_shortcuts_window.c:120 msgid "Cycle aspect ratio override" msgstr "循环切换宽高比重写" #: src/gmpv_shortcuts_window.c:123 msgid "User Interface" msgstr "用户界面" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "视频" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "音频" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "字幕" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "音频" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "跳转" #: src/gmpv_view.c:711 msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "" #: src/gmpv_view.c:1280 msgid "Add File to Playlist" msgstr "添加文件到播放列表" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "打开文件" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "添加位置到播放列表" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "打开位置" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "" #: src/gmpv_view.c:1349 msgid "Load Subtitle Track…" msgstr "" #: src/gmpv_view.c:1374 msgid "Save Playlist" msgstr "保存播放列表" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "MPV 的 GTK 前端程序" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "" "Mingye Wang , 2015, 2016.\n" "Jeff Bai , 2015, 2016.\n" "Sun , 2015, 2016.\n" "Huang Jiayao , 2017." gnome-mpv-0.13/po/zh_TW.po000066400000000000000000000437541317030365200153700ustar00rootroot00000000000000# Chinese translations for gnome-mpv package # gnome-mpv 套件的正體中文翻譯 # Copyright (C) 2015 THE GNOME-MPV'S COPYRIGHT HOLDER # This file is distributed under the same license as the gnome-mpv package. # sun , 2015. # Mingye Wang , 2015. # gnome-mpv , 2015. #zanata # Mingye Wang , 2016. #zanata # gnome-mpv , 2016. #zanata # gnome-mpv , 2017. #zanata msgid "" msgstr "" "Project-Id-Version: gnome-mpv 0.6\n" "Report-Msgid-Bugs-To: \n" "POT-Creation-Date: 2015-11-16 21:24+0800\n" "PO-Revision-Date: 2017-08-02 12:10-0400\n" "Last-Translator: Copied by Zanata \n" "Language-Team: zh_Hant \n" "Language: zh-TW\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=1; plural=0;\n" "X-Generator: Zanata 3.9.6\n" #: data/org.gnome-mpv.gschema.xml:9 data/io.github.GnomeMpv.gschema.xml:16 msgid "Enable or disable dark theme" msgstr "啟用或禁用暗色主題" #: data/org.gnome-mpv.gschema.xml:15 data/io.github.GnomeMpv.gschema.xml:22 msgid "Enable or disable client-side decorations" msgstr "啟用或禁用客戶端裝飾" #: data/org.gnome-mpv.gschema.xml:21 data/io.github.GnomeMpv.gschema.xml:34 msgid "" "Whether or not to make file chooser dialog remember last folder accessed" msgstr "是否讓檔案選擇對話窗記住最近訪問的資料夾" #: data/org.gnome-mpv.gschema.xml:27 data/io.github.GnomeMpv.gschema.xml:46 msgid "Options to pass to mpv" msgstr "要傳遞給 mpv 的選項" #: data/org.gnome-mpv.gschema.xml:33 data/io.github.GnomeMpv.gschema.xml:52 msgid "Path to mpv configuration file" msgstr "mpv 配置檔的路徑" #: data/org.gnome-mpv.gschema.xml:39 data/io.github.GnomeMpv.gschema.xml:58 msgid "Load or don't load mpv configuration file" msgstr "是否載入 mpv 配置檔" #: data/org.gnome-mpv.gschema.xml:45 data/io.github.GnomeMpv.gschema.xml:64 msgid "Path to mpv input configuration file" msgstr "mpv 輸入配置檔的路徑" #: data/org.gnome-mpv.gschema.xml:51 data/io.github.GnomeMpv.gschema.xml:70 msgid "Load or don't load mpv input configuration file" msgstr "是否載入 mpv 輸入配置檔" #: data/org.gnome-mpv.gschema.xml:61 data/io.github.GnomeMpv.gschema.xml:98 msgid "Width of the window" msgstr "視窗寬度" #: data/org.gnome-mpv.gschema.xml:67 data/io.github.GnomeMpv.gschema.xml:104 msgid "Height of the window" msgstr "視窗高度" #: data/org.gnome-mpv.gschema.xml:73 data/io.github.GnomeMpv.gschema.xml:111 msgid "Volume of player" msgstr "播放器音量" #: data/org.gnome-mpv.gschema.xml:79 data/io.github.GnomeMpv.gschema.xml:117 msgid "Width of the playlist" msgstr "播放列表寬度" #: data/org.gnome-mpv.gschema.xml:85 data/io.github.GnomeMpv.gschema.xml:129 msgid "Show or not show the playlist" msgstr "是否顯示播放列表" #: data/org.gnome-mpv.gschema.xml:91 data/io.github.GnomeMpv.gschema.xml:135 msgid "URI of the last folder accessed" msgstr "最近訪問的資料夾 URI" #: data/io.github.GnomeMpv.gschema.xml:10 msgid "" "Whether the settings has already been migrated from the previous version" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:28 msgid "Whether or not to use floating controls in windowed mode" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:40 msgid "Whether or not to create new windows when there is already an instance" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:76 msgid "Whether or not to enable MPRIS support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:82 msgid "" "Whether or not to enable GNOME-Settings-Daemon-based media keys support" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:88 msgid "Whether or not to prefetch metadata for non-current playlist entries" msgstr "" #: data/io.github.GnomeMpv.gschema.xml:123 msgid "Show or not show the controls" msgstr "" #: data/io.github.GnomeMpv.appdata.xml.in:7 #: data/io.github.GnomeMpv.desktop.in:4 src/gmpv_application.c:330 #: src/gmpv_view.c:955 msgid "GNOME MPV" msgstr "GNOME MPV" #: data/io.github.GnomeMpv.appdata.xml.in:8 #: data/io.github.GnomeMpv.desktop.in:5 msgid "GTK+ frontend for mpv" msgstr "MPV 之 GTK 前端程式" #: data/io.github.GnomeMpv.appdata.xml.in:12 msgid "" "GNOME MPV is a simple GTK+ frontend for mpv, which is a very powerful media " "player capable of playing virtually all video and audio formats. The design " "of GNOME MPV is based on GNOME HIG, though it is not dependent on any GNOME " "libraries. GNOME MPV also offers an option to disable client-side " "decorations (CSD) for better compatibility with non-GNOME systems." msgstr "" "GNOME MPV 是一個簡單的 GTK+ mpv 前端,mpv 是一個功能強大的媒體播放器,可用於播放幾乎所有的視訊和音訊格式。儘管該程式不依賴於任何" " GNOME 庫,GNOME MPV 是一個基於 GNOME HIG(人機介面準則)設計的程式。GNOME MPV " "還提供禁用客戶端裝飾(CSD)的選項以為不執行 GNOME 的系統提供更好的相容性。" #: data/io.github.GnomeMpv.appdata.xml.in:19 msgid "Features:" msgstr "特性:" #: data/io.github.GnomeMpv.appdata.xml.in:21 msgid "Drag and drop playlist" msgstr "拖放播放列表" #: data/io.github.GnomeMpv.appdata.xml.in:22 msgid "Loading external mpv configuration files" msgstr "正在載入外部 mpv 配置檔" #: data/io.github.GnomeMpv.appdata.xml.in:23 msgid "MPRIS2 D-Bus interface" msgstr "MPRIS2 D-Bus 介面" #: data/io.github.GnomeMpv.appdata.xml.in:36 msgid "The main window with CSD disabled" msgstr "關閉了 CSD 的主視窗" #: data/io.github.GnomeMpv.appdata.xml.in:40 msgid "The main window with playlist open" msgstr "打開了播放列表的主視窗" #. Translators: This is an icon name, don't translate! #: data/io.github.GnomeMpv.desktop.in:8 msgid "gnome-mpv" msgstr "" #: data/io.github.GnomeMpv.desktop.in:19 msgid "New Window" msgstr "" #: src/gmpv_application.c:370 msgid "Playing" msgstr "正在播放" #: src/gmpv_application.c:415 msgid "Show release version" msgstr "" #: src/gmpv_application.c:423 msgid "Enqueue" msgstr "" #: src/gmpv_application.c:431 msgid "Create a new window" msgstr "" #: src/gmpv_application.c:439 msgid "Don't connect to an already-running instance" msgstr "" #: src/gmpv_control_box.c:286 msgid "Pause" msgstr "" #: src/gmpv_control_box.c:286 src/gmpv_control_box.c:433 msgid "Play" msgstr "" #: src/gmpv_control_box.c:436 msgid "Stop" msgstr "" #: src/gmpv_control_box.c:439 msgid "Forward" msgstr "" #: src/gmpv_control_box.c:442 msgid "Rewind" msgstr "" #: src/gmpv_control_box.c:445 msgid "Next Chapter" msgstr "" #: src/gmpv_control_box.c:448 msgid "Previous Chapter" msgstr "" #: src/gmpv_control_box.c:451 src/gmpv_header_bar.c:89 msgid "Toggle Fullscreen" msgstr "" #: src/gmpv_controller.c:715 src/gmpv_view.c:1400 msgid "Error" msgstr "錯誤" #: src/gmpv_file_chooser.c:90 src/gmpv_open_location_dialog.c:127 #: src/gmpv_preferences_dialog.c:378 msgid "_Cancel" msgstr "取消(_C)" #: src/gmpv_file_chooser.c:92 src/gmpv_menu.c:244 src/gmpv_menu.c:321 #: src/gmpv_open_location_dialog.c:129 msgid "_Open" msgstr "開啟(_O)" #: src/gmpv_file_chooser.c:135 src/gmpv_plugins_manager.c:148 msgid "All Files" msgstr "" #: src/gmpv_file_chooser.c:143 msgid "Media Files" msgstr "" #: src/gmpv_file_chooser.c:154 msgid "Audio Files" msgstr "" #: src/gmpv_file_chooser.c:162 msgid "Video Files" msgstr "" #: src/gmpv_file_chooser.c:170 msgid "Image Files" msgstr "" #: src/gmpv_file_chooser.c:180 msgid "Subtitle Files" msgstr "" #: src/gmpv_menu.c:102 msgid "None" msgstr "無" #. For simplicity, also dup the default string used when the #. * track has no title. #: src/gmpv_menu.c:117 msgid "Unknown" msgstr "未知" #: src/gmpv_menu.c:150 msgid "_Load External…" msgstr "" #: src/gmpv_menu.c:243 msgid "_File" msgstr "檔案(_F)" #: src/gmpv_menu.c:245 src/gmpv_menu.c:322 msgid "Open _Location" msgstr "開啟位置(_L)" #: src/gmpv_menu.c:246 src/gmpv_menu.c:296 msgid "_Save Playlist" msgstr "儲存播放列表(_S)" #: src/gmpv_menu.c:247 src/gmpv_menu.c:338 msgid "_Quit" msgstr "退出(_Q)" #: src/gmpv_menu.c:248 msgid "_Edit" msgstr "編輯(_E)" #: src/gmpv_menu.c:249 src/gmpv_menu.c:334 msgid "_Preferences" msgstr "偏好設定(_P)" #: src/gmpv_menu.c:250 src/gmpv_menu.c:298 msgid "_Video Track" msgstr "視訊軌道(_V)" #: src/gmpv_menu.c:251 src/gmpv_menu.c:299 msgid "_Audio Track" msgstr "音軌(_A)" #: src/gmpv_menu.c:252 src/gmpv_menu.c:300 msgid "S_ubtitle Track" msgstr "字幕軌道(_U)" #: src/gmpv_menu.c:253 msgid "_View" msgstr "檢視(_V)" #: src/gmpv_menu.c:254 src/gmpv_menu.c:293 msgid "_Toggle Controls" msgstr "" #: src/gmpv_menu.c:255 src/gmpv_menu.c:295 msgid "_Toggle Playlist" msgstr "切換播放列表(_T)" #: src/gmpv_menu.c:256 msgid "_Fullscreen" msgstr "全屏(_F)" #: src/gmpv_menu.c:257 src/gmpv_menu.c:302 msgid "_Normal Size" msgstr "正常尺寸(_N)" #: src/gmpv_menu.c:258 src/gmpv_menu.c:303 msgid "_Double Size" msgstr "兩倍尺寸(_D)" #: src/gmpv_menu.c:259 src/gmpv_menu.c:304 msgid "_Half Size" msgstr "一半尺寸(_H)" #: src/gmpv_menu.c:260 msgid "_Help" msgstr "幫助(_F)" #: src/gmpv_menu.c:261 src/gmpv_menu.c:336 msgid "_Keyboard Shortcuts" msgstr "" #: src/gmpv_menu.c:262 src/gmpv_menu.c:337 msgid "_About" msgstr "關於(_A)" #: src/gmpv_menu.c:332 msgid "_New Window" msgstr "" #: src/gmpv_mpv.c:216 #, fuzzy, c-format msgid "Playback was terminated abnormally. Reason: %s." msgstr "回放被異常終止。原因:%s。" #: src/gmpv_open_location_dialog.c:123 msgid "Location:" msgstr "位置:" #: src/gmpv_player.c:493 msgid "Failed to apply one or more MPV options." msgstr "套用一個或多個 MPV 選項失敗。" #: src/gmpv_playlist_widget.c:533 msgid "_Add…" msgstr "新增(_A)…" #: src/gmpv_playlist_widget.c:537 msgid "Add _Location…" msgstr "" #: src/gmpv_playlist_widget.c:539 msgid "_Shuffle" msgstr "" #: src/gmpv_playlist_widget.c:540 msgid "L_oop" msgstr "" #: src/gmpv_playlist_widget.c:654 msgid "Playlist" msgstr "播放列表" #: src/gmpv_plugins_manager.c:141 src/gmpv_plugins_manager.c:372 msgid "Add Lua Script" msgstr "" #: src/gmpv_plugins_manager.c:153 src/gmpv_preferences_dialog.c:375 msgid "Lua Scripts" msgstr "" #: src/gmpv_plugins_manager.c:299 #, fuzzy, c-format msgid "Failed to copy file from '%s' to '%s'. Reason: %s" msgstr "" #: src/gmpv_plugins_manager.c:348 msgid "No Lua script found" msgstr "" #: src/gmpv_plugins_manager_item.c:69 msgid "Remove" msgstr "" #: src/gmpv_plugins_manager_item.c:163 msgid "" "Are you sure you want to remove this script? This action cannot be undone." msgstr "" #: src/gmpv_plugins_manager_item.c:184 #, fuzzy, c-format msgid "Failed to delete file '%s'. Reason: %s" msgstr "" #: src/gmpv_preferences_dialog.c:290 msgid "User Interface" msgstr "" #: src/gmpv_preferences_dialog.c:293 msgid "Enable client-side decorations" msgstr "啟用客戶端裝飾" #: src/gmpv_preferences_dialog.c:296 msgid "Enable dark theme" msgstr "啟用暗色主題" #: src/gmpv_preferences_dialog.c:299 msgid "Use floating controls in windowed mode" msgstr "" #: src/gmpv_preferences_dialog.c:302 msgid "Remember last file's location" msgstr "記住最後一次開啟位置" #: src/gmpv_preferences_dialog.c:305 msgid "MPV Configuration" msgstr "MPV 配置" #: src/gmpv_preferences_dialog.c:308 msgid "Load MPV configuration file" msgstr "載入 MPV 配置檔" #: src/gmpv_preferences_dialog.c:311 msgid "MPV configuration file:" msgstr "MPV 配置檔:" #: src/gmpv_preferences_dialog.c:314 msgid "Keybindings" msgstr "鍵繫結" #: src/gmpv_preferences_dialog.c:317 msgid "Load MPV input configuration file" msgstr "載入 MPV 輸入配置檔" #: src/gmpv_preferences_dialog.c:320 msgid "MPV input configuration file:" msgstr "MPV 輸入配置檔:" #: src/gmpv_preferences_dialog.c:323 msgid "Miscellaneous" msgstr "雜項" #: src/gmpv_preferences_dialog.c:326 msgid "Always open new window" msgstr "" #: src/gmpv_preferences_dialog.c:329 msgid "Prefetch metadata" msgstr "" #: src/gmpv_preferences_dialog.c:332 msgid "Enable MPRIS support" msgstr "" #: src/gmpv_preferences_dialog.c:335 msgid "Enable media keys support" msgstr "" #: src/gmpv_preferences_dialog.c:338 msgid "Extra MPV options:" msgstr "額外的 MPV 選項:" #: src/gmpv_preferences_dialog.c:371 msgid "General" msgstr "" #: src/gmpv_preferences_dialog.c:380 msgid "_Save" msgstr "儲存(_S)" #: src/gmpv_preferences_dialog.c:397 msgid "Preferences" msgstr "偏好設定" #: src/gmpv_shortcuts_window.c:56 msgid "Open file" msgstr "" #: src/gmpv_shortcuts_window.c:57 msgid "Open location" msgstr "" #: src/gmpv_shortcuts_window.c:58 msgid "Add file to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:59 msgid "Add location to playlist" msgstr "" #: src/gmpv_shortcuts_window.c:60 msgid "Show preferences dialog" msgstr "" #: src/gmpv_shortcuts_window.c:61 msgid "Toggle controls" msgstr "" #: src/gmpv_shortcuts_window.c:62 msgid "Toggle playlist" msgstr "" #: src/gmpv_shortcuts_window.c:63 msgid "Toggle fullscreen mode" msgstr "" #: src/gmpv_shortcuts_window.c:64 msgid "Leave fullscreen mode" msgstr "" #: src/gmpv_shortcuts_window.c:65 msgid "Toggle OSD states between normal and playback time/duration" msgstr "" #: src/gmpv_shortcuts_window.c:66 msgid "Show filename on the OSD" msgstr "" #: src/gmpv_shortcuts_window.c:67 msgid "Show progress, elapsed time, and duration on the OSD" msgstr "" #: src/gmpv_shortcuts_window.c:70 msgid "Seek backward/forward 5 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:71 msgid "Exact seek backward/forward 1 second" msgstr "" #: src/gmpv_shortcuts_window.c:72 msgid "Seek backward/forward 1 minute" msgstr "" #: src/gmpv_shortcuts_window.c:73 msgid "Exact seek backward/forward 5 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:74 msgid "Seek to previous/next subtitle" msgstr "" #: src/gmpv_shortcuts_window.c:75 msgid "Step backward/forward a single frame" msgstr "" #: src/gmpv_shortcuts_window.c:76 msgid "Seek to the beginning of the previous/next chapter" msgstr "" #: src/gmpv_shortcuts_window.c:79 msgid "Decrease/increase playback speed by 10%" msgstr "" #: src/gmpv_shortcuts_window.c:80 msgid "Halve/double current playback speed" msgstr "" #: src/gmpv_shortcuts_window.c:81 msgid "Reset playback speed to normal" msgstr "" #: src/gmpv_shortcuts_window.c:82 msgid "Go backward/forward in the playlist" msgstr "" #: src/gmpv_shortcuts_window.c:83 msgid "Remove selected playlist item" msgstr "" #: src/gmpv_shortcuts_window.c:84 msgid "Save playlist" msgstr "" #: src/gmpv_shortcuts_window.c:85 msgid "Set/clear A-B loop points" msgstr "" #: src/gmpv_shortcuts_window.c:86 msgid "Toggle infinite looping" msgstr "" #: src/gmpv_shortcuts_window.c:87 msgid "Pause or unpause" msgstr "" #: src/gmpv_shortcuts_window.c:88 msgid "Quit" msgstr "" #: src/gmpv_shortcuts_window.c:89 msgid "Save current playback position and quit" msgstr "" #: src/gmpv_shortcuts_window.c:92 msgid "Cycle through audio tracks" msgstr "" #: src/gmpv_shortcuts_window.c:93 src/gmpv_shortcuts_window.c:94 msgid "Decrease/increase volume" msgstr "" #: src/gmpv_shortcuts_window.c:95 msgid "Mute or unmute" msgstr "" #: src/gmpv_shortcuts_window.c:96 msgid "Adjust audio delay by +/- 0.1 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:99 msgid "Toggle subtitle visibility" msgstr "" #: src/gmpv_shortcuts_window.c:100 msgid "Cycle through available subtitles" msgstr "" #: src/gmpv_shortcuts_window.c:101 msgid "Adjust subtitle delay by +/- 0.1 seconds" msgstr "" #: src/gmpv_shortcuts_window.c:102 msgid "Toggle SSA/ASS subtitles style override" msgstr "" #: src/gmpv_shortcuts_window.c:103 msgid "Move subtitles up/down" msgstr "" #: src/gmpv_shortcuts_window.c:104 msgid "Toggle VSFilter aspect compatibility mode" msgstr "" #: src/gmpv_shortcuts_window.c:107 msgid "Cycle through video tracks" msgstr "" #: src/gmpv_shortcuts_window.c:108 msgid "Decrease/increase pan-and-scan range" msgstr "" #: src/gmpv_shortcuts_window.c:109 msgid "Take a screenshot" msgstr "" #: src/gmpv_shortcuts_window.c:110 msgid "Take a screenshot, without subtitles" msgstr "" #: src/gmpv_shortcuts_window.c:111 msgid "Take a screenshot, as the window shows it" msgstr "" #: src/gmpv_shortcuts_window.c:112 msgid "Resize video to half its original size" msgstr "" #: src/gmpv_shortcuts_window.c:113 msgid "Resize video to its original size" msgstr "" #: src/gmpv_shortcuts_window.c:114 msgid "Resize video to double its original size" msgstr "" #: src/gmpv_shortcuts_window.c:115 msgid "Adjust contrast" msgstr "" #: src/gmpv_shortcuts_window.c:116 msgid "Adjust brightness" msgstr "" #: src/gmpv_shortcuts_window.c:117 msgid "Adjust gamma" msgstr "" #: src/gmpv_shortcuts_window.c:118 msgid "Adjust saturation" msgstr "" #: src/gmpv_shortcuts_window.c:119 msgid "Activate or deactivate deinterlacer" msgstr "" #: src/gmpv_shortcuts_window.c:120 msgid "Cycle aspect ratio override" msgstr "" #: src/gmpv_shortcuts_window.c:123 msgid "User Interface" msgstr "" #: src/gmpv_shortcuts_window.c:124 msgid "Video" msgstr "" #: src/gmpv_shortcuts_window.c:125 msgid "Audio" msgstr "" #: src/gmpv_shortcuts_window.c:126 msgid "Subtitle" msgstr "" #: src/gmpv_shortcuts_window.c:127 msgid "Playback" msgstr "" #: src/gmpv_shortcuts_window.c:128 msgid "Seeking" msgstr "" #: src/gmpv_view.c:711 msgid "" "Enabling or disabling client-side decorations requires restarting to take " "effect." msgstr "" #: src/gmpv_view.c:1280 msgid "Add File to Playlist" msgstr "新增檔案到播放列表" #: src/gmpv_view.c:1281 msgid "Open File" msgstr "開啟檔案" #: src/gmpv_view.c:1308 msgid "Add Location to Playlist" msgstr "" #: src/gmpv_view.c:1309 msgid "Open Location" msgstr "開啟位置" #: src/gmpv_view.c:1330 msgid "Load Audio Track…" msgstr "" #: src/gmpv_view.c:1349 msgid "Load Subtitle Track…" msgstr "" #: src/gmpv_view.c:1374 msgid "Save Playlist" msgstr "儲存播放列表" #: src/gmpv_view.c:1439 msgid "A GTK frontend for MPV" msgstr "MPV 的 GTK 前端程式" #: src/gmpv_view.c:1449 msgid "translator-credits" msgstr "" "Mingye Wang\n" "Sun" gnome-mpv-0.13/src/000077500000000000000000000000001317030365200141315ustar00rootroot00000000000000gnome-mpv-0.13/src/Makefile.am000066400000000000000000000061451317030365200161730ustar00rootroot00000000000000AUTOMAKE_OPTIONS = foreign bin_PROGRAMS = gnome-mpv mpris_generated = mpris/gmpv_mpris_gdbus.c mpris/gmpv_mpris_gdbus.h mpris_files = mpris/gmpv_mpris.c mpris/gmpv_mpris.h \ mpris/gmpv_mpris_module.c mpris/gmpv_mpris_module.h \ mpris/gmpv_mpris_base.c mpris/gmpv_mpris_base.h \ mpris/gmpv_mpris_player.c mpris/gmpv_mpris_player.h \ mpris/gmpv_mpris_track_list.c mpris/gmpv_mpris_track_list.h \ $(mpris_generated) $(mpris_generated): $(top_srcdir)/data/gmpv_mpris_gdbus.xml $(AM_V_GEN) \ $(GDBUS_CODEGEN) --c-namespace gmpv_mpris --generate-c-code mpris/gmpv_mpris_gdbus $< && \ $(SED) -i '1i#pragma GCC diagnostic ignored \"-Wconversion\"' mpris/gmpv_mpris_gdbus.c marshal_generated = gmpv_marshal.c gmpv_marshal.h marshal_files = $(marshal_generated) gmpv_marshal.h: $(top_srcdir)/data/gmpv_marshal.lst $(AM_V_GEN) \ $(GLIB_GENMARSHAL) --prefix="g_cclosure_gen_marshal" --header $< > $@ gmpv_marshal.c: $(top_srcdir)/data/gmpv_marshal.lst $(AM_V_GEN) \ $(GLIB_GENMARSHAL) --prefix="g_cclosure_gen_marshal" --body $< > $@ && \ $(SED) -i '1i#pragma GCC diagnostic ignored \"-Wmissing-prototypes\"' $@ authors_generated = gmpv_authors.h authors_files = $(authors_generated) gmpv_authors.h: $(top_srcdir)/AUTHORS $(AM_V_GEN) \ $(AWK) 'BEGIN{print "#ifndef AUTHORS_H\n" \ "#define AUTHORS_H\n\n" \ "#define AUTHORS {\\"} \ /^[^#].+/{print "\"" $$0 "\",\\"} \ END{print "NULL}\n\n#endif"}' $< > $@ media_key_files = media_keys/gmpv_media_keys.c media_keys/gmpv_media_keys.h BUILT_SOURCES = $(mpris_generated) $(marshal_generated) $(authors_generated) gnome_mpv_SOURCES = gmpv_main.c gmpv_def.h \ gmpv_application.c gmpv_application.h \ gmpv_common.c gmpv_common.h \ gmpv_controller.c gmpv_controller.h \ gmpv_controller_actions.c gmpv_controller_actions.h \ gmpv_controller_private.h \ gmpv_controller_input.c gmpv_controller_input.h \ gmpv_control_box.c gmpv_control_box.h \ gmpv_file_chooser.c gmpv_file_chooser.h \ gmpv_header_bar.c gmpv_header_bar.h \ gmpv_main_window.c gmpv_main_window.h \ gmpv_menu.c gmpv_menu.h \ gmpv_metadata_cache.c gmpv_metadata_cache.h \ gmpv_model.c gmpv_model.h \ gmpv_mpv.c gmpv_mpv.h \ gmpv_mpv_private.h \ gmpv_open_location_dialog.c gmpv_open_location_dialog.h \ gmpv_player.c gmpv_player.h \ gmpv_player_options.c gmpv_player_options.h \ gmpv_playlist_widget.c gmpv_playlist_widget.h \ gmpv_plugins_manager.c gmpv_plugins_manager.h \ gmpv_plugins_manager_item.c gmpv_plugins_manager_item.h \ gmpv_preferences_dialog.c gmpv_preferences_dialog.h \ gmpv_seek_bar.c gmpv_seek_bar.h \ gmpv_video_area.c gmpv_video_area.h \ gmpv_view.c gmpv_view.h \ gmpv_mpv_wrapper.c gmpv_mpv_wrapper.h \ $(mpris_files) $(marshal_files) $(media_key_files) \ $(authors_files) if NEW_GTK gnome_mpv_SOURCES += gmpv_shortcuts_window.c gmpv_shortcuts_window.h endif gnome_mpv_CFLAGS = $(DEPS_CFLAGS) \ -DG_SETTINGS_ENABLE_BACKEND \ -DPACKAGE_LOCALEDIR=\""$(localedir)"\" \ -Impris gnome_mpv_LDADD = $(DEPS_LIBS) CLEANFILES = $(mpris_generated) $(marshal_generated) $(authors_generated) EXTRA_DIST = meson.build generate_authors.py gnome-mpv-0.13/src/generate_authors.py000077500000000000000000000005311317030365200200440ustar00rootroot00000000000000#!/usr/bin/env python3 import sys in_file = sys.argv[1] out_file = sys.argv[2] with open(in_file) as i, open(out_file, 'w') as o: o.write('#pragma once\n\n') o.write('#define AUTHORS {\\\n') for author in i: if not author.startswith('#'): o.write('"{}",\\\n'.format(author.rstrip())) o.write('NULL}\n') gnome-mpv-0.13/src/gmpv_application.c000066400000000000000000000266251317030365200176440ustar00rootroot00000000000000/* * Copyright (c) 2016-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include #include #include "gmpv_application.h" #include "gmpv_controller.h" #include "gmpv_mpv_wrapper.h" #include "gmpv_common.h" #include "gmpv_def.h" struct _GmpvApplication { GtkApplication parent; GSList *controllers; gboolean enqueue; gboolean new_window; guint inhibit_cookie; }; struct _GmpvApplicationClass { GtkApplicationClass parent_class; }; static void migrate_config(void); static void initialize_gui(GmpvApplication *app); static void create_dirs(void); static gboolean shutdown_signal_handler(gpointer data); static void new_window_handler( GSimpleAction *simple, GVariant *parameter, gpointer data ); static void activate_handler(GApplication *gapp, gpointer data); static void open_handler( GApplication *gapp, GFile **files, gint n_files, gchar *hint, gpointer data ); static gint options_handler( GApplication *gapp, GVariantDict *options, gpointer data ); static gint command_line_handler( GApplication *gapp, GApplicationCommandLine *cli, gpointer data ); static void startup_handler(GApplication *gapp, gpointer data); static void idle_handler( GObject *object, GParamSpec *pspec, gpointer data ); static void shutdown_handler(GmpvController *controller, gpointer data); static void gmpv_application_class_init(GmpvApplicationClass *klass); static void gmpv_application_init(GmpvApplication *app); G_DEFINE_TYPE(GmpvApplication, gmpv_application, GTK_TYPE_APPLICATION) static void migrate_config() { const gchar *keys[] = { "dark-theme-enable", "csd-enable", "last-folder-enable", "mpv-options", "mpv-config-file", "mpv-config-enable", "mpv-input-config-file", "mpv-input-config-enable", NULL }; GSettings *old_settings = g_settings_new("org.gnome-mpv"); GSettings *new_settings = g_settings_new(CONFIG_ROOT); if(!g_settings_get_boolean(new_settings, "settings-migrated")) { g_settings_set_boolean(new_settings, "settings-migrated", TRUE); for(gint i = 0; keys[i]; i++) { GVariant *buf = g_settings_get_user_value (old_settings, keys[i]); if(buf) { g_settings_set_value (new_settings, keys[i], buf); g_variant_unref(buf); } } } g_object_unref(old_settings); g_object_unref(new_settings); } static void initialize_gui(GmpvApplication *app) { GmpvController *controller; GmpvView *view; GSettings *settings; migrate_config(); controller = gmpv_controller_new(app); view = gmpv_controller_get_view(controller); settings = g_settings_new(CONFIG_ROOT); app->controllers = g_slist_prepend(app->controllers, controller); g_unix_signal_add(SIGHUP, shutdown_signal_handler, app); g_unix_signal_add(SIGINT, shutdown_signal_handler, app); g_unix_signal_add(SIGTERM, shutdown_signal_handler, app); g_signal_connect( controller, "notify::idle", G_CALLBACK(idle_handler), app ); g_signal_connect( controller, "shutdown", G_CALLBACK(shutdown_handler), app ); g_settings_bind( settings, "always-use-floating-controls", gmpv_view_get_main_window(view), "always-use-floating-controls", G_SETTINGS_BIND_GET ); g_settings_bind( settings, "dark-theme-enable", gtk_settings_get_default(), "gtk-application-prefer-dark-theme", G_SETTINGS_BIND_GET ); g_object_unref(settings); } static void create_dirs() { gchar *config_dir = get_config_dir_path(); gchar *scripts_dir = get_scripts_dir_path(); gchar *watch_dir = get_watch_dir_path(); g_mkdir_with_parents(config_dir, 0600); g_mkdir_with_parents(scripts_dir, 0700); g_mkdir_with_parents(watch_dir, 0600); g_free(config_dir); g_free(scripts_dir); g_free(watch_dir); } static gboolean shutdown_signal_handler(gpointer data) { g_info("Shutdown signal received. Shutting down..."); gmpv_application_quit(data); return FALSE; } static void new_window_handler( GSimpleAction *simple, GVariant *parameter, gpointer data ) { initialize_gui(data); } static void activate_handler(GApplication *gapp, gpointer data) { GmpvApplication *app = data; if(!app->controllers) { initialize_gui(app); } } static void open_handler( GApplication *gapp, GFile **files, gint n_files, gchar *hint, gpointer data ) { GmpvApplication *app = data; GSettings *settings = g_settings_new(CONFIG_ROOT); /* Only activate new-window if always-open-new-window is set. It is not * necessary to handle --new-window here since options_handler() would * have activated new-window already if it were set. */ if(g_settings_get_boolean(settings, "always-open-new-window")) { activate_action_string(G_ACTION_MAP(gapp), "new-window"); } g_application_activate(gapp); for(gint i = 0; i < n_files; i++) { GtkApplication *gtkapp = GTK_APPLICATION(gapp); GtkWindow *window = gtk_application_get_active_window(gtkapp); GActionMap *map = G_ACTION_MAP(window); gchar *uri = g_file_get_uri(((GFile **)files)[i]); gboolean append = i != 0 || app->enqueue; GVariant *param = g_variant_new("(sb)", uri, append); GAction *action = g_action_map_lookup_action(map, "open"); g_action_activate(action, param); g_free(uri); } g_object_unref(settings); } static gint options_handler( GApplication *gapp, GVariantDict *options, gpointer data ) { gboolean version = FALSE; g_variant_dict_lookup(options, "version", "b", &version); if(version) { g_printf("GNOME MPV " VERSION "\n"); } else { gboolean no_existing_session = FALSE; g_variant_dict_lookup( options, "no-existing-session", "b", &no_existing_session ); if(no_existing_session) { GApplicationFlags flags = g_application_get_flags(gapp); g_info("Single instance negotiation is disabled"); g_application_set_flags (gapp, flags|G_APPLICATION_NON_UNIQUE); } } return version?0:-1; } static gint command_line_handler( GApplication *gapp, GApplicationCommandLine *cli, gpointer data ) { GmpvApplication *app = data; gint argc = 1; gchar **argv = g_application_command_line_get_arguments(cli, &argc); GVariantDict *options = g_application_command_line_get_options_dict(cli); GSettings *settings = g_settings_new(CONFIG_ROOT); gboolean always_open_new_window = FALSE; const gint n_files = argc-1; GFile *files[n_files]; app->enqueue = FALSE; app->new_window = FALSE; always_open_new_window = g_settings_get_boolean (settings, "always-open-new-window"); g_variant_dict_lookup(options, "enqueue", "b", &app->enqueue); g_variant_dict_lookup(options, "new-window", "b", &app->new_window); for(gint i = 0; i < n_files; i++) { files[i] = g_application_command_line_create_file_for_arg (cli, argv[i+1]); } /* If always-open-new-window is set, only activate the new-window action * if there are no files to be opened. If there are files, * open_handler() will activate the action by itself. This is necessary * because when opening files from file managers, files to be opened may * be sent in the form of DBus message, bypassing this function * entirely. */ if(app->new_window || (n_files == 0 && always_open_new_window)) { activate_action_string(G_ACTION_MAP(gapp), "new-window"); } else if(n_files == 0 || !app->controllers) { g_application_activate(gapp); } if(n_files > 0) { g_application_open (gapp, files, n_files, app->enqueue?"enqueue":""); } for(gint i = 0; i < n_files; i++) { g_object_unref(files[i]); } gdk_notify_startup_complete(); g_object_unref(settings); g_strfreev(argv); return 0; } static void startup_handler(GApplication *gapp, gpointer data) { setlocale(LC_NUMERIC, "C"); g_set_application_name(_("GNOME MPV")); gtk_window_set_default_icon_name(ICON_NAME); bindtextdomain(GETTEXT_PACKAGE, PACKAGE_LOCALEDIR); bind_textdomain_codeset(GETTEXT_PACKAGE, "UTF-8"); textdomain(GETTEXT_PACKAGE); create_dirs(); g_info("Starting GNOME MPV " VERSION); } static void idle_handler( GObject *object, GParamSpec *pspec, gpointer data ) { GmpvApplication *app = data; GmpvController *controller = NULL; gboolean idle = TRUE; for( GSList *iter = app->controllers; iter && idle; iter = g_slist_next(iter) ) { gboolean current = TRUE; g_object_get(iter->data, "idle", ¤t, NULL); idle &= current; controller = iter->data; } if(!idle && app->inhibit_cookie == 0) { GmpvView *view = gmpv_controller_get_view(controller); GmpvMainWindow *window = gmpv_view_get_main_window(view); app->inhibit_cookie = gtk_application_inhibit ( GTK_APPLICATION(app), GTK_WINDOW(window), GTK_APPLICATION_INHIBIT_IDLE, _("Playing") ); } else if(idle && app->inhibit_cookie != 0) { gtk_application_uninhibit (GTK_APPLICATION(app), app->inhibit_cookie); app->inhibit_cookie = 0; } } static void shutdown_handler(GmpvController *controller, gpointer data) { GmpvApplication *app = data; app->controllers = g_slist_remove(app->controllers, controller); g_object_unref(controller); if(!app->controllers) { gmpv_application_quit(data); } } static void gmpv_application_class_init(GmpvApplicationClass *klass) { } static void gmpv_application_init(GmpvApplication *app) { GSimpleAction *new_window = g_simple_action_new("new-window", NULL); app->controllers = NULL; app->enqueue = FALSE; app->new_window = FALSE; app->inhibit_cookie = 0; g_action_map_add_action(G_ACTION_MAP(app), G_ACTION(new_window)); g_application_add_main_option ( G_APPLICATION(app), "version", '\0', G_OPTION_FLAG_NONE, G_OPTION_ARG_NONE, _("Show release version"), NULL ); g_application_add_main_option ( G_APPLICATION(app), "enqueue", '\0', G_OPTION_FLAG_NONE, G_OPTION_ARG_NONE, _("Enqueue"), NULL ); g_application_add_main_option ( G_APPLICATION(app), "new-window", '\0', G_OPTION_FLAG_NONE, G_OPTION_ARG_NONE, _("Create a new window"), NULL ); g_application_add_main_option ( G_APPLICATION(app), "no-existing-session", '\0', G_OPTION_FLAG_NONE, G_OPTION_ARG_NONE, _("Don't connect to an already-running instance"), NULL ); g_signal_connect (new_window, "activate", G_CALLBACK(new_window_handler), app); g_signal_connect (app, "handle-local-options", G_CALLBACK(options_handler), app); g_signal_connect (app, "command-line", G_CALLBACK(command_line_handler), app); g_signal_connect (app, "startup", G_CALLBACK(startup_handler), app); g_signal_connect (app, "activate", G_CALLBACK(activate_handler), app); g_signal_connect (app, "open", G_CALLBACK(open_handler), app); } GmpvApplication *gmpv_application_new(gchar *id, GApplicationFlags flags) { return GMPV_APPLICATION(g_object_new( gmpv_application_get_type(), "application-id", id, "flags", flags, NULL )); } void gmpv_application_quit(GmpvApplication *app) { g_application_quit(G_APPLICATION(app)); } gnome-mpv-0.13/src/gmpv_application.h000066400000000000000000000022051317030365200176350ustar00rootroot00000000000000/* * Copyright (c) 2016-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef APPLICATION_H #define APPLICATION_H #include #include "gmpv_main_window.h" #include "gmpv_mpv.h" G_BEGIN_DECLS #define GMPV_TYPE_APPLICATION (gmpv_application_get_type()) G_DECLARE_FINAL_TYPE(GmpvApplication, gmpv_application, GMPV, APPLICATION, GtkApplication) GmpvApplication *gmpv_application_new(gchar *id, GApplicationFlags flags); void gmpv_application_quit(GmpvApplication *app); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_common.c000066400000000000000000000116251317030365200166230ustar00rootroot00000000000000/* * Copyright (c) 2014-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include #include #include #include "gmpv_common.h" #include "gmpv_def.h" #include "gmpv_mpv.h" #include "gmpv_mpv_wrapper.h" #include "gmpv_main_window.h" #include "gmpv_control_box.h" GmpvPlaylistEntry *gmpv_playlist_entry_new( const gchar *filename, const gchar *title ) { GmpvPlaylistEntry *entry = g_malloc(sizeof(GmpvPlaylistEntry)); entry->filename = g_strdup(filename); entry->title = g_strdup(title); entry->metadata = g_ptr_array_new_with_free_func ((GDestroyNotify)gmpv_metadata_entry_free); return entry; } void gmpv_playlist_entry_free(GmpvPlaylistEntry *entry) { g_free(entry->filename); g_free(entry->title); g_ptr_array_free(entry->metadata, TRUE); g_free(entry); } GmpvMetadataEntry *gmpv_metadata_entry_new(const gchar *key, const gchar *value) { GmpvMetadataEntry *entry = g_malloc(sizeof(GmpvMetadataEntry)); entry->key = g_strdup(key); entry->value = g_strdup(value); return entry; } void gmpv_metadata_entry_free(GmpvMetadataEntry *entry) { g_free(entry->key); g_free(entry->value); g_free(entry); } GmpvTrack *gmpv_track_new(void) { GmpvTrack *entry = g_malloc(sizeof(GmpvTrack)); entry->type = TRACK_TYPE_INVALID; entry->title = NULL; entry->lang = NULL; entry->id = 0; return entry; } void gmpv_track_free(GmpvTrack *entry) { if(entry) { g_free(entry->title); g_free(entry->lang); g_free(entry); } } gchar *get_config_dir_path(void) { return g_build_filename( g_get_user_config_dir(), CONFIG_DIR, NULL ); } gchar *get_scripts_dir_path(void) { return g_build_filename( g_get_user_config_dir(), CONFIG_DIR, "scripts", NULL ); } gchar *get_watch_dir_path(void) { return g_build_filename( g_get_user_config_dir(), CONFIG_DIR, "watch_later", NULL ); } gchar *get_path_from_uri(const gchar *uri) { GFile *file = g_vfs_get_file_for_uri(g_vfs_get_default(), uri); gchar *path = g_file_get_path(file); if(file) { g_object_unref(file); } return path?path:g_strdup(uri); } gchar *get_name_from_path(const gchar *path) { const gchar *scheme = g_uri_parse_scheme(path); gchar *basename = NULL; /* Check whether the given path is likely to be a local path */ if(!scheme && path) { basename = g_path_get_basename(path); } return basename?basename:g_strdup(path); } gboolean extension_matches(const gchar *filename, const gchar **extensions) { const gchar *ext = strrchr(filename, '.'); gboolean result = FALSE; /* Only start checking the extension if there is at * least one character after the dot. */ if(ext && ++ext) { const gchar **iter = extensions; /* Check if the file extension matches one of the * supported subtitle formats. */ while(*iter && g_strcmp0(ext, *(iter++)) != 0); result = !!(*iter); } return result; } void *gslist_to_array(GSList *slist) { void **result = g_malloc(sizeof(void **)*(g_slist_length(slist)+1)); gint i = 0; for(GSList *iter = slist; iter; iter = g_slist_next(iter)) { result[i++] = iter->data; } result[i] = NULL; return result; } gchar *strnjoinv(const gchar *separator, const gchar **str_array, gsize count) { gsize args_size = ((gsize)count+1)*sizeof(gchar *); gchar **args = g_malloc(args_size); gchar *result; memcpy(args, str_array, args_size-sizeof(gchar *)); args[count] = NULL; result = g_strjoinv(separator, args); g_free(args); return result; } void activate_action_string(GActionMap *map, const gchar *str) { GAction *action = NULL; gchar *name = NULL; GVariant *param = NULL; gboolean param_match = FALSE; g_action_parse_detailed_name(str, &name, ¶m, NULL); if(name) { const GVariantType *action_ptype; const GVariantType *given_ptype; action = g_action_map_lookup_action(map, name); action_ptype = g_action_get_parameter_type(action); given_ptype = param?g_variant_get_type(param):NULL; param_match = (action_ptype == given_ptype) || ( given_ptype && g_variant_type_is_subtype_of (action_ptype, given_ptype) ); } if(action && param_match) { g_debug("Activating action %s", str); g_action_activate(action, param); } else { g_warning("Failed to activate action \"%s\"", str); } } gnome-mpv-0.13/src/gmpv_common.h000066400000000000000000000042311317030365200166230ustar00rootroot00000000000000/* * Copyright (c) 2014-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef COMMON_H #define COMMON_H #include #include G_BEGIN_DECLS typedef struct _GmpvPlaylistEntry GmpvPlaylistEntry; typedef struct _GmpvMetadataEntry GmpvMetadataEntry; typedef enum TrackType TrackType; typedef struct GmpvTrack GmpvTrack; enum TrackType { TRACK_TYPE_INVALID, TRACK_TYPE_AUDIO, TRACK_TYPE_VIDEO, TRACK_TYPE_SUBTITLE, TRACK_TYPE_N }; struct _GmpvPlaylistEntry { gchar *filename; gchar *title; gdouble duration; GPtrArray *metadata; }; struct _GmpvMetadataEntry { gchar *key; gchar *value; }; struct GmpvTrack { TrackType type; gint64 id; gchar *title; gchar *lang; }; GmpvPlaylistEntry *gmpv_playlist_entry_new( const gchar *filename, const gchar *title ); void gmpv_playlist_entry_free(GmpvPlaylistEntry *entry); GmpvMetadataEntry *gmpv_metadata_entry_new( const gchar *key, const gchar *value ); void gmpv_metadata_entry_free(GmpvMetadataEntry *entry); GmpvTrack *gmpv_track_new(void); void gmpv_track_free(GmpvTrack *entry); gchar *get_config_dir_path(void); gchar *get_scripts_dir_path(void); gchar *get_watch_dir_path(void); gchar *get_path_from_uri(const gchar *uri); gchar *get_name_from_path(const gchar *path); gboolean extension_matches(const gchar *filename, const gchar **extensions); void *gslist_to_array(GSList *slist); gchar *strnjoinv(const gchar *separator, const gchar **str_array, gsize count); void activate_action_string(GActionMap *map, const gchar *str); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_control_box.c000066400000000000000000000353701317030365200176660ustar00rootroot00000000000000/* * Copyright (c) 2014-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include "gmpv_control_box.h" #include "gmpv_seek_bar.h" enum { PROP_0, PROP_CHAPTERS_ENABLED, PROP_DURATION, PROP_ENABLED, PROP_PAUSE, PROP_SHOW_FULLSCREEN_BUTTON, PROP_TIME_POSITION, PROP_VOLUME, N_PROPERTIES }; struct _GmpvControlBox { GtkBox parent_instance; GtkWidget *play_button; GtkWidget *stop_button; GtkWidget *forward_button; GtkWidget *rewind_button; GtkWidget *next_button; GtkWidget *previous_button; GtkWidget *volume_button; GtkWidget *fullscreen_button; GtkWidget *seek_bar; gboolean chapters_enabled; gdouble duration; gboolean enabled; gboolean pause; gboolean show_fullscreen_button; gdouble time_position; gdouble volume; }; struct _GmpvControlBoxClass { GtkBoxClass parent_class; }; static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ); static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ); static gboolean gtk_to_mpv_volume( GBinding *binding, const GValue *from_value, GValue *to_value, gpointer data ); static gboolean mpv_to_gtk_volume( GBinding *binding, const GValue *from_value, GValue *to_value, gpointer data ); static void seek_handler( GmpvSeekBar *seek_bar, gdouble value, gpointer data ); static void volume_changed_handler( GtkVolumeButton *button, gdouble value, gpointer data ); static void simple_signal_handler(GtkWidget *widget, gpointer data); static void set_enabled(GmpvControlBox *box, gboolean enabled); static void set_chapter_enabled(GmpvControlBox *box, gboolean enabled); static void set_playing_state(GmpvControlBox *box, gboolean playing); static void init_button( GtkWidget *button, const gchar *icon_name, const gchar *tooltip_text ); G_DEFINE_TYPE(GmpvControlBox, gmpv_control_box, GTK_TYPE_BOX) static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ) { GmpvControlBox *self = GMPV_CONTROL_BOX(object); switch(property_id) { case PROP_CHAPTERS_ENABLED: self->chapters_enabled = g_value_get_boolean(value); set_chapter_enabled(self, self->chapters_enabled); break; case PROP_DURATION: self->duration = g_value_get_double(value); gmpv_seek_bar_set_duration (GMPV_SEEK_BAR(self->seek_bar), self->duration); break; case PROP_ENABLED: self->enabled = g_value_get_boolean(value); set_enabled(self, self->enabled); break; case PROP_PAUSE: self->pause = g_value_get_boolean(value); set_playing_state(self, !self->pause); break; case PROP_SHOW_FULLSCREEN_BUTTON: self->show_fullscreen_button = g_value_get_boolean(value); break; case PROP_TIME_POSITION: self->time_position = g_value_get_double(value); gmpv_seek_bar_set_pos (GMPV_SEEK_BAR(self->seek_bar), self->time_position); break; case PROP_VOLUME: self->volume = g_value_get_double(value); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ) { GmpvControlBox *self = GMPV_CONTROL_BOX(object); switch(property_id) { case PROP_CHAPTERS_ENABLED: g_value_set_boolean(value, self->chapters_enabled); break; case PROP_DURATION: g_value_set_double(value, self->duration); break; case PROP_ENABLED: g_value_set_boolean(value, self->enabled); break; case PROP_PAUSE: g_value_set_boolean(value, self->pause); break; case PROP_SHOW_FULLSCREEN_BUTTON: g_value_set_boolean(value, self->show_fullscreen_button); break; case PROP_TIME_POSITION: g_value_set_double(value, self->time_position); break; case PROP_VOLUME: g_value_set_double(value, self->volume); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static gboolean gtk_to_mpv_volume( GBinding *binding, const GValue *from_value, GValue *to_value, gpointer data ) { gdouble from = g_value_get_double(from_value); g_value_set_double(to_value, from*100); return TRUE; } static gboolean mpv_to_gtk_volume( GBinding *binding, const GValue *from_value, GValue *to_value, gpointer data ) { gdouble from = g_value_get_double(from_value); g_value_set_double(to_value, from/100.0); return TRUE; } static void seek_handler( GmpvSeekBar *seek_bar, gdouble value, gpointer data ) { g_signal_emit_by_name(data, "seek", value); } static void volume_changed_handler( GtkVolumeButton *button, gdouble value, gpointer data ) { g_signal_emit_by_name(data, "volume-changed", value*100.0); } static void simple_signal_handler(GtkWidget *widget, gpointer data) { GmpvControlBox *box = data; gint i; const struct { const GtkWidget *widget; const gchar *name; const gchar *button; } signal_map[] = { {box->play_button, "button-clicked", "play"}, {box->stop_button, "button-clicked", "stop"}, {box->forward_button, "button-clicked", "forward"}, {box->rewind_button, "button-clicked", "rewind"}, {box->previous_button, "button-clicked", "previous"}, {box->next_button, "button-clicked", "next"}, {box->fullscreen_button, "button-clicked", "fullscreen"}, {NULL, NULL, NULL} }; for(i = 0; signal_map[i].name && signal_map[i].widget != widget; i++); if(signal_map[i].name) { g_signal_emit_by_name (data, signal_map[i].name, signal_map[i].button); } } static void set_enabled(GmpvControlBox *box, gboolean enabled) { gtk_widget_set_sensitive(box->previous_button, enabled); gtk_widget_set_sensitive(box->rewind_button, enabled); gtk_widget_set_sensitive(box->stop_button, enabled); gtk_widget_set_sensitive(box->play_button, enabled); gtk_widget_set_sensitive(box->forward_button, enabled); gtk_widget_set_sensitive(box->next_button, enabled); } static void set_chapter_enabled(GmpvControlBox *box, gboolean enabled) { if(enabled) { gtk_widget_show_all(box->previous_button); gtk_widget_show_all(box->next_button); } else { gtk_widget_hide(box->previous_button); gtk_widget_hide(box->next_button); } } static void set_playing_state(GmpvControlBox *box, gboolean playing) { GtkWidget *image = gtk_button_get_image(GTK_BUTTON(box->play_button)); const gchar *tooltip = playing?_("Pause"):_("Play"); gtk_image_set_from_icon_name( GTK_IMAGE(image), playing? "media-playback-pause-symbolic": "media-playback-start-symbolic", GTK_ICON_SIZE_BUTTON ); gtk_widget_set_tooltip_text(box->play_button, tooltip); } static void init_button( GtkWidget *button, const gchar *icon_name, const gchar *tooltip_text ) { GtkWidget *icon = gtk_image_new_from_icon_name (icon_name, GTK_ICON_SIZE_BUTTON); gtk_widget_set_tooltip_text(button, tooltip_text); g_object_set(button, "relief", GTK_RELIEF_NONE, NULL); gtk_widget_set_can_focus(button, FALSE); gtk_button_set_image(GTK_BUTTON(button), icon); } static void gmpv_control_box_class_init(GmpvControlBoxClass *klass) { GObjectClass *object_class = G_OBJECT_CLASS(klass); GParamSpec *pspec = NULL; object_class->set_property = set_property; object_class->get_property = get_property; pspec = g_param_spec_boolean ( "chapters-enabled", "Chapters enabled", "Whether the chapter controls are enabled", FALSE, G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_CHAPTERS_ENABLED, pspec); pspec = g_param_spec_double ( "duration", "Duration", "Duration of the file", 0.0, G_MAXDOUBLE, 0.0, G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_DURATION, pspec); pspec = g_param_spec_boolean ( "enabled", "Enabled", "Whether the controls are enabled", TRUE, G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_ENABLED, pspec); pspec = g_param_spec_boolean ( "pause", "Pause", "Whether there is a file playing", TRUE, G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_PAUSE, pspec); pspec = g_param_spec_boolean ( "show-fullscreen-button", "Show fullscreen button", "Whether to show fullscreen button when applicable", FALSE, G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_SHOW_FULLSCREEN_BUTTON, pspec); pspec = g_param_spec_double ( "time-position", "Time position", "The current timr position in the current file", 0.0, G_MAXDOUBLE, 0.0, G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_TIME_POSITION, pspec); pspec = g_param_spec_double ( "volume", "Volume", "The value of the volume button", 0.0, G_MAXDOUBLE, 0.0, G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_VOLUME, pspec); g_signal_new( "button-clicked", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__STRING, G_TYPE_NONE, 1, G_TYPE_STRING ); g_signal_new( "seek", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__DOUBLE, G_TYPE_NONE, 1, G_TYPE_DOUBLE ); g_signal_new( "volume-changed", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__DOUBLE, G_TYPE_NONE, 1, G_TYPE_DOUBLE ); } static void gmpv_control_box_init(GmpvControlBox *box) { box->play_button = gtk_button_new(); box->stop_button = gtk_button_new(); box->forward_button = gtk_button_new(); box->rewind_button = gtk_button_new(); box->next_button = gtk_button_new(); box->previous_button = gtk_button_new(); box->fullscreen_button = gtk_button_new(); box->volume_button = gtk_volume_button_new(); box->seek_bar = gmpv_seek_bar_new(); box->chapters_enabled = FALSE; box->duration = 0.0; box->enabled = TRUE; box->pause = TRUE; box->show_fullscreen_button = FALSE; box->time_position = 0.0; box->volume = 0.0; init_button( box->play_button, "media-playback-start-symbolic", _("Play") ); init_button( box->stop_button, "media-playback-stop-symbolic", _("Stop") ); init_button( box->forward_button, "media-seek-forward-symbolic", _("Forward") ); init_button( box->rewind_button, "media-seek-backward-symbolic", _("Rewind") ); init_button( box->next_button, "media-skip-forward-symbolic", _("Next Chapter") ); init_button( box->previous_button, "media-skip-backward-symbolic", _("Previous Chapter") ); init_button( box->fullscreen_button, "view-fullscreen-symbolic", _("Toggle Fullscreen") ); gtk_style_context_add_class ( gtk_widget_get_style_context(GTK_WIDGET(box)), GTK_STYLE_CLASS_BACKGROUND ); gtk_widget_set_can_focus(box->volume_button, FALSE); gtk_widget_set_can_focus(box->seek_bar, FALSE); gtk_container_add(GTK_CONTAINER(box), box->previous_button); gtk_container_add(GTK_CONTAINER(box), box->rewind_button); gtk_container_add(GTK_CONTAINER(box), box->play_button); gtk_container_add(GTK_CONTAINER(box), box->stop_button); gtk_container_add(GTK_CONTAINER(box), box->forward_button); gtk_container_add(GTK_CONTAINER(box), box->next_button); gtk_box_pack_start(GTK_BOX(box), box->seek_bar, TRUE, TRUE, 0); gtk_container_add(GTK_CONTAINER(box), box->volume_button); gtk_container_add(GTK_CONTAINER(box), box->fullscreen_button); g_object_bind_property_full( box->volume_button, "value", box, "volume", G_BINDING_BIDIRECTIONAL, gtk_to_mpv_volume, mpv_to_gtk_volume, NULL, NULL ); g_signal_connect( box, "button-press-event", G_CALLBACK(gtk_true), NULL ); g_signal_connect( box->play_button, "clicked", G_CALLBACK(simple_signal_handler), box ); g_signal_connect( box->stop_button, "clicked", G_CALLBACK(simple_signal_handler), box ); g_signal_connect( box->seek_bar, "seek", G_CALLBACK(seek_handler), box ); g_signal_connect( box->forward_button, "clicked", G_CALLBACK(simple_signal_handler), box ); g_signal_connect( box->rewind_button, "clicked", G_CALLBACK(simple_signal_handler), box ); g_signal_connect( box->previous_button, "clicked", G_CALLBACK(simple_signal_handler), box ); g_signal_connect( box->next_button, "clicked", G_CALLBACK(simple_signal_handler), box ); g_signal_connect( box->fullscreen_button, "clicked", G_CALLBACK(simple_signal_handler), box ); g_signal_connect( box->volume_button, "value-changed", G_CALLBACK(volume_changed_handler), box ); } GtkWidget *gmpv_control_box_new(void) { return GTK_WIDGET(g_object_new(gmpv_control_box_get_type(), NULL)); } void gmpv_control_box_set_seek_bar_pos(GmpvControlBox *box, gdouble pos) { gmpv_seek_bar_set_pos(GMPV_SEEK_BAR(box->seek_bar), pos); } void gmpv_control_box_set_seek_bar_duration(GmpvControlBox *box, gint duration) { gmpv_seek_bar_set_duration(GMPV_SEEK_BAR(box->seek_bar), duration); } void gmpv_control_box_set_volume(GmpvControlBox *box, gdouble volume) { g_signal_handlers_block_by_func(box, volume_changed_handler, box); gtk_scale_button_set_value (GTK_SCALE_BUTTON(box->volume_button), volume/100.0); g_signal_handlers_unblock_by_func(box, volume_changed_handler, box); } gdouble gmpv_control_box_get_volume(GmpvControlBox *box) { return gtk_scale_button_get_value(GTK_SCALE_BUTTON(box->volume_button)); } gboolean gmpv_control_box_get_volume_popup_visible(GmpvControlBox *box) { GtkScaleButton *volume_button = GTK_SCALE_BUTTON(box->volume_button); return gtk_widget_is_visible(gtk_scale_button_get_popup(volume_button)); } void gmpv_control_box_set_fullscreen_state( GmpvControlBox *box, gboolean fullscreen ) { GtkWidget *image = gtk_button_get_image(GTK_BUTTON(box->fullscreen_button)); gtk_image_set_from_icon_name( GTK_IMAGE(image), fullscreen? "view-restore-symbolic": "view-fullscreen-symbolic", GTK_ICON_SIZE_BUTTON ); gtk_widget_set_visible( box->fullscreen_button, !fullscreen && box->show_fullscreen_button ); } void gmpv_control_box_reset(GmpvControlBox *box) { gmpv_control_box_set_seek_bar_pos(box, 0); gmpv_control_box_set_seek_bar_duration(box, 0); set_playing_state(box, FALSE); set_chapter_enabled(box, FALSE); gmpv_control_box_set_fullscreen_state(box, FALSE); } gnome-mpv-0.13/src/gmpv_control_box.h000066400000000000000000000031341317030365200176640ustar00rootroot00000000000000/* * Copyright (c) 2014-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef CONTROL_BOX_H #define CONTROL_BOX_H #include #include #include G_BEGIN_DECLS #define GMPV_TYPE_CONTROL_BOX (gmpv_control_box_get_type()) G_DECLARE_FINAL_TYPE(GmpvControlBox, gmpv_control_box, GMPV, CONTROL_BOX, GtkBox) GtkWidget *gmpv_control_box_new(void); void gmpv_control_box_set_enabled(GmpvControlBox *box, gboolean enabled); void gmpv_control_box_set_seek_bar_pos(GmpvControlBox *box, gdouble pos); void gmpv_control_box_set_seek_bar_duration(GmpvControlBox *box, gint duration); void gmpv_control_box_set_volume(GmpvControlBox *box, gdouble volume); gdouble gmpv_control_box_get_volume(GmpvControlBox *box); gboolean gmpv_control_box_get_volume_popup_visible(GmpvControlBox *box); void gmpv_control_box_set_fullscreen_state( GmpvControlBox *box, gboolean fullscreen ); void gmpv_control_box_reset(GmpvControlBox *box); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_controller.c000066400000000000000000000572451317030365200175260ustar00rootroot00000000000000/* * Copyright (c) 2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include #include #include #include "gmpv_controller_private.h" #include "gmpv_controller.h" #include "gmpv_controller_actions.h" #include "gmpv_controller_input.h" #include "gmpv_def.h" static void constructed(GObject *object); static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ); static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ); static void dispose(GObject *object); static void mpris_enable_handler( GSettings *settings, gchar *key, gpointer data ); static void media_keys_enable_handler( GSettings *settings, gchar *key, gpointer data ); static void view_ready_handler(GmpvView *view, gpointer data); static void render_handler(GmpvView *view, gpointer data); static void preferences_updated_handler(GmpvView *view, gpointer data); static void audio_track_load_handler( GmpvView *view, const gchar *uri, gpointer data ); static void subtitle_track_load_handler( GmpvView *view, const gchar *uri, gpointer data ); static void file_open_handler( GmpvView *view, const gchar **uri_list, gboolean append, gpointer data ); static void grab_handler(GmpvView *view, gboolean was_grabbed, gpointer data); static void delete_handler(GmpvView *view, gpointer data); static void playlist_item_activated_handler( GmpvView *view, gint pos, gpointer data ); static void playlist_item_deleted_handler( GmpvView *view, gint pos, gpointer data ); static void playlist_reordered_handler( GmpvView *view, gint src, gint dst, gpointer data ); static void connect_signals(GmpvController *controller); static gboolean update_seek_bar(gpointer data); static gboolean is_more_than_one( GBinding *binding, const GValue *from_value, GValue *to_value, gpointer data ); static void idle_active_handler( GObject *object, GParamSpec *pspec, gpointer data); static void playlist_handler( GObject *object, GParamSpec *pspec, gpointer data); static void vid_handler( GObject *object, GParamSpec *pspec, gpointer data); static void model_ready_handler( GObject *object, GParamSpec *pspec, gpointer data ); static void frame_ready_handler(GmpvModel *model, gpointer data); static void metadata_update_handler(GmpvModel *model, gint64 pos, gpointer data); static void window_resize_handler( GmpvModel *model, gint64 width, gint64 height, gpointer data ); static void window_move_handler( GmpvModel *model, gboolean flip_x, gboolean flip_y, GValue *x, GValue *y, gpointer data ); static void message_handler(GmpvMpv *mpv, const gchar *message, gpointer data); static void error_handler(GmpvMpv *mpv, const gchar *message, gpointer data); static void shutdown_handler(GmpvMpv *mpv, gpointer data); static void fullscreen_handler( GObject *object, GParamSpec *pspec, gpointer data ); static void play_button_handler(GtkButton *button, gpointer data); static void stop_button_handler(GtkButton *button, gpointer data); static void forward_button_handler(GtkButton *button, gpointer data); static void rewind_button_handler(GtkButton *button, gpointer data); static void next_button_handler(GtkButton *button, gpointer data); static void previous_button_handler(GtkButton *button, gpointer data); static void fullscreen_button_handler(GtkButton *button, gpointer data); static void seek_handler(GtkButton *button, gdouble value, gpointer data); static void gmpv_controller_class_init(GmpvControllerClass *klass); static void gmpv_controller_init(GmpvController *controller); G_DEFINE_TYPE(GmpvController, gmpv_controller, G_TYPE_OBJECT) static void constructed(GObject *object) { GmpvController *controller; GmpvMainWindow *window; gboolean always_floating; gint64 wid; controller = GMPV_CONTROLLER(object); always_floating = g_settings_get_boolean ( controller->settings, "always-use-floating-controls" ); controller->view = gmpv_view_new(controller->app, always_floating); window = gmpv_view_get_main_window(controller->view); wid = gmpv_video_area_get_xid(gmpv_main_window_get_video_area(window)); controller->model = gmpv_model_new(wid); connect_signals(controller); gmpv_controller_action_register_actions(controller); gmpv_controller_input_connect_signals(controller); g_signal_connect( controller->settings, "changed::mpris-enable", G_CALLBACK(mpris_enable_handler), controller ); g_signal_connect( controller->settings, "changed::media-keys-enable", G_CALLBACK(media_keys_enable_handler), controller ); if(g_settings_get_boolean(controller->settings, "mpris-enable")) { controller->mpris = gmpv_mpris_new(controller); } if(g_settings_get_boolean(controller->settings, "media-keys-enable")) { controller->media_keys = gmpv_media_keys_new(controller); } G_OBJECT_CLASS(gmpv_controller_parent_class)->constructed(object); } static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ) { GmpvController *self = GMPV_CONTROLLER(object); switch(property_id) { case PROP_APP: self->app = g_value_get_pointer(value); break; case PROP_READY: self->ready = g_value_get_boolean(value); break; case PROP_IDLE: self->idle = g_value_get_boolean(value); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ) { GmpvController *self = GMPV_CONTROLLER(object); switch(property_id) { case PROP_APP: g_value_set_pointer(value, self->app); break; case PROP_READY: g_value_set_boolean(value, self->ready); break; case PROP_IDLE: g_value_set_boolean(value, self->idle); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void dispose(GObject *object) { GmpvController *controller = GMPV_CONTROLLER(object); g_clear_object(&controller->settings); g_clear_object(&controller->mpris); g_clear_object(&controller->media_keys); if(controller->update_seekbar_id != 0) { g_source_remove(controller->update_seekbar_id); controller->update_seekbar_id = 0; } if(controller->view) { gmpv_view_make_gl_context_current(controller->view); g_clear_object(&controller->model); g_clear_object(&controller->view); } G_OBJECT_CLASS(gmpv_controller_parent_class)->dispose(object); } static void mpris_enable_handler( GSettings *settings, gchar *key, gpointer data ) { GmpvController *controller = data; if(!controller->mpris && g_settings_get_boolean(settings, key)) { controller->mpris = gmpv_mpris_new(controller); } else if(controller->mpris) { g_clear_object(&controller->mpris); } } static void media_keys_enable_handler( GSettings *settings, gchar *key, gpointer data ) { GmpvController *controller = data; if(!controller->media_keys && g_settings_get_boolean(settings, key)) { controller->media_keys = gmpv_media_keys_new(controller); } else if(controller->media_keys) { g_clear_object(&controller->media_keys); } } static void view_ready_handler(GmpvView *view, gpointer data) { gmpv_model_initialize(GMPV_CONTROLLER(data)->model); } static void render_handler(GmpvView *view, gpointer data) { GmpvController *controller = data; gint scale = 1; gint width = -1; gint height = -1; scale = gmpv_view_get_scale_factor(controller->view); gmpv_view_get_video_area_geometry(controller->view, &width, &height); gmpv_model_render_frame(controller->model, scale*width, scale*height); } static void preferences_updated_handler(GmpvView *view, gpointer data) { gmpv_model_reset(GMPV_CONTROLLER(data)->model); } static void audio_track_load_handler( GmpvView *view, const gchar *uri, gpointer data ) { gmpv_model_load_audio_track(GMPV_CONTROLLER(data)->model, uri); } static void subtitle_track_load_handler( GmpvView *view, const gchar *uri, gpointer data ) { gmpv_model_load_subtitle_track(GMPV_CONTROLLER(data)->model, uri); } static void file_open_handler( GmpvView *view, const gchar **uri_list, gboolean append, gpointer data ) { for(const gchar **iter = uri_list; iter && *iter; iter++) { gmpv_model_load_file( GMPV_CONTROLLER(data)->model, *iter, append || iter != uri_list ); } } static void grab_handler(GmpvView *view, gboolean was_grabbed, gpointer data) { if(!was_grabbed) { gmpv_model_reset_keys(GMPV_CONTROLLER(data)->model); } } static void delete_handler(GmpvView *view, gpointer data) { g_signal_emit_by_name(data, "shutdown"); } static void playlist_item_activated_handler( GmpvView *view, gint pos, gpointer data ) { GmpvController *controller = GMPV_CONTROLLER(data); gboolean idle_active = FALSE; g_object_get(controller->model, "idle-active", &idle_active, NULL); gmpv_model_play(controller->model); if(idle_active) { controller->target_playlist_pos = pos; } else { gmpv_model_set_playlist_position(controller->model, pos); } } static void playlist_item_deleted_handler( GmpvView *view, gint pos, gpointer data ) { gmpv_model_remove_playlist_entry(GMPV_CONTROLLER(data)->model, pos); } static void playlist_reordered_handler( GmpvView *view, gint src, gint dst, gpointer data ) { gmpv_model_move_playlist_entry(GMPV_CONTROLLER(data)->model, src, dst); } static void connect_signals(GmpvController *controller) { g_object_bind_property( controller->model, "core-idle", controller, "idle", G_BINDING_DEFAULT ); g_object_bind_property( controller->model, "pause", controller->view, "pause", G_BINDING_DEFAULT ); g_object_bind_property( controller->model, "media-title", controller->view, "title", G_BINDING_DEFAULT ); g_object_bind_property( controller->model, "volume", controller->view, "volume", G_BINDING_BIDIRECTIONAL ); g_object_bind_property( controller->model, "duration", controller->view, "duration", G_BINDING_DEFAULT ); g_object_bind_property( controller->model, "playlist-pos", controller->view, "playlist-pos", G_BINDING_DEFAULT ); g_object_bind_property( controller->model, "track-list", controller->view, "track-list", G_BINDING_DEFAULT ); g_object_bind_property_full( controller->model, "chapters", controller->view, "chapters-enabled", G_BINDING_DEFAULT, is_more_than_one, NULL, NULL, NULL ); g_signal_connect( controller->model, "notify::ready", G_CALLBACK(model_ready_handler), controller ); g_signal_connect( controller->model, "notify::idle-active", G_CALLBACK(idle_active_handler), controller ); g_signal_connect( controller->model, "notify::playlist", G_CALLBACK(playlist_handler), controller ); g_signal_connect( controller->model, "notify::vid", G_CALLBACK(vid_handler), controller ); g_signal_connect( controller->model, "frame-ready", G_CALLBACK(frame_ready_handler), controller ); g_signal_connect( controller->model, "metadata-update", G_CALLBACK(metadata_update_handler), controller ); g_signal_connect( controller->model, "window-resize", G_CALLBACK(window_resize_handler), controller ); g_signal_connect( controller->model, "window-move", G_CALLBACK(window_move_handler), controller ); g_signal_connect( controller->model, "message", G_CALLBACK(message_handler), controller ); g_signal_connect( controller->model, "error", G_CALLBACK(error_handler), controller ); g_signal_connect( controller->model, "shutdown", G_CALLBACK(shutdown_handler), controller ); g_signal_connect( controller->view, "notify::fullscreen", G_CALLBACK(fullscreen_handler), controller ); g_signal_connect( controller->view, "button-clicked::play", G_CALLBACK(play_button_handler), controller ); g_signal_connect( controller->view, "button-clicked::stop", G_CALLBACK(stop_button_handler), controller ); g_signal_connect( controller->view, "button-clicked::forward", G_CALLBACK(forward_button_handler), controller ); g_signal_connect( controller->view, "button-clicked::rewind", G_CALLBACK(rewind_button_handler), controller ); g_signal_connect( controller->view, "button-clicked::next", G_CALLBACK(next_button_handler), controller ); g_signal_connect( controller->view, "button-clicked::previous", G_CALLBACK(previous_button_handler), controller ); g_signal_connect( controller->view, "button-clicked::fullscreen", G_CALLBACK(fullscreen_button_handler), controller ); g_signal_connect( controller->view, "seek", G_CALLBACK(seek_handler), controller ); g_signal_connect( controller->view, "ready", G_CALLBACK(view_ready_handler), controller ); g_signal_connect( controller->view, "render", G_CALLBACK(render_handler), controller ); g_signal_connect( controller->view, "preferences-updated", G_CALLBACK(preferences_updated_handler), controller ); g_signal_connect( controller->view, "audio-track-load", G_CALLBACK(audio_track_load_handler), controller ); g_signal_connect( controller->view, "subtitle-track-load", G_CALLBACK(subtitle_track_load_handler), controller ); g_signal_connect( controller->view, "file-open", G_CALLBACK(file_open_handler), controller ); g_signal_connect( controller->view, "grab-notify", G_CALLBACK(grab_handler), controller ); g_signal_connect( controller->view, "delete-notify", G_CALLBACK(delete_handler), controller ); g_signal_connect( controller->view, "playlist-item-activated", G_CALLBACK(playlist_item_activated_handler), controller ); g_signal_connect( controller->view, "playlist-item-deleted", G_CALLBACK(playlist_item_deleted_handler), controller ); g_signal_connect( controller->view, "playlist-reordered", G_CALLBACK(playlist_reordered_handler), controller ); controller->update_seekbar_id = g_timeout_add( SEEK_BAR_UPDATE_INTERVAL, (GSourceFunc)update_seek_bar, controller ); } gboolean update_seek_bar(gpointer data) { GmpvController *controller = data; gdouble time_pos = gmpv_model_get_time_position(controller->model); gmpv_view_set_time_position(controller->view, time_pos); return TRUE; } static gboolean is_more_than_one( GBinding *binding, const GValue *from_value, GValue *to_value, gpointer data ) { gint64 from = g_value_get_int64(from_value); g_value_set_boolean(to_value, from > 1); return TRUE; } static void idle_active_handler( GObject *object, GParamSpec *pspec, gpointer data ) { GmpvController *controller = data; gboolean idle_active = TRUE; g_object_get(object, "idle-active", &idle_active, NULL); if(idle_active) { gmpv_view_reset(GMPV_CONTROLLER(data)->view); } else if(controller->target_playlist_pos >= 0) { gmpv_model_set_playlist_position (controller->model, controller->target_playlist_pos); } } static void playlist_handler( GObject *object, GParamSpec *pspec, gpointer data ) { GmpvView *view = GMPV_CONTROLLER(data)->view; GPtrArray *playlist = NULL; gint64 pos = 0; g_object_get( object, "playlist", &playlist, "playlist-pos", &pos, NULL ); gmpv_view_update_playlist(view, playlist); gmpv_view_set_playlist_pos(view, pos); } static void vid_handler( GObject *object, GParamSpec *pspec, gpointer data ) { GmpvController *controller = data; GmpvMainWindow *window = gmpv_view_get_main_window(controller->view); GActionMap *map = G_ACTION_MAP(window); GAction *action = g_action_map_lookup_action(map, "set-video-size"); gchar *vid_str = NULL; gint64 vid = 0; g_object_get(object, "vid", &vid_str, NULL); vid = g_ascii_strtoll(vid_str, NULL, 10); g_simple_action_set_enabled(G_SIMPLE_ACTION(action), vid > 0); g_free(vid_str); } static void model_ready_handler( GObject *object, GParamSpec *pspec, gpointer data ) { GmpvController *controller = data; gboolean ready = FALSE; g_object_get(object, "ready", &ready, NULL); if(ready) { gboolean use_opengl_cb; use_opengl_cb = gmpv_model_get_use_opengl_cb(controller->model); gmpv_view_set_use_opengl_cb(controller->view, use_opengl_cb); if(use_opengl_cb) { gmpv_view_make_gl_context_current(controller->view); gmpv_model_initialize_gl(controller->model); } } controller->ready = ready; g_object_notify(data, "ready"); } static void frame_ready_handler(GmpvModel *model, gpointer data) { gmpv_view_queue_render(GMPV_CONTROLLER(data)->view); } static void metadata_update_handler(GmpvModel *model, gint64 pos, gpointer data) { GmpvView *view = GMPV_CONTROLLER(data)->view; GPtrArray *playlist = NULL; g_object_get(G_OBJECT(model), "playlist", &playlist, NULL); gmpv_view_update_playlist(view, playlist); } static void window_resize_handler( GmpvModel *model, gint64 width, gint64 height, gpointer data ) { GmpvController *controller = data; gmpv_view_resize_video_area(controller->view, (gint)width, (gint)height); } static void window_move_handler( GmpvModel *model, gboolean flip_x, gboolean flip_y, GValue *x, GValue *y, gpointer data ) { gmpv_view_move(GMPV_CONTROLLER(data)->view, flip_x, flip_y, x, y); } static void message_handler(GmpvMpv *mpv, const gchar *message, gpointer data) { const gsize prefix_length = sizeof(ACTION_PREFIX)-1; /* Verify that both the prefix and the scope matches */ if(message && strncmp(message, ACTION_PREFIX, prefix_length) == 0) { const gchar *action = message+prefix_length+1; GmpvController *controller = data; GmpvView *view = controller->view; GActionMap *map = NULL; if(g_str_has_prefix(action, "win.")) { map = G_ACTION_MAP(gmpv_view_get_main_window(view)); } else if(g_str_has_prefix(action, "app.")) { map = G_ACTION_MAP(controller->app); } if(map) { /* Strip scope and activate */ activate_action_string(map, strchr(action, '.')+1); } else { g_warning( "Received action with missing or " "unknown scope %s", action ); } } } static void error_handler(GmpvMpv *mpv, const gchar *message, gpointer data) { gmpv_view_show_message_dialog( GMPV_CONTROLLER(data)->view, GTK_MESSAGE_ERROR, _("Error"), NULL, message ); } static void shutdown_handler(GmpvMpv *mpv, gpointer data) { g_signal_emit_by_name(data, "shutdown"); } static void fullscreen_handler( GObject *object, GParamSpec *pspec, gpointer data ) { GmpvView *view = GMPV_CONTROLLER(data)->view; GmpvMainWindow *window = gmpv_view_get_main_window(view); GActionMap *map = G_ACTION_MAP(window); GAction *toggle_playlist = NULL; GAction *toggle_controls = NULL; gboolean fullscreen = FALSE; toggle_playlist = g_action_map_lookup_action(map, "toggle-playlist"); toggle_controls = g_action_map_lookup_action(map, "toggle-controls"); g_object_get(view, "fullscreen", &fullscreen, NULL); g_simple_action_set_enabled (G_SIMPLE_ACTION(toggle_playlist), !fullscreen); g_simple_action_set_enabled (G_SIMPLE_ACTION(toggle_controls), !fullscreen); } static void play_button_handler(GtkButton *button, gpointer data) { GmpvModel *model = GMPV_CONTROLLER(data)->model; gboolean pause = TRUE; g_object_get(model, "pause", &pause, NULL); if(pause) { gmpv_model_play(model); } else { gmpv_model_pause(model); } } static void stop_button_handler(GtkButton *button, gpointer data) { gmpv_model_stop(GMPV_CONTROLLER(data)->model); } static void forward_button_handler(GtkButton *button, gpointer data) { gmpv_model_forward(GMPV_CONTROLLER(data)->model); } static void rewind_button_handler(GtkButton *button, gpointer data) { gmpv_model_rewind(GMPV_CONTROLLER(data)->model); } static void next_button_handler(GtkButton *button, gpointer data) { gmpv_model_next_chapter(GMPV_CONTROLLER(data)->model); } static void previous_button_handler(GtkButton *button, gpointer data) { gmpv_model_previous_chapter(GMPV_CONTROLLER(data)->model); } static void fullscreen_button_handler(GtkButton *button, gpointer data) { GmpvView *view = GMPV_CONTROLLER(data)->view; gboolean fullscreen = FALSE; g_object_get(view, "fullscreen", &fullscreen, NULL); g_object_set(view, "fullscreen", !fullscreen, NULL); } static void seek_handler(GtkButton *button, gdouble value, gpointer data) { gmpv_model_seek(GMPV_CONTROLLER(data)->model, value); } static void gmpv_controller_class_init(GmpvControllerClass *klass) { GObjectClass *obj_class = G_OBJECT_CLASS(klass); GParamSpec *pspec; obj_class->constructed = constructed; obj_class->set_property = set_property; obj_class->get_property = get_property; obj_class->dispose = dispose; pspec = g_param_spec_pointer ( "app", "App", "The GmpvApplication to use", G_PARAM_CONSTRUCT_ONLY|G_PARAM_READWRITE ); g_object_class_install_property(obj_class, PROP_APP, pspec); pspec = g_param_spec_boolean ( "ready", "Ready", "Whether mpv is ready to receive commands", FALSE, G_PARAM_READWRITE ); g_object_class_install_property(obj_class, PROP_READY, pspec); pspec = g_param_spec_boolean ( "idle", "Idle", "Whether or not the player is idle", TRUE, G_PARAM_READWRITE ); g_object_class_install_property(obj_class, PROP_IDLE, pspec); g_signal_new( "shutdown", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__VOID, G_TYPE_NONE, 0 ); } static void gmpv_controller_init(GmpvController *controller) { controller->app = NULL; controller->model = NULL; controller->view = NULL; controller->ready = FALSE; controller->idle = TRUE; controller->target_playlist_pos = -1; controller->update_seekbar_id = 0; controller->settings = g_settings_new(CONFIG_ROOT); controller->media_keys = NULL; controller->mpris = NULL; } GmpvController *gmpv_controller_new(GmpvApplication *app) { return GMPV_CONTROLLER(g_object_new( gmpv_controller_get_type(), "app", app, NULL )); } void gmpv_controller_quit(GmpvController *controller) { gmpv_view_quit(controller->view); } void gmpv_controller_autofit(GmpvController *controller, gdouble multiplier) { gchar *vid = NULL; gint64 width = -1; gint64 height = -1; g_object_get(G_OBJECT(controller->model), "vid", &vid, NULL); gmpv_model_get_video_geometry(controller->model, &width, &height); if(vid && strncmp(vid, "no", 3) != 0 && width >= 0 && width >= 0) { gint new_width = (gint)(multiplier*(gdouble)width); gint new_height = (gint)(multiplier*(gdouble)height); g_debug("Resizing window to %dx%d", new_width, new_height); gmpv_view_resize_video_area( controller->view, new_width, new_height ); } g_free(vid); } void gmpv_controller_present(GmpvController *controller) { gmpv_view_present(controller->view); } void gmpv_controller_open( GmpvController *controller, const gchar *uri, gboolean append ) { gmpv_model_load_file(controller->model, uri, append); } GmpvView *gmpv_controller_get_view(GmpvController *controller) { return controller->view; } GmpvModel *gmpv_controller_get_model(GmpvController *controller) { return controller->model; } gnome-mpv-0.13/src/gmpv_controller.h000066400000000000000000000027161317030365200175240ustar00rootroot00000000000000/* * Copyright (c) 2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef CONTROLLER_H #define CONTROLLER_H #include #include "gmpv_model.h" #include "gmpv_view.h" G_BEGIN_DECLS #define GMPV_TYPE_CONTROLLER (gmpv_controller_get_type()) G_DECLARE_FINAL_TYPE(GmpvController, gmpv_controller, GMPV, CONTROLLER, GObject) GmpvController *gmpv_controller_new(GmpvApplication *app); void gmpv_controller_quit(GmpvController *controller); void gmpv_controller_autofit(GmpvController *controller, gdouble multiplier); void gmpv_controller_present(GmpvController *controller); void gmpv_controller_open( GmpvController *controller, const gchar *urii, gboolean append ); GmpvView *gmpv_controller_get_view(GmpvController *controller); GmpvModel *gmpv_controller_get_model(GmpvController *controller); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_controller_actions.c000066400000000000000000000313061317030365200212340ustar00rootroot00000000000000/* * Copyright (c) 2015-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include "gmpv_controller_actions.h" #include "gmpv_controller_private.h" #include "gmpv_file_chooser.h" #include "gmpv_common.h" static gboolean track_id_to_state( GBinding *binding, const GValue *from_value, GValue *to_value, gpointer user_data ); static gboolean state_to_track_id( GBinding *binding, const GValue *from_value, GValue *to_value, gpointer user_data ); static gboolean loop_to_state( GBinding *binding, const GValue *from_value, GValue *to_value, gpointer user_data ); static gboolean state_to_loop( GBinding *binding, const GValue *from_value, GValue *to_value, gpointer user_data ); static void bind_properties(GmpvController *controller); static void open_handler( GSimpleAction *action, GVariant *param, gpointer data ); static void show_open_dialog_handler( GSimpleAction *action, GVariant *param, gpointer data ); static void show_open_location_dialog_handler( GSimpleAction *action, GVariant *param, gpointer data ); static void toggle_loop_handler( GSimpleAction *action, GVariant *value, gpointer data ); static void show_shortcuts_dialog_handler( GSimpleAction *action, GVariant *param, gpointer data ); static void toggle_controls_handler( GSimpleAction *action, GVariant *param, gpointer data ); static void toggle_playlist_handler( GSimpleAction *action, GVariant *param, gpointer data ); static void save_playlist_handler( GSimpleAction *action, GVariant *param, gpointer data ); static void shuffle_playlist_handler( GSimpleAction *action, GVariant *param, gpointer data ); static void remove_selected_playlist_item_handler( GSimpleAction *action, GVariant *param, gpointer data ); static void show_preferences_dialog_handler( GSimpleAction *action, GVariant *param, gpointer data ); static void quit_handler( GSimpleAction *action, GVariant *param, gpointer data ); static void set_audio_track_handler( GSimpleAction *action, GVariant *value, gpointer data ); static void set_video_track_handler( GSimpleAction *action, GVariant *value, gpointer data ); static void set_subtitle_track_handler( GSimpleAction *action, GVariant *value, gpointer data ); static void load_track_handler( GSimpleAction *action, GVariant *param, gpointer data ); static void toggle_fullscreen_handler( GSimpleAction *action, GVariant *param, gpointer data ); static void enter_fullscreen_handler( GSimpleAction *action, GVariant *param, gpointer data ); static void leave_fullscreen_handler( GSimpleAction *action, GVariant *param, gpointer data ); static void set_video_size_handler( GSimpleAction *action, GVariant *param, gpointer data ); static void show_about_dialog_handler( GSimpleAction *action, GVariant *param, gpointer data ); static gboolean track_id_to_state( GBinding *binding, const GValue *from_value, GValue *to_value, gpointer user_data ) { const gchar *id = g_value_get_string(from_value); gint64 value = g_strcmp0(id, "no") == 0?0:g_ascii_strtoll(id, NULL, 10); GVariant *to = g_variant_new("x", value); g_value_set_variant(to_value, to); return TRUE; } static gboolean state_to_track_id( GBinding *binding, const GValue *from_value, GValue *to_value, gpointer user_data ) { GVariant *from = g_value_get_variant(from_value); gint64 id = g_variant_get_int64(from); gchar *value = id <= 0? g_strdup("no"): g_strdup_printf("%" G_GINT64_FORMAT, id); g_value_take_string(to_value, value); return TRUE; } static gboolean loop_to_state( GBinding *binding, const GValue *from_value, GValue *to_value, gpointer user_data ) { const gchar *from = g_value_get_string(from_value); GVariant *to = g_variant_new("b", g_strcmp0(from, "no") != 0); g_value_set_variant(to_value, to); return TRUE; } static gboolean state_to_loop( GBinding *binding, const GValue *from_value, GValue *to_value, gpointer user_data ) { GVariant *from = g_value_get_variant(from_value); gboolean to = g_variant_get_boolean(from); g_value_set_static_string(to_value, to?"inf":"no"); return TRUE; } static void bind_properties(GmpvController *controller) { GmpvMainWindow *window = gmpv_view_get_main_window(controller->view); GAction *action = NULL; action = g_action_map_lookup_action (G_ACTION_MAP(window), "set-audio-track"); g_object_bind_property_full( controller->model, "aid", action, "state", G_BINDING_BIDIRECTIONAL, track_id_to_state, state_to_track_id, NULL, NULL ); action = g_action_map_lookup_action (G_ACTION_MAP(window), "set-video-track"); g_object_bind_property_full( controller->model, "vid", action, "state", G_BINDING_BIDIRECTIONAL, track_id_to_state, state_to_track_id, NULL, NULL ); action = g_action_map_lookup_action (G_ACTION_MAP(window), "set-subtitle-track"); g_object_bind_property_full( controller->model, "sid", action, "state", G_BINDING_BIDIRECTIONAL, track_id_to_state, state_to_track_id, NULL, NULL ); action = g_action_map_lookup_action (G_ACTION_MAP(window), "toggle-loop"); g_object_bind_property_full( controller->model, "loop-playlist", action, "state", G_BINDING_BIDIRECTIONAL, loop_to_state, state_to_loop, NULL, NULL ); } static void open_handler( GSimpleAction *action, GVariant *param, gpointer data ) { gchar *uri = NULL; gboolean append = FALSE; g_variant_get(param, "(sb)", &uri, &append); gmpv_controller_open(data, uri, append); g_free(uri); } static void show_open_dialog_handler( GSimpleAction *action, GVariant *param, gpointer data ) { gboolean append = g_variant_get_boolean(param); gmpv_view_show_open_dialog (gmpv_controller_get_view(data), append); } static void show_open_location_dialog_handler( GSimpleAction *action, GVariant *param, gpointer data ) { gboolean append = g_variant_get_boolean(param); gmpv_view_show_open_location_dialog (gmpv_controller_get_view(data), append); } static void toggle_loop_handler( GSimpleAction *action, GVariant *value, gpointer data ) { g_simple_action_set_state(action, value); } static void show_shortcuts_dialog_handler( GSimpleAction *action, GVariant *param, gpointer data ) { gmpv_view_show_shortcuts_dialog(gmpv_controller_get_view(data)); } static void toggle_controls_handler( GSimpleAction *action, GVariant *param, gpointer data ) { GmpvView *view = gmpv_controller_get_view(data); gboolean visible = gmpv_view_get_controls_visible(view); gmpv_view_set_controls_visible(view, !visible); } static void toggle_playlist_handler( GSimpleAction *action, GVariant *param, gpointer data ) { GmpvView *view = gmpv_controller_get_view(data); gboolean visible = gmpv_view_get_playlist_visible(view); gmpv_view_set_playlist_visible(view, !visible); } static void save_playlist_handler( GSimpleAction *action, GVariant *param, gpointer data ) { gmpv_view_show_save_playlist_dialog(gmpv_controller_get_view(data)); } static void shuffle_playlist_handler( GSimpleAction *action, GVariant *param, gpointer data ) { gmpv_model_shuffle_playlist(gmpv_controller_get_model(data)); } static void remove_selected_playlist_item_handler( GSimpleAction *action, GVariant *param, gpointer data ) { GmpvView *view = gmpv_controller_get_view(data); GmpvMainWindow *wnd = gmpv_view_get_main_window(view); if(gmpv_main_window_get_playlist_visible(wnd)) { GmpvPlaylistWidget *playlist; playlist = gmpv_main_window_get_playlist(wnd); gmpv_playlist_widget_remove_selected(playlist); } } static void show_preferences_dialog_handler( GSimpleAction *action, GVariant *param, gpointer data ) { gmpv_view_show_preferences_dialog(gmpv_controller_get_view(data)); } static void quit_handler( GSimpleAction *action, GVariant *param, gpointer data ) { gmpv_controller_quit(data); } static void set_audio_track_handler( GSimpleAction *action, GVariant *value, gpointer data ) { g_simple_action_set_state(action, value); } static void set_video_track_handler( GSimpleAction *action, GVariant *value, gpointer data ) { g_simple_action_set_state(action, value); } static void set_subtitle_track_handler( GSimpleAction *action, GVariant *value, gpointer data ) { g_simple_action_set_state(action, value); } static void load_track_handler( GSimpleAction *action, GVariant *param, gpointer data ) { GmpvView *view = gmpv_controller_get_view(data); gchar *cmd_name = NULL; g_variant_get(param, "s", &cmd_name); if(g_strcmp0(cmd_name, "audio-add") == 0) { gmpv_view_show_open_audio_track_dialog(view); } else if(g_strcmp0(cmd_name, "sub-add") == 0) { gmpv_view_show_open_subtitle_track_dialog(view); } else { g_assert_not_reached(); } g_free(cmd_name); } static void toggle_fullscreen_handler( GSimpleAction *action, GVariant *param, gpointer data ) { GmpvView *view = gmpv_controller_get_view(data); gboolean fullscreen = FALSE; g_object_get(view, "fullscreen", &fullscreen, NULL); gmpv_view_set_fullscreen(view, !fullscreen); } static void enter_fullscreen_handler( GSimpleAction *action, GVariant *param, gpointer data ) { gmpv_view_set_fullscreen(gmpv_controller_get_view(data), TRUE); } static void leave_fullscreen_handler( GSimpleAction *action, GVariant *param, gpointer data ) { gmpv_view_set_fullscreen(gmpv_controller_get_view(data), FALSE); } static void set_video_size_handler( GSimpleAction *action, GVariant *param, gpointer data ) { gdouble value = g_variant_get_double(param); gmpv_controller_autofit(data, value); } static void show_about_dialog_handler( GSimpleAction *action, GVariant *param, gpointer data ) { gmpv_view_show_about_dialog(gmpv_controller_get_view(data)); } void gmpv_controller_action_register_actions(GmpvController *controller) { const GActionEntry entries[] = { {.name = "open", .activate = open_handler, .parameter_type = "(sb)"}, {.name = "show-open-dialog", .activate = show_open_dialog_handler, .parameter_type = "b"}, {.name = "quit", .activate = quit_handler}, {.name = "show-about-dialog", .activate = show_about_dialog_handler}, {.name = "show-preferences-dialog", .activate = show_preferences_dialog_handler}, {.name = "show-open-location-dialog", .activate = show_open_location_dialog_handler, .parameter_type = "b"}, {.name = "toggle-loop", .state = "false", .change_state = toggle_loop_handler}, {.name = "show-shortcuts-dialog", .activate = show_shortcuts_dialog_handler}, {.name = "toggle-controls", .activate = toggle_controls_handler}, {.name = "toggle-playlist", .activate = toggle_playlist_handler}, {.name = "save-playlist", .activate = save_playlist_handler}, {.name = "shuffle-playlist", .activate = shuffle_playlist_handler}, {.name = "remove-selected-playlist-item", .activate = remove_selected_playlist_item_handler}, {.name = "set-audio-track", .change_state = set_audio_track_handler, .state = "@x 0", .parameter_type = "x"}, {.name = "set-video-track", .change_state = set_video_track_handler, .state = "@x 0", .parameter_type = "x"}, {.name = "set-subtitle-track", .change_state = set_subtitle_track_handler, .state = "@x 0", .parameter_type = "x"}, {.name = "load-track", .activate = load_track_handler, .parameter_type = "s"}, {.name = "toggle-fullscreen", .activate = toggle_fullscreen_handler}, {.name = "enter-fullscreen", .activate = enter_fullscreen_handler}, {.name = "leave-fullscreen", .activate = leave_fullscreen_handler}, {.name = "set-video-size", .activate = set_video_size_handler, .parameter_type = "d"} }; GmpvMainWindow *window = gmpv_view_get_main_window(controller->view); g_action_map_add_action_entries( G_ACTION_MAP(window), entries, G_N_ELEMENTS(entries), controller ); bind_properties(controller); } gnome-mpv-0.13/src/gmpv_controller_actions.h000066400000000000000000000016551317030365200212450ustar00rootroot00000000000000/* * Copyright (c) 2015-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef CONTROLLER_ACTIONS_H #define CONTROLLER_ACTIONS_H #include #include "gmpv_controller.h" G_BEGIN_DECLS void gmpv_controller_action_register_actions(GmpvController *controller); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_controller_input.c000066400000000000000000000146701317030365200207400ustar00rootroot00000000000000/* * Copyright (c) 2016-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include #include #include "gmpv_controller_private.h" #include "gmpv_controller.h" #include "gmpv_controller_input.h" #include "gmpv_mpv.h" #include "gmpv_mpv_wrapper.h" #include "gmpv_main_window.h" #include "gmpv_video_area.h" #include "gmpv_def.h" static gchar *get_full_keystr(guint keyval, guint state); static gboolean key_press_handler( GtkWidget *widget, GdkEvent *event, gpointer data ); static gboolean key_release_handler( GtkWidget *widget, GdkEvent *event, gpointer data ); static gboolean mouse_button_handler( GtkWidget *widget, GdkEvent *event, gpointer data ); static gboolean mouse_move_handler( GtkWidget *widget, GdkEvent *event, gpointer data ); static gboolean scroll_handler( GtkWidget *widget, GdkEvent *event, gpointer data ); static gchar *get_full_keystr(guint keyval, guint state) { /* strlen("Ctrl+Alt+Shift+Meta+")+1 == 21 */ const gsize max_modstr_len = 21; gchar modstr[max_modstr_len]; gboolean found = FALSE; const gchar *keystr = gdk_keyval_name(keyval); const gchar *keystrmap[] = KEYSTRING_MAP; modstr[0] = '\0'; if((state&GDK_SHIFT_MASK) != 0) { g_strlcat(modstr, "Shift+", max_modstr_len); } if((state&GDK_CONTROL_MASK) != 0) { g_strlcat(modstr, "Ctrl+", max_modstr_len); } if((state&GDK_MOD1_MASK) != 0) { g_strlcat(modstr, "Alt+", max_modstr_len); } /* Super is Meta in mpv */ if((state&GDK_SUPER_MASK) != 0) { g_strlcat(modstr, "Meta+", max_modstr_len); } /* Translate GDK key name to mpv key name */ for(gint i = 0; !found && keystrmap[i]; i += 2) { gint rc = g_ascii_strncasecmp( keystr, keystrmap[i+1], KEYSTRING_MAX_LEN ); if(rc == 0) { keystr = keystrmap[i]; found = TRUE; } } return (strlen(keystr) > 0)?g_strconcat(modstr, keystr, NULL):NULL; } static gboolean key_press_handler( GtkWidget *widget, GdkEvent *event, gpointer data ) { GmpvController *controller = data; guint keyval = ((GdkEventKey*)event)->keyval; guint state = ((GdkEventKey*)event)->state; gchar *keystr = get_full_keystr(keyval, state); if(keystr) { gmpv_model_key_down(controller->model, keystr); g_free(keystr); } return FALSE; } static gboolean key_release_handler( GtkWidget *widget, GdkEvent *event, gpointer data ) { GmpvController *controller = data; guint keyval = ((GdkEventKey*)event)->keyval; guint state = ((GdkEventKey*)event)->state; gchar *keystr = get_full_keystr(keyval, state); if(keystr) { gmpv_model_key_up(controller->model, keystr); g_free(keystr); } return FALSE; } static gboolean mouse_button_handler( GtkWidget *widget, GdkEvent *event, gpointer data ) { GdkEventButton *btn_event = (GdkEventButton *)event; if(btn_event->type == GDK_BUTTON_PRESS || btn_event->type == GDK_BUTTON_RELEASE || btn_event->type == GDK_SCROLL) { GmpvController *controller = data; gchar *btn_str = g_strdup_printf ("MOUSE_BTN%u", btn_event->button-1); void (*func)(GmpvModel *, const gchar *) = (btn_event->type == GDK_SCROLL)? gmpv_model_key_press: (btn_event->type == GDK_BUTTON_PRESS)? gmpv_model_key_down:gmpv_model_key_up; func(controller->model, btn_str); g_free(btn_str); } return TRUE; } static gboolean mouse_move_handler( GtkWidget *widget, GdkEvent *event, gpointer data ) { GmpvController *controller = data; GdkEventMotion *motion_event = (GdkEventMotion *)event; if(controller->model) { gmpv_model_mouse( controller->model, (gint)motion_event->x, (gint)motion_event->y ); } return FALSE; } static gboolean scroll_handler( GtkWidget *widget, GdkEvent *event, gpointer data ) { GdkEventScroll *scroll_event = (GdkEventScroll *)event; guint button = 0; gint count = 0; /* Only one axis will be used at a time to prevent accidental activation * of commands bound to buttons associated with the other axis. */ if(ABS(scroll_event->delta_x) > ABS(scroll_event->delta_y)) { count = (gint)ABS(scroll_event->delta_x); if(scroll_event->delta_x <= -1) { button = 6; } else if(scroll_event->delta_x >= 1) { button = 7; } } else { count = (gint)ABS(scroll_event->delta_y); if(scroll_event->delta_y <= -1) { button = 4; } else if(scroll_event->delta_y >= 1) { button = 5; } } if(button > 0) { GdkEventButton btn_event; btn_event.type = scroll_event->type; btn_event.window = scroll_event->window; btn_event.send_event = scroll_event->send_event; btn_event.time = scroll_event->time; btn_event.x = scroll_event->x; btn_event.y = scroll_event->y; btn_event.axes = NULL; btn_event.state = scroll_event->state; btn_event.button = button; btn_event.device = scroll_event->device; btn_event.x_root = scroll_event->x_root; btn_event.y_root = scroll_event->y_root; for(gint i = 0; i < count; i++) { /* Not used */ gboolean rc; g_signal_emit_by_name (widget, "button-press-event", &btn_event, &rc); } } return TRUE; } void gmpv_controller_input_connect_signals(GmpvController *controller) { g_signal_connect( controller->view, "key-press-event", G_CALLBACK(key_press_handler), controller ); g_signal_connect( controller->view, "key-release-event", G_CALLBACK(key_release_handler), controller ); g_signal_connect( controller->view, "button-press-event", G_CALLBACK(mouse_button_handler), controller ); g_signal_connect( controller->view, "button-release-event", G_CALLBACK(mouse_button_handler), controller ); g_signal_connect( controller->view, "motion-notify-event", G_CALLBACK(mouse_move_handler), controller ); g_signal_connect( controller->view, "scroll-event", G_CALLBACK(scroll_handler), controller ); } gnome-mpv-0.13/src/gmpv_controller_input.h000066400000000000000000000016551317030365200207440ustar00rootroot00000000000000/* * Copyright (c) 2016-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef CONTROLLER_INPUT_H #define CONTROLLER_INPUT_H #include #include "gmpv_controller_input.h" G_BEGIN_DECLS void gmpv_controller_input_connect_signals(GmpvController *controller); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_controller_private.h000066400000000000000000000024541317030365200212550ustar00rootroot00000000000000/* * Copyright (c) 2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef CONTROLLER_PRIVATE_H #define CONTROLLER_PRIVATE_H #include "gmpv_model.h" #include "gmpv_view.h" #include "mpris/gmpv_mpris.h" #include "media_keys/gmpv_media_keys.h" G_BEGIN_DECLS enum { PROP_0, PROP_APP, PROP_READY, PROP_IDLE, N_PROPERTIES }; struct _GmpvController { GObject parent; GmpvApplication *app; GmpvModel *model; GmpvView *view; gboolean ready; gboolean idle; gint64 target_playlist_pos; guint update_seekbar_id; GSettings *settings; GmpvMediaKeys *media_keys; GmpvMpris *mpris; }; struct _GmpvControllerClass { GObjectClass parent_class; }; G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_def.h000066400000000000000000000163651317030365200161040ustar00rootroot00000000000000/* * Copyright (c) 2014-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef DEF_H #define DEF_H #define APP_ID "io.github.GnomeMpv" #define ICON_NAME "gnome-mpv" #define CONFIG_DIR "gnome-mpv" #define CONFIG_ROOT APP_ID #define CONFIG_WIN_STATE APP_ID".window-state" #define ACTION_PREFIX "gmpv-action" #define DEFAULT_LOG_LEVEL MPV_LOG_LEVEL_ERROR #define MPRIS_TRACK_LIST_BEFORE 10 #define MPRIS_TRACK_LIST_AFTER 10 #define MPRIS_TRACK_ID_NO_TRACK "/org/mpris/MediaPlayer2/TrackList/NoTrack" #define MPRIS_TRACK_ID_PREFIX "/io/github/GnomeMpv/Track/" #define MPRIS_BUS_NAME "org.mpris.MediaPlayer2.GnomeMpv" #define MPRIS_OBJ_ROOT_PATH "/org/mpris/MediaPlayer2" #define PLAYLIST_DEFAULT_WIDTH 200 #define PLAYLIST_MIN_WIDTH 20 #define CSD_WIDTH_OFFSET 52 #define CSD_HEIGHT_OFFSET 99 #define WAYLAND_NOCSD_HEIGHT_OFFSET 60 #define MAIN_WINDOW_DEFAULT_WIDTH 625 #define MAIN_WINDOW_DEFAULT_HEIGHT 400 #define SEEK_BAR_UPDATE_INTERVAL 250 #define FS_CONTROL_HIDE_DELAY 1 #define KEYSTRING_MAX_LEN 16 #define SUBTITLE_EXTS { "utf",\ "utf8",\ "utf-8",\ "idx",\ "sub",\ "srt",\ "smi",\ "rt",\ "txt",\ "ssa",\ "aqt",\ "jss",\ "js",\ "ass",\ "mks",\ "vtt",\ "sup",\ NULL } #define PLAYLIST_EXTS { "m3u",\ "m3u8",\ "ini",\ "pls",\ "txt",\ NULL } #define DND_TARGETS { {.target = "PLAYLIST_PATH",\ .flags = GTK_TARGET_SAME_APP,\ .info = 0},\ {.target = "text/uri-list",\ .flags = 0,\ .info = 0},\ {.target = "text/plain",\ .flags = 0,\ .info = 0},\ {.target = "STRING",\ .flags = 0,\ .info = 0} } #define DEFAULT_KEYBINDS \ { "Ctrl+o script-message gmpv-action win.show-open-dialog(false)",\ "Ctrl+l script-message gmpv-action win.show-open-location-dialog(false)",\ "Ctrl+Shift+o script-message gmpv-action win.show-open-dialog(true)",\ "Ctrl+Shift+l script-message gmpv-action win.show-open-location-dialog(true)",\ "Ctrl+Shift+s script-message gmpv-action win.save-playlist",\ "Ctrl+q script-message gmpv-action win.quit",\ "Ctrl+? script-message gmpv-action win.show-shortcuts-dialog",\ "Ctrl+p script-message gmpv-action win.show-preferences-dialog",\ "Ctrl+h script-message gmpv-action win.toggle-controls",\ "F9 script-message gmpv-action win.toggle-playlist",\ "F11 script-message gmpv-action win.toggle-fullscreen",\ "f script-message gmpv-action win.toggle-fullscreen",\ "ESC script-message gmpv-action win.leave-fullscreen",\ "v osd-msg cycle sub-visibility",\ "s osd-msg screenshot",\ "S osd-msg screenshot video",\ "j osd-msg cycle sub",\ "J osd-msg cycle sub down",\ "@ osd-msg cycle chapter",\ "! osd-msg cycle chapter down",\ "DEL script-message gmpv-action win.remove-selected-playlist-item",\ "U stop",\ "RIGHT no-osd seek 10",\ "LEFT no-osd seek -10",\ "UP no-osd seek 60",\ "DOWN no-osd seek -60",\ "Alt+0 script-message gmpv-action win.set-video-size(0.5)",\ "Alt+1 script-message gmpv-action win.set-video-size(1.0)",\ "Alt+2 script-message gmpv-action win.set-video-size(2.0)",\ "MOUSE_BTN0_DBL script-message gmpv-action win.toggle-fullscreen",\ "MOUSE_BTN3 add volume 2",\ "MOUSE_BTN4 add volume -2",\ "MOUSE_BTN5 no-osd seek -10",\ "MOUSE_BTN6 no-osd seek 10",\ NULL } #define KEYSTRING_MAP { "<", "less",\ ">", "greater",\ "PGUP", "Page_Up",\ "PGDWN", "Page_Down",\ "BS", "BackSpace",\ ".", "period",\ ",", "comma",\ "`", "grave",\ "~", "asciitilde",\ "!", "exclam",\ "@", "at",\ "SHARP", "numbersign",\ "$", "dollar",\ "%", "percent",\ "^", "caret",\ "&", "ampersand",\ "*", "asterisk",\ "-", "minus",\ "_", "underscore",\ "=", "equal",\ "+", "plus",\ ";", "semicolon",\ ":", "colon",\ "'", "apostrophe",\ "\"", "quotedbl",\ "/", "slash",\ "\\", "backslash",\ "(", "parenleft",\ ")", "parenright",\ "[", "bracketleft",\ "]", "bracketright",\ "?", "question",\ "RIGHT", "Right",\ "LEFT", "Left",\ "UP", "Up",\ "DOWN", "Down",\ "ESC", "Escape",\ "DEL", "Delete",\ "ENTER", "Return",\ "INS", "Insert",\ "", "Control_L",\ "", "Control_R",\ "", "Alt_L",\ "", "Alt_R",\ "", "Meta_L",\ "", "Meta_R",\ "", "Shift_L",\ "", "Shift_R",\ NULL } #define SUPPORTED_PROTOCOLS { "cdda",\ "rtmp",\ "rtsp",\ "http",\ "https",\ "mms",\ "mmst",\ "mmsh",\ "mmshttp",\ "rtp",\ "httpproxy",\ "hls",\ "rtmpe",\ "rtmps",\ "rtmpt",\ "rtmpte",\ "rtmpts",\ "srtp",\ "lavf",\ "ffmpeg",\ "udp",\ "ftp",\ "tcp",\ "tls",\ "unix",\ "sftp",\ "md5",\ "concat",\ "avdevice",\ "av",\ "dvb",\ "tv",\ "pvr",\ "smb",\ "file",\ "dvdread",\ "dvd",\ "dvdnav",\ "bd",\ "br",\ "bluray",\ "bdnav",\ "brnav",\ "bluraynav",\ "memory",\ "null",\ "mf",\ "edl",\ "rar",\ NULL } #define SUPPORTED_MIME_TYPES { "application/ogg",\ "application/x-ogg",\ "application/sdp",\ "application/smil",\ "application/x-smil",\ "application/streamingmedia",\ "application/x-streamingmedia",\ "application/vnd.rn-realmedia",\ "application/vnd.rn-realmedia-vbr",\ "audio/aac",\ "audio/x-aac",\ "audio/m4a",\ "audio/x-m4a",\ "audio/mp1",\ "audio/x-mp1",\ "audio/mp2",\ "audio/x-mp2",\ "audio/mp3",\ "audio/x-mp3",\ "audio/mpeg",\ "audio/x-mpeg",\ "audio/mpegurl",\ "audio/x-mpegurl",\ "audio/mpg",\ "audio/x-mpg",\ "audio/rn-mpeg",\ "audio/ogg",\ "audio/scpls",\ "audio/x-scpls",\ "audio/vnd.rn-realaudio",\ "audio/wav",\ "audio/x-pn-windows-pcm",\ "audio/x-realaudio",\ "audio/x-pn-realaudio",\ "audio/x-ms-wma",\ "audio/x-pls",\ "audio/x-wav",\ "video/mpeg",\ "video/x-mpeg",\ "video/x-mpeg2",\ "video/mp4",\ "video/msvideo",\ "video/x-msvideo",\ "video/ogg",\ "video/quicktime",\ "video/vnd.rn-realvideo",\ "video/x-ms-afs",\ "video/x-ms-asf",\ "video/x-ms-wmv",\ "video/x-ms-wmx",\ "video/x-ms-wvxvideo",\ "video/x-avi",\ "video/x-fli",\ "video/x-flv",\ "video/x-theora",\ "video/x-matroska",\ "video/webm",\ "audio/x-flac",\ "audio/x-vorbis+ogg",\ "video/x-ogm+ogg",\ "audio/x-shorten",\ "audio/x-ape",\ "audio/x-wavpack",\ "audio/x-tta",\ "audio/AMR",\ "audio/ac3",\ "video/mp2t",\ "audio/flac",\ NULL } #endif gnome-mpv-0.13/src/gmpv_file_chooser.c000066400000000000000000000123501317030365200177700ustar00rootroot00000000000000/* * Copyright (c) 2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include "gmpv_file_chooser.h" #include "gmpv_def.h" static void load_last_folder(GtkFileChooser *chooser); static void save_last_folder(GtkFileChooser *chooser); static void response_handler(GtkDialog *dialog, gint response_id, gpointer data); static void load_last_folder(GtkFileChooser *chooser) { GSettings *win_config = g_settings_new(CONFIG_WIN_STATE); gchar *uri = g_settings_get_string(win_config, "last-folder-uri"); if(uri && *uri) { gtk_file_chooser_set_current_folder_uri(chooser, uri); } g_free(uri); g_object_unref(win_config); } static void save_last_folder(GtkFileChooser *chooser) { gchar *uri = gtk_file_chooser_get_current_folder_uri(chooser); GSettings *win_config = g_settings_new(CONFIG_WIN_STATE); g_settings_set_string(win_config, "last-folder-uri", uri?:""); g_free(uri); g_object_unref(win_config); } static void response_handler(GtkDialog *dialog, gint response_id, gpointer data) { if(response_id == GTK_RESPONSE_ACCEPT) { GSettings *main_config; gboolean last_folder_enable; main_config = g_settings_new(CONFIG_ROOT); last_folder_enable = g_settings_get_boolean (main_config, "last-folder-enable"); if(last_folder_enable) { save_last_folder(GTK_FILE_CHOOSER(dialog)); } g_object_unref(main_config); } } GmpvFileChooser *gmpv_file_chooser_new( const gchar *title, GtkWindow *parent, GtkFileChooserAction action ) { GmpvFileChooser *chooser; GtkFileChooser *gtk_chooser; GSettings *main_config; gboolean last_folder_enable; #if GTK_CHECK_VERSION(3, 19, 7) chooser = gtk_file_chooser_native_new(title, parent, action, NULL, NULL); #else chooser = gtk_file_chooser_dialog_new( title, parent, action, _("_Cancel"), GTK_RESPONSE_CANCEL, _("_Open"), GTK_RESPONSE_ACCEPT, NULL ); #endif gtk_chooser = GTK_FILE_CHOOSER(chooser); main_config = g_settings_new(CONFIG_ROOT); last_folder_enable = g_settings_get_boolean (main_config, "last-folder-enable"); if(last_folder_enable) { load_last_folder(GTK_FILE_CHOOSER(chooser)); } gmpv_file_chooser_set_modal(chooser, TRUE); gtk_file_chooser_set_select_multiple(gtk_chooser, TRUE); gtk_file_chooser_set_do_overwrite_confirmation(gtk_chooser, TRUE); g_signal_connect(chooser, "response", G_CALLBACK(response_handler), NULL); g_object_unref(main_config); return chooser; } void gmpv_file_chooser_set_default_filters( GmpvFileChooser *chooser, gboolean audio, gboolean video, gboolean image, gboolean subtitle ) { GtkFileChooser *gtk_chooser = GTK_FILE_CHOOSER(chooser); GSList *filters = gtk_file_chooser_list_filters(gtk_chooser); for(GSList *iter = filters; iter; iter = g_slist_next(iter)) { gtk_file_chooser_remove_filter(gtk_chooser, iter->data); } if(audio || video || image || subtitle) { GtkFileFilter *filter = gtk_file_filter_new(); gtk_file_filter_set_name(filter, _("All Files")); gtk_file_filter_add_pattern(filter, "*"); gtk_file_chooser_add_filter(gtk_chooser, filter); } if(audio || video || image) { GtkFileFilter *filter = gtk_file_filter_new(); gtk_file_filter_set_name(filter, _("Media Files")); gtk_file_filter_add_mime_type(filter, "audio/*"); gtk_file_filter_add_mime_type(filter, "video/*"); gtk_file_filter_add_mime_type(filter, "images/*"); gtk_file_chooser_add_filter(gtk_chooser, filter); gtk_file_chooser_set_filter(gtk_chooser, filter); } if(audio) { GtkFileFilter *filter = gtk_file_filter_new(); gtk_file_filter_set_name(filter, _("Audio Files")); gtk_file_filter_add_mime_type(filter, "audio/*"); gtk_file_chooser_add_filter(gtk_chooser, filter); } if(video) { GtkFileFilter *filter = gtk_file_filter_new(); gtk_file_filter_set_name(filter, _("Video Files")); gtk_file_filter_add_mime_type(filter, "video/*"); gtk_file_chooser_add_filter(gtk_chooser, filter); } if(image) { GtkFileFilter *filter = gtk_file_filter_new(); gtk_file_filter_set_name(filter, _("Image Files")); gtk_file_filter_add_mime_type(filter, "images/*"); gtk_file_chooser_add_filter(gtk_chooser, filter); } if(subtitle) { GtkFileFilter *filter = gtk_file_filter_new(); const gchar *exts[] = SUBTITLE_EXTS; gtk_file_filter_set_name(filter, _("Subtitle Files")); for(gint i = 0; exts[i]; i++) { gchar *pattern = g_strdup_printf("*.%s", exts[i]); gtk_file_filter_add_pattern(filter, pattern); g_free(pattern); } gtk_file_chooser_add_filter(gtk_chooser, filter); if(!(audio || video || image)) { gtk_file_chooser_set_filter(gtk_chooser, filter); } } } gnome-mpv-0.13/src/gmpv_file_chooser.h000066400000000000000000000036221317030365200177770ustar00rootroot00000000000000/* * Copyright (c) 2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef FILE_CHOOSER_H #define FILE_CHOOSER_H #include G_BEGIN_DECLS #if GTK_CHECK_VERSION(3, 19, 7) #define GMPV_FILE_CHOOSER GTK_FILE_CHOOSER_NATIVE #define GmpvFileChooser GtkFileChooserNative #define gmpv_file_chooser_destroy(x) gtk_native_dialog_destroy(GTK_NATIVE_DIALOG(x)) #define gmpv_file_chooser_show(x) gtk_native_dialog_show(GTK_NATIVE_DIALOG(x)) #define gmpv_file_chooser_set_modal(x, y) gtk_native_dialog_set_modal(GTK_NATIVE_DIALOG(x), y) #define gmpv_file_chooser_run(x) gtk_native_dialog_run(GTK_NATIVE_DIALOG(x)) #else #define GMPV_FILE_CHOOSER GTK_WIDGET #define GmpvFileChooser GtkWidget #define gmpv_file_chooser_destroy(x) gtk_widget_destroy(GTK_WIDGET(x)) #define gmpv_file_chooser_show(x) gtk_widget_show_all(GTK_WIDGET(x)) #define gmpv_file_chooser_set_modal(x, y) gtk_window_set_modal(GTK_WINDOW(x), y) #define gmpv_file_chooser_run(x) gtk_dialog_run(GTK_DIALOG(x)) #endif GmpvFileChooser *gmpv_file_chooser_new( const gchar *title, GtkWindow *parent, GtkFileChooserAction action ); void gmpv_file_chooser_set_default_filters( GmpvFileChooser *chooser, gboolean audio, gboolean video, gboolean image, gboolean subtitle ); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_header_bar.c000066400000000000000000000103431317030365200174030ustar00rootroot00000000000000/* * Copyright (c) 2016-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include "gmpv_header_bar.h" #include "gmpv_menu.h" struct _GmpvHeaderBar { GtkHeaderBar parent_instance; GtkWidget *open_btn; GtkWidget *fullscreen_btn; GtkWidget *menu_btn; }; struct _GmpvHeaderBarClass { GtkHeaderBarClass parent_class; }; G_DEFINE_TYPE(GmpvHeaderBar, gmpv_header_bar, GTK_TYPE_HEADER_BAR) static void gmpv_header_bar_class_init(GmpvHeaderBarClass *klass) { } static void gmpv_header_bar_init(GmpvHeaderBar *hdr) { GtkHeaderBar *ghdr; GMenu *open_btn_menu; GMenu *menu_btn_menu; GtkWidget *open_icon; GtkWidget *fullscreen_icon; GtkWidget *menu_icon; ghdr = GTK_HEADER_BAR(hdr); open_btn_menu = g_menu_new(); menu_btn_menu = g_menu_new(); open_icon = gtk_image_new_from_icon_name ("list-add-symbolic", GTK_ICON_SIZE_MENU); fullscreen_icon = gtk_image_new_from_icon_name ("view-fullscreen-symbolic", GTK_ICON_SIZE_MENU); menu_icon = gtk_image_new_from_icon_name ("open-menu-symbolic", GTK_ICON_SIZE_MENU); hdr->open_btn = gtk_menu_button_new(); hdr->fullscreen_btn = gtk_button_new(); hdr->menu_btn = gtk_menu_button_new(); gmpv_menu_build_open_btn(open_btn_menu); gmpv_menu_build_menu_btn(menu_btn_menu, NULL); g_object_set(open_icon, "use-fallback", TRUE, NULL); g_object_set(fullscreen_icon, "use-fallback", TRUE, NULL); g_object_set(menu_icon, "use-fallback", TRUE, NULL); gtk_button_set_image(GTK_BUTTON(hdr->open_btn), open_icon); gtk_button_set_image(GTK_BUTTON(hdr->fullscreen_btn), fullscreen_icon); gtk_button_set_image(GTK_BUTTON(hdr->menu_btn), menu_icon); gtk_menu_button_set_menu_model ( GTK_MENU_BUTTON(hdr->open_btn), G_MENU_MODEL(open_btn_menu) ); gtk_menu_button_set_menu_model ( GTK_MENU_BUTTON(hdr->menu_btn), G_MENU_MODEL(menu_btn_menu) ); gtk_widget_set_tooltip_text (hdr->fullscreen_btn, _("Toggle Fullscreen")); gtk_actionable_set_action_name (GTK_ACTIONABLE(hdr->fullscreen_btn), "win.toggle-fullscreen"); gtk_widget_set_can_focus(hdr->open_btn, FALSE); gtk_widget_set_can_focus(hdr->fullscreen_btn, FALSE); gtk_widget_set_can_focus(hdr->menu_btn, FALSE); gtk_header_bar_pack_start(ghdr, hdr->open_btn); gtk_header_bar_pack_end(ghdr, hdr->menu_btn); gtk_header_bar_pack_end(ghdr, hdr->fullscreen_btn); gtk_header_bar_set_show_close_button(ghdr, TRUE); } GtkWidget *gmpv_header_bar_new() { return GTK_WIDGET(g_object_new(gmpv_header_bar_get_type(), NULL)); } gboolean gmpv_header_bar_get_open_button_popup_visible(GmpvHeaderBar *hdr) { GtkMenuButton *btn = GTK_MENU_BUTTON(hdr->open_btn); GtkWidget *popover = GTK_WIDGET(gtk_menu_button_get_popover(btn)); return gtk_widget_is_visible(popover); } gboolean gmpv_header_bar_get_menu_button_popup_visible(GmpvHeaderBar *hdr) { GtkMenuButton *btn = GTK_MENU_BUTTON(hdr->menu_btn); GtkWidget *popover = GTK_WIDGET(gtk_menu_button_get_popover(btn)); return gtk_widget_is_visible(popover); } void gmpv_header_bar_set_fullscreen_state( GmpvHeaderBar *hdr, gboolean fullscreen ) { GtkWidget *image = gtk_button_get_image(GTK_BUTTON(hdr->fullscreen_btn)); gtk_image_set_from_icon_name( GTK_IMAGE(image), fullscreen? "view-restore-symbolic": "view-fullscreen-symbolic", GTK_ICON_SIZE_MENU ); gtk_header_bar_set_show_close_button(GTK_HEADER_BAR(hdr), !fullscreen); } void gmpv_header_bar_update_track_list( GmpvHeaderBar *hdr, const GPtrArray *track_list ) { GMenu *menu = g_menu_new(); gmpv_menu_build_menu_btn(menu, track_list); gtk_menu_button_set_menu_model (GTK_MENU_BUTTON(hdr->menu_btn), G_MENU_MODEL(menu)); } gnome-mpv-0.13/src/gmpv_header_bar.h000066400000000000000000000025231317030365200174110ustar00rootroot00000000000000/* * Copyright (c) 2016-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef HEADER_BAR_H #define HEADER_BAR_H #include #include #include #define GMPV_TYPE_HEADER_BAR (gmpv_header_bar_get_type ()) G_DECLARE_FINAL_TYPE(GmpvHeaderBar, gmpv_header_bar, GMPV, HEADER_BAR, GtkHeaderBar) GtkWidget *gmpv_header_bar_new(void); gboolean gmpv_header_bar_get_open_button_popup_visible(GmpvHeaderBar *hdr); gboolean gmpv_header_bar_get_menu_button_popup_visible(GmpvHeaderBar *hdr); void gmpv_header_bar_set_fullscreen_state( GmpvHeaderBar *hdr, gboolean fullscreen ); void gmpv_header_bar_update_track_list( GmpvHeaderBar *hdr, const GPtrArray *track_list ); #endif gnome-mpv-0.13/src/gmpv_main.c000066400000000000000000000022061317030365200162520ustar00rootroot00000000000000/* * Copyright (c) 2014-2016 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include "gmpv_application.h" #include "gmpv_def.h" int main(int argc, char **argv) { GApplicationFlags flags; GmpvApplication *app; gint status; flags = G_APPLICATION_HANDLES_COMMAND_LINE|G_APPLICATION_HANDLES_OPEN; app = gmpv_application_new(APP_ID, flags); status = g_application_run(G_APPLICATION(app), argc, argv); g_object_unref(app); return status; } gnome-mpv-0.13/src/gmpv_main_window.c000066400000000000000000000434731317030365200176540ustar00rootroot00000000000000/* * Copyright (c) 2014-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include #include "gmpv_def.h" #include "gmpv_marshal.h" #include "gmpv_menu.h" #include "gmpv_application.h" #include "gmpv_playlist_widget.h" #include "gmpv_main_window.h" #include "gmpv_header_bar.h" #include "gmpv_control_box.h" #include "gmpv_video_area.h" enum { PROP_0, PROP_ALWAYS_FLOATING, N_PROPERTIES }; struct _GmpvMainWindow { GtkApplicationWindow parent_instance; gint width_offset; gint height_offset; gint resize_target[2]; gboolean csd; gboolean always_floating; gboolean use_floating_controls; gboolean fullscreen; gboolean playlist_visible; gboolean playlist_first_toggle; gboolean pre_fs_playlist_visible; gint playlist_width; guint timeout_tag; const GPtrArray *track_list; GtkWidget *header_bar; GtkWidget *main_box; GtkWidget *vid_area_paned; GtkWidget *vid_area; GtkWidget *control_box; GtkWidget *playlist; }; struct _GmpvMainWindowClass { GtkApplicationWindowClass parent_class; }; static void gmpv_main_window_constructed(GObject *object); static void gmpv_main_window_set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ); static void gmpv_main_window_get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ); static void seek_handler(GtkWidget *widget, gdouble value, gpointer data); static void button_clicked_handler( GmpvControlBox *control_box, const gchar *button, gpointer data ); static void gmpv_main_window_notify(GObject *object, GParamSpec *pspec); static void resize_video_area_finalize( GtkWidget *widget, GdkRectangle *allocation, gpointer data ); static gboolean resize_to_target(gpointer data); G_DEFINE_TYPE(GmpvMainWindow, gmpv_main_window, GTK_TYPE_APPLICATION_WINDOW) static void gmpv_main_window_constructed(GObject *object) { GmpvMainWindow *self = GMPV_MAIN_WINDOW(object); self->playlist = gmpv_playlist_widget_new(); gtk_widget_show_all(self->playlist); gtk_widget_hide(self->playlist); gtk_widget_set_no_show_all(self->playlist, TRUE); gtk_widget_show_all(self->control_box); gtk_widget_hide(self->control_box); gtk_widget_set_no_show_all(self->control_box, TRUE); gtk_paned_pack1( GTK_PANED(self->vid_area_paned), self->vid_area, TRUE, TRUE ); gtk_paned_pack2( GTK_PANED(self->vid_area_paned), self->playlist, FALSE, FALSE ); G_OBJECT_CLASS(gmpv_main_window_parent_class)->constructed(object); } static void gmpv_main_window_set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ) { GmpvMainWindow *self = GMPV_MAIN_WINDOW(object); if(property_id == PROP_ALWAYS_FLOATING) { self->always_floating = g_value_get_boolean(value); } else { G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); } } static void gmpv_main_window_get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ) { GmpvMainWindow *self = GMPV_MAIN_WINDOW(object); if(property_id == PROP_ALWAYS_FLOATING) { g_value_set_boolean(value, self->always_floating); } else { G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); } } static void seek_handler(GtkWidget *widget, gdouble value, gpointer data) { g_signal_emit_by_name(data, "seek", value); } static void button_clicked_handler( GmpvControlBox *control_box, const gchar *button, gpointer data ) { g_signal_emit_by_name(data, "button-clicked", button); } static void gmpv_main_window_notify(GObject *object, GParamSpec *pspec) { if(g_strcmp0(pspec->name, "always-use-floating-controls") == 0) { GmpvMainWindow *wnd = GMPV_MAIN_WINDOW(object); gboolean floating = wnd->always_floating || wnd->fullscreen; gmpv_main_window_set_use_floating_controls(wnd, floating); } } static void resize_video_area_finalize( GtkWidget *widget, GdkRectangle *allocation, gpointer data ) { GmpvMainWindow *wnd = data; GdkScreen *screen = gdk_screen_get_default(); gint screen_width = gdk_screen_get_width(screen); gint screen_height = gdk_screen_get_height(screen); gint width = allocation->width; gint height = allocation->height; gint target_width = wnd->resize_target[0]; gint target_height = wnd->resize_target[1]; g_signal_handlers_disconnect_by_func (widget, resize_video_area_finalize, data); /* Adjust resize offset */ if((width != target_width || height != target_height) && (target_width < screen_width && target_height < screen_height) && !gtk_window_is_maximized(GTK_WINDOW(wnd)) && !wnd->fullscreen) { wnd->width_offset += target_width-width; wnd->height_offset += target_height-height; g_idle_add_full(G_PRIORITY_HIGH_IDLE, resize_to_target, wnd, NULL); } } static gboolean resize_to_target(gpointer data) { GmpvMainWindow *wnd = data; gint target_width = wnd->resize_target[0]; gint target_height = wnd->resize_target[1]; gtk_window_resize( GTK_WINDOW(wnd), target_width+wnd->width_offset, target_height+wnd->height_offset ); /* Prevent graphical glitches that appear when calling * gmpv_main_window_resize_video_area() with the current size as the * target size. */ gmpv_playlist_widget_queue_draw(GMPV_PLAYLIST_WIDGET(wnd->playlist)); return FALSE; } static void gmpv_main_window_class_init(GmpvMainWindowClass *klass) { GObjectClass *obj_class = G_OBJECT_CLASS(klass); GParamSpec *pspec = NULL; obj_class->constructed = gmpv_main_window_constructed; obj_class->set_property = gmpv_main_window_set_property; obj_class->get_property = gmpv_main_window_get_property; obj_class->notify = gmpv_main_window_notify; pspec = g_param_spec_boolean ( "always-use-floating-controls", "Always use floating controls", "Whether or not to use floating controls in windowed mode", FALSE, G_PARAM_READWRITE ); g_object_class_install_property(obj_class, PROP_ALWAYS_FLOATING, pspec); g_signal_new( "button-clicked", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__STRING, G_TYPE_NONE, 1, G_TYPE_STRING ); g_signal_new( "seek", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__DOUBLE, G_TYPE_NONE, 1, G_TYPE_DOUBLE ); } static void gmpv_main_window_init(GmpvMainWindow *wnd) { GmpvControlBox *vid_area_control_box = NULL; wnd->csd = FALSE; wnd->always_floating = FALSE; wnd->use_floating_controls = FALSE; wnd->fullscreen = FALSE; wnd->playlist_visible = FALSE; wnd->pre_fs_playlist_visible = FALSE; wnd->playlist_width = PLAYLIST_DEFAULT_WIDTH; wnd->timeout_tag = 0; wnd->track_list = NULL; wnd->header_bar = gmpv_header_bar_new(); wnd->main_box = gtk_box_new(GTK_ORIENTATION_VERTICAL, 0); wnd->vid_area_paned = gtk_paned_new(GTK_ORIENTATION_HORIZONTAL); wnd->vid_area = gmpv_video_area_new(); wnd->control_box = gmpv_control_box_new(); wnd->playlist_first_toggle = TRUE; wnd->width_offset = 0; wnd->height_offset = 0; vid_area_control_box = gmpv_video_area_get_control_box (GMPV_VIDEO_AREA(wnd->vid_area)); g_object_bind_property( wnd, "title", wnd->vid_area, "title", G_BINDING_DEFAULT ); g_object_bind_property( wnd->control_box, "duration", vid_area_control_box, "duration", G_BINDING_DEFAULT ); g_object_bind_property( wnd->control_box, "pause", vid_area_control_box, "pause", G_BINDING_DEFAULT ); g_object_bind_property( wnd->control_box, "chapters-enabled", vid_area_control_box, "chapters-enabled", G_BINDING_DEFAULT ); g_object_bind_property( wnd->control_box, "time-position", vid_area_control_box, "time-position", G_BINDING_DEFAULT ); g_object_bind_property( wnd->control_box, "volume", vid_area_control_box, "volume", G_BINDING_BIDIRECTIONAL ); g_signal_connect( wnd->control_box, "seek", G_CALLBACK(seek_handler), wnd ); g_signal_connect( wnd->control_box, "button-clicked", G_CALLBACK(button_clicked_handler), wnd ); g_signal_connect( vid_area_control_box, "seek", G_CALLBACK(seek_handler), wnd ); g_signal_connect( vid_area_control_box, "button-clicked", G_CALLBACK(button_clicked_handler), wnd ); gtk_widget_add_events( wnd->vid_area, GDK_ENTER_NOTIFY_MASK |GDK_LEAVE_NOTIFY_MASK ); gtk_window_set_title(GTK_WINDOW(wnd), g_get_application_name()); gtk_paned_set_position( GTK_PANED(wnd->vid_area_paned), MAIN_WINDOW_DEFAULT_WIDTH -PLAYLIST_DEFAULT_WIDTH ); gtk_window_set_default_size( GTK_WINDOW(wnd), MAIN_WINDOW_DEFAULT_WIDTH, MAIN_WINDOW_DEFAULT_HEIGHT ); gtk_box_pack_start (GTK_BOX(wnd->main_box), wnd->vid_area_paned, TRUE, TRUE, 0); gtk_container_add(GTK_CONTAINER(wnd->main_box), wnd->control_box); gtk_container_add(GTK_CONTAINER(wnd), wnd->main_box); } GtkWidget *gmpv_main_window_new( GtkApplication *app, gboolean always_floating ) { return GTK_WIDGET(g_object_new( gmpv_main_window_get_type(), "application", app, "always-use-floating-controls", always_floating, NULL )); } GmpvPlaylistWidget *gmpv_main_window_get_playlist(GmpvMainWindow *wnd) { return GMPV_PLAYLIST_WIDGET(wnd->playlist); } GmpvControlBox *gmpv_main_window_get_control_box(GmpvMainWindow *wnd) { return GMPV_CONTROL_BOX(wnd->control_box); } GmpvVideoArea *gmpv_main_window_get_video_area(GmpvMainWindow *wnd) { return GMPV_VIDEO_AREA(wnd->vid_area); } void gmpv_main_window_set_use_floating_controls( GmpvMainWindow *wnd, gboolean floating ) { if(floating != wnd->use_floating_controls) { gtk_widget_set_visible (wnd->control_box, !floating); gmpv_video_area_set_control_box_visible (GMPV_VIDEO_AREA(wnd->vid_area), floating); wnd->use_floating_controls = floating; } } gboolean gmpv_main_window_get_use_floating_controls(GmpvMainWindow *wnd) { return wnd->use_floating_controls; } void gmpv_main_window_set_fullscreen(GmpvMainWindow *wnd, gboolean fullscreen) { if(fullscreen != wnd->fullscreen) { GmpvVideoArea *vid_area = GMPV_VIDEO_AREA(wnd->vid_area); gboolean floating = wnd->always_floating || fullscreen; gboolean playlist_visible = !fullscreen && wnd->pre_fs_playlist_visible; if(fullscreen) { gtk_window_fullscreen(GTK_WINDOW(wnd)); gtk_window_present(GTK_WINDOW(wnd)); wnd->pre_fs_playlist_visible = wnd->playlist_visible; } else { gtk_window_unfullscreen(GTK_WINDOW(wnd)); wnd->playlist_visible = wnd->pre_fs_playlist_visible; } if(!gmpv_main_window_get_csd_enabled(wnd)) { GtkApplication *app; GMenu *menu; app = gtk_window_get_application(GTK_WINDOW(wnd)); menu = G_MENU(gtk_application_get_menubar(app)); /* gtk_application_window_set_show_menubar() cannot be * used here since it will cause assertion failure when * opengl-cb is used. */ if(fullscreen) { g_menu_remove_all(menu); } else { gmpv_menu_build_full(menu, wnd->track_list); } } gmpv_video_area_set_fullscreen_state(vid_area, fullscreen); gmpv_main_window_set_use_floating_controls(wnd, floating); gtk_widget_set_visible(wnd->playlist, playlist_visible); wnd->fullscreen = fullscreen; } } gboolean gmpv_main_window_get_fullscreen(GmpvMainWindow *wnd) { return wnd->fullscreen; } void gmpv_main_window_toggle_fullscreen(GmpvMainWindow *wnd) { gmpv_main_window_set_fullscreen(wnd, !wnd->fullscreen); } void gmpv_main_window_reset(GmpvMainWindow *wnd) { gtk_window_set_title(GTK_WINDOW(wnd), g_get_application_name()); gmpv_control_box_reset(GMPV_CONTROL_BOX(wnd->control_box)); } void gmpv_main_window_save_state(GmpvMainWindow *wnd) { GSettings *settings; gint width; gint height; gint handle_pos; gdouble volume; gboolean controls_visible; settings = g_settings_new(CONFIG_WIN_STATE); handle_pos = gtk_paned_get_position(GTK_PANED(wnd->vid_area_paned)); volume = gmpv_control_box_get_volume(GMPV_CONTROL_BOX(wnd->control_box)); controls_visible = gtk_widget_get_visible(wnd->control_box); gtk_window_get_size(GTK_WINDOW(wnd), &width, &height); g_settings_set_int(settings, "width", width); g_settings_set_int(settings, "height", height); g_settings_set_double(settings, "volume", volume); g_settings_set_boolean(settings, "show-controls", controls_visible); g_settings_set_boolean(settings, "show-playlist", wnd->playlist_visible); if(gmpv_main_window_get_playlist_visible(wnd)) { g_settings_set_int( settings, "playlist-width", width-handle_pos ); } else { g_settings_set_int( settings, "playlist-width", wnd->playlist_width ); } g_clear_object(&settings); } void gmpv_main_window_load_state(GmpvMainWindow *wnd) { if(!gtk_widget_get_realized(GTK_WIDGET(wnd))) { GSettings *settings = g_settings_new(CONFIG_WIN_STATE); gint width = g_settings_get_int(settings, "width"); gint height = g_settings_get_int(settings, "height"); gint handle_pos; gboolean controls_visible; gdouble volume; wnd->playlist_width = g_settings_get_int(settings, "playlist-width"); wnd->playlist_visible = g_settings_get_boolean(settings, "show-playlist"); controls_visible = g_settings_get_boolean(settings, "show-controls"); volume = g_settings_get_double(settings, "volume"); handle_pos = width-(wnd->playlist_visible?wnd->playlist_width:0); gmpv_control_box_set_volume (GMPV_CONTROL_BOX(wnd->control_box), volume); gtk_widget_set_visible(wnd->control_box, controls_visible); gtk_widget_set_visible(wnd->playlist, wnd->playlist_visible); gtk_window_resize(GTK_WINDOW(wnd), width, height); gtk_paned_set_position (GTK_PANED(wnd->vid_area_paned), handle_pos); g_clear_object(&settings); } else { g_critical( "Attempted to call gmpv_main_window_load_state() " "on realized window" ); } } void gmpv_main_window_update_track_list( GmpvMainWindow *wnd, const GPtrArray *track_list ) { wnd->track_list = track_list; if(gmpv_main_window_get_csd_enabled(wnd)) { gmpv_header_bar_update_track_list (GMPV_HEADER_BAR(wnd->header_bar), track_list); gmpv_video_area_update_track_list (GMPV_VIDEO_AREA(wnd->vid_area), track_list); } else { GtkApplication *app; GMenu *menu; app = gtk_window_get_application(GTK_WINDOW(wnd)); menu = G_MENU(gtk_application_get_menubar(app)); if(menu) { g_menu_remove_all(menu); gmpv_menu_build_full(menu, track_list); } } } void gmpv_main_window_resize_video_area( GmpvMainWindow *wnd, gint width, gint height ) { g_signal_connect( wnd->vid_area, "size-allocate", G_CALLBACK(resize_video_area_finalize), wnd ); wnd->resize_target[0] = width; wnd->resize_target[1] = height; resize_to_target(wnd); /* The size may not change, so this is needed to ensure that * resize_video_area_finalize() will be called so that the event handler * will be disconnected. */ #if GTK_CHECK_VERSION(3, 20, 0) gtk_widget_queue_allocate(wnd->vid_area); #else gtk_widget_queue_resize(wnd->vid_area); #endif } void gmpv_main_window_enable_csd(GmpvMainWindow *wnd) { wnd->csd = TRUE; wnd->playlist_width = PLAYLIST_DEFAULT_WIDTH; gtk_paned_set_position( GTK_PANED(wnd->vid_area_paned), MAIN_WINDOW_DEFAULT_WIDTH -PLAYLIST_DEFAULT_WIDTH ); gtk_window_set_titlebar(GTK_WINDOW(wnd), wnd->header_bar); gtk_window_set_title(GTK_WINDOW(wnd), g_get_application_name()); } gboolean gmpv_main_window_get_csd_enabled(GmpvMainWindow *wnd) { return wnd->csd; } void gmpv_main_window_set_playlist_visible( GmpvMainWindow *wnd, gboolean visible ) { if(visible != wnd->playlist_visible && !wnd->fullscreen) { gboolean maximized; gint handle_pos; gint width; gint height; maximized = gtk_window_is_maximized(GTK_WINDOW(wnd)); handle_pos = gtk_paned_get_position (GTK_PANED(wnd->vid_area_paned)); gtk_window_get_size(GTK_WINDOW(wnd), &width, &height); if(wnd->playlist_first_toggle && visible) { gint new_pos = width-(maximized?wnd->playlist_width:0); if(gtk_check_version(3, 20, 0)) { /* Workaround for window sizing bug affecting * GTK+ < 3.20 */ new_pos -= 52; } gtk_paned_set_position( GTK_PANED(wnd->vid_area_paned), new_pos ); } else if(!visible) { wnd->playlist_width = width-handle_pos; } wnd->playlist_visible = visible; gtk_widget_set_visible(wnd->playlist, visible); if(!maximized) { if(!gtk_check_version(3, 20, 0)) { gint new_width; new_width = visible? width+wnd->playlist_width: handle_pos; gtk_window_resize( GTK_WINDOW(wnd), new_width, height ); } else { /* Workaround for window sizing bug affecting * GTK+ < 3.20 */ gboolean csd; gint wnd_offset; gint new_width; csd = gmpv_main_window_get_csd_enabled(wnd); wnd_offset = csd?52:0; new_width = visible? width+wnd->playlist_width-wnd_offset: handle_pos+wnd_offset; gtk_window_resize( GTK_WINDOW(wnd), new_width, height ); } } wnd->playlist_first_toggle = FALSE; } } gboolean gmpv_main_window_get_playlist_visible(GmpvMainWindow *wnd) { return gtk_widget_get_visible(GTK_WIDGET(wnd->playlist)); } void gmpv_main_window_set_controls_visible( GmpvMainWindow *wnd, gboolean visible ) { gtk_widget_set_visible(GTK_WIDGET(wnd->control_box), visible); } gboolean gmpv_main_window_get_controls_visible(GmpvMainWindow *wnd) { return gtk_widget_get_visible(GTK_WIDGET(wnd->control_box)); } gnome-mpv-0.13/src/gmpv_main_window.h000066400000000000000000000050451317030365200176520ustar00rootroot00000000000000/* * Copyright (c) 2014-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef MAIN_WINDOW_H #define MAIN_WINDOW_H #include #include #include #include "gmpv_playlist_widget.h" #include "gmpv_control_box.h" #include "gmpv_video_area.h" G_BEGIN_DECLS #define GMPV_TYPE_MAIN_WINDOW (gmpv_main_window_get_type ()) G_DECLARE_FINAL_TYPE(GmpvMainWindow, gmpv_main_window, GMPV, MAIN_WINDOW, GtkApplicationWindow) GtkWidget *gmpv_main_window_new( GtkApplication *app, gboolean always_floating ); GmpvPlaylistWidget *gmpv_main_window_get_playlist(GmpvMainWindow *wnd); GmpvControlBox *gmpv_main_window_get_control_box(GmpvMainWindow *wnd); GmpvVideoArea *gmpv_main_window_get_video_area(GmpvMainWindow *wnd); void gmpv_main_window_set_use_floating_controls( GmpvMainWindow *wnd, gboolean floating ); gboolean gmpv_main_window_get_use_floating_controls(GmpvMainWindow *wnd); void gmpv_main_window_set_fullscreen(GmpvMainWindow *wnd, gboolean fullscreen); gboolean gmpv_main_window_get_fullscreen(GmpvMainWindow *wnd); void gmpv_main_window_toggle_fullscreen(GmpvMainWindow *wnd); void gmpv_main_window_reset(GmpvMainWindow *wnd); void gmpv_main_window_save_state(GmpvMainWindow *wnd); void gmpv_main_window_load_state(GmpvMainWindow *wnd); void gmpv_main_window_update_track_list( GmpvMainWindow *wnd, const GPtrArray *track_list ); void gmpv_main_window_resize_video_area( GmpvMainWindow *wnd, gint width, gint height ); void gmpv_main_window_enable_csd(GmpvMainWindow *wnd); gboolean gmpv_main_window_get_csd_enabled(GmpvMainWindow *wnd); void gmpv_main_window_set_playlist_visible( GmpvMainWindow *wnd, gboolean visible ); gboolean gmpv_main_window_get_playlist_visible(GmpvMainWindow *wnd); void gmpv_main_window_set_controls_visible( GmpvMainWindow *wnd, gboolean visible ); gboolean gmpv_main_window_get_controls_visible(GmpvMainWindow *wnd); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_menu.c000066400000000000000000000220261317030365200162740ustar00rootroot00000000000000/* * Copyright (c) 2015-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include #include "gmpv_menu.h" #include "gmpv_common.h" typedef struct GmpvMenuEntry GmpvMenuEntry; struct GmpvMenuEntry { gchar *title; gchar *action; GMenu *submenu; }; static void split_track_list( const GPtrArray *track_list, GPtrArray **audio_tracks, GPtrArray **video_tracks, GPtrArray **subtitle_tracks ); static GMenu *build_menu_from_track_list( const GPtrArray *list, const gchar *action, const gchar *load_action ); static void build_menu(GMenu *menu, const GmpvMenuEntry *entries, gboolean flat); static GMenu *build_video_track_menu(const GPtrArray *list); static GMenu *build_audio_track_menu(const GPtrArray *list); static GMenu *build_subtitle_track_menu(const GPtrArray *list); static void split_track_list( const GPtrArray *track_list, GPtrArray **audio_tracks, GPtrArray **video_tracks, GPtrArray **subtitle_tracks ) { guint track_list_len = track_list?track_list->len:0; g_assert(audio_tracks && video_tracks && subtitle_tracks); /* The contents of these array are shallow-copied from track_list and * therefore only the container should be freed. */ *audio_tracks = g_ptr_array_new(); *video_tracks = g_ptr_array_new(); *subtitle_tracks = g_ptr_array_new(); for(guint i = 0; i < track_list_len; i++) { GmpvTrack *track = g_ptr_array_index(track_list, i); switch(track->type) { case TRACK_TYPE_AUDIO: g_ptr_array_add(*audio_tracks, track); break; case TRACK_TYPE_VIDEO: g_ptr_array_add(*video_tracks, track); break; case TRACK_TYPE_SUBTITLE: g_ptr_array_add(*subtitle_tracks, track); break; default: g_assert_not_reached(); break; } } } static GMenu *build_menu_from_track_list( const GPtrArray *list, const gchar *action, const gchar *load_action ) { GMenu *menu = g_menu_new(); const glong max_len = 32; gchar *detailed_action; g_assert(list); detailed_action = g_strdup_printf("%s(@x 0)", action); g_menu_append(menu, _("None"), detailed_action); g_free(detailed_action); for(guint i = 0; i < list->len; i++) { GmpvTrack *entry; glong entry_title_len; gchar *entry_title; gchar *title; entry = g_ptr_array_index(list, i); /* For simplicity, also dup the default string used when the * track has no title. */ entry_title = g_strdup(entry->title?:_("Unknown")); /* Maximum number of bytes per UTF-8 character is 4 */ entry_title_len = g_utf8_strlen(entry_title, 4*(max_len+1)); if(entry_title_len > max_len) { /* Truncate the string */ *(g_utf8_offset_to_pointer(entry_title, max_len)) = '\0'; } detailed_action = g_strdup_printf( "%s(@x %" G_GINT64_FORMAT ")", action, entry->id ); /* Ellipsize the title if it's longer than max_len */ title = g_strdup_printf( entry->lang? "%s%s (%s)":"%s%s", entry_title, (entry_title_len > max_len)? "…":"", entry->lang ); g_menu_append(menu, title, detailed_action); g_free(detailed_action); g_free(entry_title); g_free(title); } if(load_action) { g_menu_append(menu, _("_Load External…"), load_action); } return menu; } static void build_menu(GMenu *menu, const GmpvMenuEntry *entries, gboolean flat) { GMenu *current_submenu = NULL; for( gint i = 0; entries[i].title || entries[i].action || entries[i].submenu; i++ ) { const gchar *title = entries[i].title; const gchar *action = entries[i].action; const GMenu *submenu = entries[i].submenu; if(title && (action || submenu)) { GMenuItem *item; if(submenu) { item = g_menu_item_new_submenu (title, G_MENU_MODEL(submenu)); } else { item = g_menu_item_new(title, action); } g_menu_append_item(current_submenu, item); g_object_unref(item); } else { GMenuModel *model; current_submenu = g_menu_new(); model = G_MENU_MODEL(current_submenu); if(flat) { g_menu_append_section(menu, title, model); } else { g_menu_append_submenu(menu, title, model); } } } } static GMenu *build_video_track_menu(const GPtrArray *list) { return build_menu_from_track_list (list, "win.set-video-track", NULL); } static GMenu *build_audio_track_menu(const GPtrArray *list) { return build_menu_from_track_list ( list, "win.set-audio-track", "win.load-track('audio-add')" ); } static GMenu *build_subtitle_track_menu(const GPtrArray *list) { return build_menu_from_track_list ( list, "win.set-subtitle-track", "win.load-track('sub-add')" ); } void gmpv_menu_build_full(GMenu *menu, const GPtrArray *track_list) { GPtrArray *audio_tracks = NULL; GPtrArray *video_tracks = NULL; GPtrArray *subtitle_tracks = NULL; GMenu *video_menu = NULL; GMenu *audio_menu = NULL; GMenu *subtitle_menu = NULL; split_track_list (track_list, &audio_tracks, &video_tracks, &subtitle_tracks); video_menu = build_video_track_menu(video_tracks); audio_menu = build_audio_track_menu(audio_tracks); subtitle_menu = build_subtitle_track_menu(subtitle_tracks); const GmpvMenuEntry entries[] = { {_("_File"), NULL, NULL}, {_("_Open"), "win.show-open-dialog(false)", NULL}, {_("Open _Location"), "win.show-open-location-dialog(false)", NULL}, {_("_Save Playlist"), "win.save-playlist", NULL}, {_("_Quit"), "win.quit", NULL}, {_("_Edit"), NULL, NULL}, {_("_Preferences"), "win.show-preferences-dialog", NULL}, {_("_Video Track"), NULL, video_menu}, {_("_Audio Track"), NULL, audio_menu}, {_("S_ubtitle Track"), NULL, subtitle_menu}, {_("_View"), NULL, NULL}, {_("_Toggle Controls"), "win.toggle-controls", NULL}, {_("_Toggle Playlist"), "win.toggle-playlist", NULL}, {_("_Fullscreen"), "win.toggle-fullscreen", NULL}, {_("_Normal Size"), "win.set-video-size(@d 1)", NULL}, {_("_Double Size"), "win.set-video-size(@d 2)", NULL}, {_("_Half Size"), "win.set-video-size(@d 0.5)", NULL}, {_("_Help"), NULL, NULL}, {_("_Keyboard Shortcuts"), "win.show-shortcuts-dialog" , NULL}, {_("_About"), "win.show-about-dialog", NULL}, {NULL, NULL, NULL} }; build_menu(menu, entries, FALSE); g_ptr_array_free(audio_tracks, FALSE); g_ptr_array_free(video_tracks, FALSE); g_ptr_array_free(subtitle_tracks, FALSE); g_object_unref(video_menu); g_object_unref(audio_menu); g_object_unref(subtitle_menu); } void gmpv_menu_build_menu_btn(GMenu *menu, const GPtrArray *track_list) { GPtrArray *audio_tracks = NULL; GPtrArray *video_tracks = NULL; GPtrArray *subtitle_tracks = NULL; GMenu *video_menu = NULL; GMenu *audio_menu = NULL; GMenu *subtitle_menu = NULL; split_track_list (track_list, &audio_tracks, &video_tracks, &subtitle_tracks); video_menu = build_video_track_menu(video_tracks); audio_menu = build_audio_track_menu(audio_tracks); subtitle_menu = build_subtitle_track_menu(subtitle_tracks); const GmpvMenuEntry entries[] = { {NULL, "", NULL}, {_("_Toggle Controls"), "win.toggle-controls", NULL}, {NULL, "", NULL}, {_("_Toggle Playlist"), "win.toggle-playlist", NULL}, {_("_Save Playlist"), "win.save-playlist", NULL}, {NULL, "", NULL}, {_("_Video Track"), NULL, video_menu}, {_("_Audio Track"), NULL, audio_menu}, {_("S_ubtitle Track"), NULL, subtitle_menu}, {NULL, "", NULL}, {_("_Normal Size"), "win.set-video-size(@d 1)", NULL}, {_("_Double Size"), "win.set-video-size(@d 2)", NULL}, {_("_Half Size"), "win.set-video-size(@d 0.5)", NULL}, {NULL, NULL, NULL} }; build_menu(menu, entries, TRUE); g_ptr_array_free(audio_tracks, FALSE); g_ptr_array_free(video_tracks, FALSE); g_ptr_array_free(subtitle_tracks, FALSE); g_object_unref(video_menu); g_object_unref(audio_menu); g_object_unref(subtitle_menu); } void gmpv_menu_build_open_btn(GMenu *menu) { const GmpvMenuEntry entries[] = { {NULL, "", NULL}, {_("_Open"), "win.show-open-dialog(false)", NULL}, {_("Open _Location"), "win.show-open-location-dialog(false)", NULL}, {NULL, NULL, NULL} }; build_menu(menu, entries, TRUE); } void gmpv_menu_build_app_menu(GMenu *menu) { const GmpvMenuEntry entries[] = { {NULL, "", NULL}, {_("_New Window"), "app.new-window", NULL}, {NULL, "", NULL}, {_("_Preferences"), "win.show-preferences-dialog", NULL}, {NULL, "", NULL}, {_("_Keyboard Shortcuts"), "win.show-shortcuts-dialog", NULL}, {_("_About"), "win.show-about-dialog", NULL}, {_("_Quit"), "win.quit", NULL}, {NULL, NULL, NULL} }; build_menu(menu, entries, TRUE); } gnome-mpv-0.13/src/gmpv_menu.h000066400000000000000000000020701317030365200162760ustar00rootroot00000000000000/* * Copyright (c) 2015-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef MENU_H #define MENU_H #include #include G_BEGIN_DECLS void gmpv_menu_build_full(GMenu *gmpv_menu, const GPtrArray *track_list); void gmpv_menu_build_menu_btn(GMenu *gmpv_menu, const GPtrArray *track_list); void gmpv_menu_build_open_btn(GMenu *gmpv_menu); void gmpv_menu_build_app_menu(GMenu *gmpv_menu); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_metadata_cache.c000066400000000000000000000177011317030365200202370ustar00rootroot00000000000000/* * Copyright (c) 2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include "gmpv_metadata_cache.h" #include "gmpv_mpv.h" #include "gmpv_mpv_wrapper.h" struct _GmpvMetadataCache { GObject parent; GHashTable *table; GmpvMpv *fetcher; GQueue *fetch_queue; }; struct _GmpvMetadataCacheClass { GObjectClass parent_class; }; static void dispose(GObject *object) { g_clear_object(&GMPV_METADATA_CACHE(object)->fetcher); } static void finalize(GObject *object) { GmpvMetadataCache *cache = GMPV_METADATA_CACHE(object); g_hash_table_unref(cache->table); g_queue_free_full(cache->fetch_queue, g_free); } static void metadata_to_ptr_array(mpv_node metadata, GPtrArray *array); static void mpv_event_notify( GmpvMpv *mpv, gint event_id, gpointer event_data, gpointer data ); static gboolean fetch_metadata(GmpvMetadataCache *cache); static GmpvMetadataCacheEntry *gmpv_metadata_cache_entry_new(void); static void gmpv_metadata_cache_entry_free(GmpvMetadataCacheEntry *entry); G_DEFINE_TYPE(GmpvMetadataCache, gmpv_metadata_cache, G_TYPE_OBJECT) static GmpvMetadataCacheEntry *gmpv_metadata_cache_entry_new(void) { GmpvMetadataCacheEntry *entry = g_new0(GmpvMetadataCacheEntry, 1); entry->tags = g_ptr_array_new_with_free_func ((GDestroyNotify)gmpv_metadata_entry_free); return entry; } static void gmpv_metadata_cache_entry_free(GmpvMetadataCacheEntry *entry) { g_free(entry->title); g_ptr_array_free(entry->tags, TRUE); g_free(entry); } static void metadata_to_ptr_array(mpv_node metadata, GPtrArray *array) { mpv_node_list *list = metadata.u.list; g_ptr_array_set_size(array, 0); if(metadata.format == MPV_FORMAT_NODE_MAP && list->num > 0) { for(gint i = 0; i < list->num; i++) { const gchar *key = list->keys[i]; mpv_node value = list->values[i]; if(value.format == MPV_FORMAT_STRING) { GmpvMetadataEntry *entry; entry = gmpv_metadata_entry_new (key, value.u.string); g_ptr_array_add(array, entry); } else { g_warning( "Ignored metadata field %s " "with unexpected format %d", key, value.format ); } } } } static void mpv_event_notify( GmpvMpv *mpv, gint event_id, gpointer event_data, gpointer data ) { if(event_id == MPV_EVENT_FILE_LOADED) { GmpvMetadataCache *cache = data; GmpvMetadataCacheEntry *entry = NULL; gchar *path = NULL; gmpv_mpv_get_property(mpv, "path", MPV_FORMAT_STRING, &path); g_debug("Fetched metadata for %s", path); entry = g_hash_table_lookup(cache->table, path); if(entry) { const gchar *cmd[] = {"playlist-next", "force", NULL}; gint64 playlist_pos = 0; gint64 playlist_count = 0; gchar *media_title = NULL; mpv_node metadata; gmpv_mpv_get_property( mpv, "duration", MPV_FORMAT_DOUBLE, &entry->duration ); gmpv_mpv_get_property( mpv, "playlist-pos", MPV_FORMAT_INT64, &playlist_pos ); gmpv_mpv_get_property( mpv, "playlist-count", MPV_FORMAT_INT64, &playlist_count ); gmpv_mpv_get_property( mpv, "media-title", MPV_FORMAT_STRING, &media_title ); gmpv_mpv_get_property( mpv, "metadata", MPV_FORMAT_NODE, &metadata ); if(!entry->title) { entry->title = g_strdup(media_title); } metadata_to_ptr_array(metadata, entry->tags); gmpv_mpv_command(mpv, cmd); g_signal_emit_by_name(cache, "update", path); mpv_free(media_title); mpv_free_node_contents(&metadata); } mpv_free(path); } else if(event_id == MPV_EVENT_END_FILE) { mpv_event_end_file *event = event_data; if(event->reason == MPV_END_FILE_REASON_ERROR) { g_debug("Failed to fetch metadata"); } } } static void shutdown_handler(GmpvMpv *mpv, gpointer data) { GmpvMetadataCache *cache = data; g_clear_object(&cache->fetcher); if(!g_queue_is_empty(cache->fetch_queue)) { g_idle_add((GSourceFunc)fetch_metadata, cache); } } static gboolean fetch_metadata(GmpvMetadataCache *cache) { g_assert(!cache->fetcher); cache->fetcher = gmpv_mpv_new(0); g_signal_connect( cache->fetcher, "mpv-event-notify", G_CALLBACK(mpv_event_notify), cache ); g_signal_connect( cache->fetcher, "shutdown", G_CALLBACK(shutdown_handler), cache ); gmpv_mpv_set_option_string(cache->fetcher, "ao", "null"); gmpv_mpv_set_option_string(cache->fetcher, "vo", "null"); gmpv_mpv_set_option_string(cache->fetcher, "idle", "once"); gmpv_mpv_set_option_string(cache->fetcher, "ytdl", "yes"); gmpv_mpv_initialize(cache->fetcher); for( gchar *uri = g_queue_pop_tail(cache->fetch_queue); uri; uri = g_queue_pop_tail(cache->fetch_queue) ) { g_debug("Queuing %s for metadata fetch", uri); gmpv_mpv_load_file(cache->fetcher, uri, TRUE); g_free(uri); } return G_SOURCE_REMOVE; } static void gmpv_metadata_cache_class_init(GmpvMetadataCacheClass *klass) { GObjectClass *object_class = G_OBJECT_CLASS(klass); object_class->dispose = dispose; object_class->finalize = finalize; g_signal_new( "update", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__STRING, G_TYPE_NONE, 1, G_TYPE_STRING ); } static void gmpv_metadata_cache_init(GmpvMetadataCache *cache) { cache->table = g_hash_table_new_full( g_str_hash, g_str_equal, g_free, (GDestroyNotify) gmpv_metadata_cache_entry_free ); cache->fetcher = NULL; cache->fetch_queue = g_queue_new(); } GmpvMetadataCache *gmpv_metadata_cache_new(void) { return g_object_new(gmpv_metadata_cache_get_type(), NULL); } void gmpv_metadata_cache_ref_entry(GmpvMetadataCache *cache, const gchar *uri) { gmpv_metadata_cache_lookup(cache, uri)->references++; } void gmpv_metadata_cache_unref_entry(GmpvMetadataCache *cache, const gchar *uri) { GmpvMetadataCacheEntry *entry = g_hash_table_lookup(cache->table, uri); if(entry && --entry->references == 0) { g_hash_table_remove(cache->table, uri); } } void gmpv_metadata_cache_load_playlist( GmpvMetadataCache *cache, const GPtrArray *playlist ) { GmpvMetadataCacheEntry *entry = NULL; GHashTableIter iter; g_hash_table_iter_init(&iter, cache->table); /* First, set the refrence count for all entries to zero */ while(g_hash_table_iter_next(&iter, NULL, (gpointer)&entry)) { g_assert(entry); entry->references = 0; } /* Then ref all entries in the playlist. This sets the reference count * to the number of times the entry appears in the playlist. */ for(guint i = 0; i < playlist->len; i++) { GmpvPlaylistEntry *entry = g_ptr_array_index(playlist, i); gmpv_metadata_cache_ref_entry(cache, entry->filename); } g_hash_table_iter_init(&iter, cache->table); /* Remove all entries that with refrence count of zero, which means that * the entry no longer exists in the playlist. */ while(g_hash_table_iter_next(&iter, NULL, (gpointer)&entry)) { g_assert(entry); if(entry->references == 0) { g_hash_table_iter_remove(&iter); } } } GmpvMetadataCacheEntry *gmpv_metadata_cache_lookup( GmpvMetadataCache *cache, const gchar *uri ) { GmpvMetadataCacheEntry *entry = g_hash_table_lookup(cache->table, uri); if(!entry) { entry = gmpv_metadata_cache_entry_new(); g_hash_table_insert(cache->table, g_strdup(uri), entry); if(!cache->fetcher && g_queue_is_empty(cache->fetch_queue)) { g_idle_add((GSourceFunc)fetch_metadata, cache); } g_queue_push_head(cache->fetch_queue, g_strdup(uri)); } return entry; } gnome-mpv-0.13/src/gmpv_metadata_cache.h000066400000000000000000000030471317030365200202420ustar00rootroot00000000000000/* * Copyright (c) 2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef METADATA_CACHE #define METADATA_CACHE #include G_BEGIN_DECLS typedef struct _GmpvMetadataCacheEntry GmpvMetadataCacheEntry; struct _GmpvMetadataCacheEntry { gint references; gchar *title; gdouble duration; GPtrArray *tags; }; #define GMPV_TYPE_METADATA_CACHE (gmpv_metadata_cache_get_type()) G_DECLARE_FINAL_TYPE(GmpvMetadataCache, gmpv_metadata_cache, GMPV, METADATA_CACHE, GObject) GmpvMetadataCache *gmpv_metadata_cache_new(void); void gmpv_metadata_cache_ref_entry(GmpvMetadataCache *cache, const gchar *uri); void gmpv_metadata_cache_unref_entry(GmpvMetadataCache *cache, const gchar *uri); void gmpv_metadata_cache_load_playlist( GmpvMetadataCache *cache, const GPtrArray *playlist ); GmpvMetadataCacheEntry *gmpv_metadata_cache_lookup( GmpvMetadataCache *cache, const gchar *uri ); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_model.c000066400000000000000000000614751317030365200164430ustar00rootroot00000000000000/* * Copyright (c) 2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include "gmpv_model.h" #include "gmpv_marshal.h" #include "gmpv_player.h" #include "gmpv_mpv_wrapper.h" #include "gmpv_metadata_cache.h" enum { PROP_INVALID, PROP_MPV, PROP_READY, PROP_PLAYLIST, PROP_METADATA, PROP_TRACK_LIST, PROP_AID, PROP_VID, PROP_SID, PROP_CHAPTERS, PROP_CORE_IDLE, PROP_IDLE_ACTIVE, PROP_FULLSCREEN, PROP_PAUSE, PROP_LOOP_PLAYLIST, PROP_DURATION, PROP_MEDIA_TITLE, PROP_PLAYLIST_COUNT, PROP_PLAYLIST_POS, PROP_SPEED, PROP_VOLUME, N_PROPERTIES }; struct _GmpvModel { GObject parent; GmpvPlayer *player; gboolean ready; GmpvMetadataCache *cache; GPtrArray *playlist; GPtrArray *metadata; GPtrArray *track_list; gboolean update_mpv_properties; gchar *aid; gchar *vid; gchar *sid; gint64 chapters; gboolean core_idle; gboolean idle_active; gboolean fullscreen; gboolean pause; gchar *loop_playlist; gdouble duration; gchar *media_title; gint64 playlist_count; gint64 playlist_pos; gdouble speed; gdouble volume; }; struct _GmpvModelClass { GObjectClass parent_class; }; static void constructed(GObject *object); static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ); static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ); static void dispose(GObject *object); static void finalize(GObject *object); static void set_mpv_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ); static void g_value_set_by_type(GValue *gvalue, GType type, gpointer value); static GParamSpec *g_param_spec_by_type( const gchar *name, const gchar *nick, const gchar *blurb, GType type, GParamFlags flags ); static gboolean emit_frame_ready(gpointer data); static void opengl_cb_update_callback(gpointer opengl_cb_ctx); static void metadata_update_handler( GmpvPlayer *player, gint64 pos, gpointer data ); static void window_resize_handler( GmpvMpv *mpv, gint64 width, gint64 height, gpointer data ); static void window_move_handler( GmpvMpv *mpv, gboolean flip_x, gboolean flip_y, GValue *x, GValue *y, gpointer data ); static void mpv_prop_change_handler( GmpvMpv *mpv, const gchar *name, gpointer value, gpointer data ); static void error_handler(GmpvMpv *mpv, const gchar* message, gpointer data); static void message_handler(GmpvMpv *mpv, const gchar* message, gpointer data); static void shutdown_handler(GmpvMpv *mpv, gpointer data); G_DEFINE_TYPE(GmpvModel, gmpv_model, G_TYPE_OBJECT) static void constructed(GObject *object) { GmpvModel *model = GMPV_MODEL(object); g_assert(model->player); g_object_bind_property( model->player, "ready", model, "ready", G_BINDING_DEFAULT ); g_object_bind_property( model->player, "playlist", model, "playlist", G_BINDING_DEFAULT|G_BINDING_SYNC_CREATE ); g_object_bind_property( model->player, "metadata", model, "metadata", G_BINDING_DEFAULT|G_BINDING_SYNC_CREATE ); g_object_bind_property( model->player, "track-list", model, "track-list", G_BINDING_DEFAULT|G_BINDING_SYNC_CREATE ); g_signal_connect( model->player, "metadata-update", G_CALLBACK(metadata_update_handler), model ); g_signal_connect( model->player, "window-resize", G_CALLBACK(window_resize_handler), model ); g_signal_connect( model->player, "window-move", G_CALLBACK(window_move_handler), model ); g_signal_connect( model->player, "mpv-property-changed", G_CALLBACK(mpv_prop_change_handler), model ); g_signal_connect( model->player, "error", G_CALLBACK(error_handler), model ); g_signal_connect( model->player, "message", G_CALLBACK(message_handler), model ); g_signal_connect( model->player, "shutdown", G_CALLBACK(shutdown_handler), model ); G_OBJECT_CLASS(gmpv_model_parent_class)->constructed(object); } static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ) { GmpvModel *self = GMPV_MODEL(object); switch(property_id) { case PROP_MPV: self->player = g_value_get_pointer(value); break; case PROP_READY: self->ready = g_value_get_boolean(value); break; case PROP_PLAYLIST: self->playlist = g_value_get_pointer(value); break; case PROP_METADATA: self->metadata = g_value_get_pointer(value); break; case PROP_TRACK_LIST: self->track_list = g_value_get_pointer(value); break; case PROP_AID: g_free(self->aid); self->aid = g_value_dup_string(value); break; case PROP_VID: g_free(self->vid); self->vid = g_value_dup_string(value); break; case PROP_SID: g_free(self->sid); self->sid = g_value_dup_string(value); break; case PROP_CHAPTERS: self->chapters = g_value_get_int64(value); break; case PROP_CORE_IDLE: self->core_idle = g_value_get_boolean(value); break; case PROP_IDLE_ACTIVE: self->idle_active = g_value_get_boolean(value); break; case PROP_FULLSCREEN: self->fullscreen = g_value_get_boolean(value); break; case PROP_PAUSE: self->pause = g_value_get_boolean(value); break; case PROP_LOOP_PLAYLIST: self->loop_playlist = g_value_dup_string(value); break; case PROP_DURATION: self->duration = g_value_get_double(value); break; case PROP_MEDIA_TITLE: g_free(self->media_title); self->media_title = g_value_dup_string(value); break; case PROP_PLAYLIST_COUNT: self->playlist_count = g_value_get_int64(value); break; case PROP_PLAYLIST_POS: self->playlist_pos = g_value_get_int64(value); break; case PROP_SPEED: self->speed = g_value_get_double(value); break; case PROP_VOLUME: self->volume = g_value_get_double(value); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } /* Do not propagate changes from mpv back to itself */ if(self->update_mpv_properties) { set_mpv_property(object, property_id, value, pspec); } } static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ) { GmpvModel *self = GMPV_MODEL(object); switch(property_id) { case PROP_MPV: g_value_set_pointer(value, self->player); break; case PROP_READY: g_value_set_boolean(value, self->ready); break; case PROP_PLAYLIST: g_value_set_pointer(value, self->playlist); break; case PROP_METADATA: g_value_set_pointer(value, self->metadata); break; case PROP_TRACK_LIST: g_value_set_pointer(value, self->track_list); break; case PROP_AID: g_value_set_string(value, self->aid); break; case PROP_VID: g_value_set_string(value, self->vid); break; case PROP_SID: g_value_set_string(value, self->sid); break; case PROP_CHAPTERS: g_value_set_int64(value, self->chapters); break; case PROP_CORE_IDLE: g_value_set_boolean(value, self->core_idle); break; case PROP_IDLE_ACTIVE: g_value_set_boolean(value, self->idle_active); break; case PROP_FULLSCREEN: g_value_set_boolean(value, self->fullscreen); break; case PROP_PAUSE: g_value_set_boolean(value, self->pause); break; case PROP_LOOP_PLAYLIST: g_value_set_string(value, self->loop_playlist); break; case PROP_DURATION: g_value_set_double(value, self->duration); break; case PROP_MEDIA_TITLE: g_value_set_string(value, self->media_title); break; case PROP_PLAYLIST_COUNT: g_value_set_int64(value, self->playlist_count); break; case PROP_PLAYLIST_POS: g_value_set_int64(value, self->idle_active?0:self->playlist_pos); break; case PROP_SPEED: g_value_set_double(value, self->speed); break; case PROP_VOLUME: g_value_set_double(value, self->volume); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void dispose(GObject *object) { GmpvModel *model = GMPV_MODEL(object); GmpvMpv *mpv = GMPV_MPV(model->player); if(mpv) { gmpv_mpv_set_opengl_cb_callback(mpv, NULL, NULL); g_clear_object(&model->player); while(g_source_remove_by_user_data(model)); } G_OBJECT_CLASS(gmpv_model_parent_class)->dispose(object); } static void finalize(GObject *object) { GmpvModel *model = GMPV_MODEL(object); g_free(model->aid); g_free(model->vid); g_free(model->sid); g_free(model->loop_playlist); g_free(model->media_title); G_OBJECT_CLASS(gmpv_model_parent_class)->finalize(object); } static void set_mpv_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ) { GmpvModel *self = GMPV_MODEL(object); GmpvMpv *mpv = GMPV_MPV(self->player); switch(property_id) { case PROP_AID: gmpv_mpv_set_property( mpv, "aid", MPV_FORMAT_STRING, &self->aid ); break; case PROP_VID: gmpv_mpv_set_property( mpv, "vid", MPV_FORMAT_STRING, &self->vid ); break; case PROP_SID: gmpv_mpv_set_property( mpv, "sid", MPV_FORMAT_STRING, &self->sid ); break; case PROP_FULLSCREEN: gmpv_mpv_set_property( mpv, "fullscreen", MPV_FORMAT_FLAG, &self->fullscreen ); break; case PROP_PAUSE: gmpv_mpv_set_property( mpv, "pause", MPV_FORMAT_FLAG, &self->pause ); break; case PROP_LOOP_PLAYLIST: gmpv_mpv_set_property( mpv, "loop-playlist", MPV_FORMAT_STRING, &self->loop_playlist ); break; case PROP_MEDIA_TITLE: gmpv_mpv_set_property( mpv, "media-title", MPV_FORMAT_INT64, &self->media_title ); break; case PROP_PLAYLIST_POS: gmpv_mpv_set_property( mpv, "playlist-pos", MPV_FORMAT_INT64, &self->playlist_pos ); break; case PROP_SPEED: gmpv_mpv_set_property( mpv, "speed", MPV_FORMAT_DOUBLE, &self->speed ); break; case PROP_VOLUME: gmpv_mpv_set_property( mpv, "volume", MPV_FORMAT_DOUBLE, &self->volume ); break; } } static void g_value_set_by_type(GValue *gvalue, GType type, gpointer value) { g_value_unset(gvalue); g_value_init(gvalue, type); switch(type) { case G_TYPE_STRING: g_value_set_string(gvalue, *((const gchar **)value)); break; case G_TYPE_BOOLEAN: g_value_set_boolean(gvalue, *((gboolean *)value)); break; case G_TYPE_INT64: g_value_set_int64(gvalue, *((gint64 *)value)); break; case G_TYPE_DOUBLE: g_value_set_double(gvalue, *((gdouble *)value)); break; case G_TYPE_POINTER: g_value_set_pointer(gvalue, *((gpointer *)value)); break; default: g_assert_not_reached(); break; } } static GParamSpec *g_param_spec_by_type( const gchar *name, const gchar *nick, const gchar *blurb, GType type, GParamFlags flags ) { GParamSpec *result = NULL; switch(type) { case G_TYPE_STRING: result = g_param_spec_string(name, nick, blurb, NULL, flags); break; case G_TYPE_BOOLEAN: result = g_param_spec_boolean(name, nick, blurb, FALSE, flags); break; case G_TYPE_INT64: result = g_param_spec_int64( name, nick, blurb, G_MININT64, G_MAXINT64, 0, flags ); break; case G_TYPE_DOUBLE: result = g_param_spec_double( name, nick, blurb, -G_MAXDOUBLE, G_MAXDOUBLE, 0.0, flags ); break; case G_TYPE_POINTER: result = g_param_spec_pointer(name, nick, blurb, flags); break; default: g_assert_not_reached(); break; } return result; } static gboolean emit_frame_ready(gpointer data) { g_signal_emit_by_name(data, "frame-ready"); return FALSE; } static void opengl_cb_update_callback(gpointer data) { g_idle_add_full( G_PRIORITY_HIGH, emit_frame_ready, data, NULL ); } static void metadata_update_handler( GmpvPlayer *player, gint64 pos, gpointer data ) { g_signal_emit_by_name(data, "metadata-update", pos); } static void window_resize_handler( GmpvMpv *mpv, gint64 width, gint64 height, gpointer data ) { g_signal_emit_by_name(data, "window-resize", width, height); } static void window_move_handler( GmpvMpv *mpv, gboolean flip_x, gboolean flip_y, GValue *x, GValue *y, gpointer data ) { g_signal_emit_by_name(data, "window-move", flip_x, flip_y, x, y); } static void mpv_prop_change_handler( GmpvMpv *mpv, const gchar *name, gpointer value, gpointer data ) { if( g_strcmp0(name, "playlist") != 0 && g_strcmp0(name, "metadata") != 0 && g_strcmp0(name, "track-list") != 0 ) { GObjectClass *klass; GParamSpec *pspec; GValue gvalue = G_VALUE_INIT; klass = G_TYPE_INSTANCE_GET_CLASS (data, GMPV_TYPE_MODEL, GObjectClass); pspec = g_object_class_find_property(klass, name); if(pspec && value) { GMPV_MODEL(data)->update_mpv_properties = FALSE; g_value_set_by_type(&gvalue, pspec->value_type, value); g_object_set_property(data, name, &gvalue); GMPV_MODEL(data)->update_mpv_properties = TRUE; } } } static void error_handler(GmpvMpv *mpv, const gchar *message, gpointer data) { g_signal_emit_by_name(data, "error", message); } static void message_handler(GmpvMpv *mpv, const gchar* message, gpointer data) { g_signal_emit_by_name(data, "message", message); } static void shutdown_handler(GmpvMpv *mpv, gpointer data) { g_signal_emit_by_name(data, "shutdown"); } static void gmpv_model_class_init(GmpvModelClass *klass) { /* The "no" value of aid, vid, and sid cannot be represented with an * int64, so we need to observe them as string to receive notifications * for all possible values. */ const struct { const gchar *name; guint id; GType type; } mpv_props[] = { {"aid", PROP_AID, G_TYPE_STRING}, {"vid", PROP_VID, G_TYPE_STRING}, {"sid", PROP_SID, G_TYPE_STRING}, {"chapters", PROP_CHAPTERS, G_TYPE_INT64}, {"core-idle", PROP_CORE_IDLE, G_TYPE_BOOLEAN}, {"idle-active", PROP_IDLE_ACTIVE, G_TYPE_BOOLEAN}, {"fullscreen", PROP_FULLSCREEN, G_TYPE_BOOLEAN}, {"pause", PROP_PAUSE, G_TYPE_BOOLEAN}, {"loop-playlist", PROP_LOOP_PLAYLIST, G_TYPE_STRING}, {"duration", PROP_DURATION, G_TYPE_DOUBLE}, {"media-title", PROP_MEDIA_TITLE, G_TYPE_STRING}, {"playlist-count", PROP_PLAYLIST_COUNT, G_TYPE_INT64}, {"playlist-pos", PROP_PLAYLIST_POS, G_TYPE_INT64}, {"speed", PROP_SPEED, G_TYPE_DOUBLE}, {"volume", PROP_VOLUME, G_TYPE_DOUBLE}, {NULL, PROP_INVALID, 0} }; GObjectClass *obj_class = G_OBJECT_CLASS(klass); GParamSpec *pspec = NULL; obj_class->constructed = constructed; obj_class->set_property = set_property; obj_class->get_property = get_property; obj_class->dispose = dispose; obj_class->finalize = finalize; pspec = g_param_spec_pointer ( "mpv", "mpv", "GmpvMpv instance to use", G_PARAM_CONSTRUCT_ONLY|G_PARAM_READWRITE ); g_object_class_install_property(obj_class, PROP_MPV, pspec); pspec = g_param_spec_boolean ( "ready", "Ready", "Whether mpv is ready to receive commands", FALSE, G_PARAM_READWRITE ); g_object_class_install_property(obj_class, PROP_READY, pspec); pspec = g_param_spec_pointer ( "playlist", "playlist", "The playlist", G_PARAM_READWRITE ); g_object_class_install_property(obj_class, PROP_PLAYLIST, pspec); pspec = g_param_spec_pointer ( "metadata", "metadata", "Metadata tags of the current file", G_PARAM_READWRITE ); g_object_class_install_property(obj_class, PROP_METADATA, pspec); pspec = g_param_spec_pointer ( "track-list", "track-list", "Audio, video, and subtitle tracks of the current file", G_PARAM_READWRITE ); g_object_class_install_property(obj_class, PROP_TRACK_LIST, pspec); for(int i = 0; mpv_props[i].name; i++) { pspec = g_param_spec_by_type( mpv_props[i].name, mpv_props[i].name, mpv_props[i].name, mpv_props[i].type, G_PARAM_READWRITE ); g_object_class_install_property (obj_class, mpv_props[i].id, pspec); } g_signal_new( "playback-restart", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__VOID, G_TYPE_NONE, 0 ); g_signal_new( "frame-ready", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__VOID, G_TYPE_NONE, 0 ); g_signal_new( "metadata-update", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_gen_marshal_VOID__INT64, G_TYPE_NONE, 1, G_TYPE_INT64 ); g_signal_new( "window-resize", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_gen_marshal_VOID__INT64_INT64, G_TYPE_NONE, 2, G_TYPE_INT64, G_TYPE_INT64 ); g_signal_new( "window-move", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_gen_marshal_VOID__BOOLEAN_BOOLEAN_POINTER_POINTER, G_TYPE_NONE, 4, G_TYPE_BOOLEAN, G_TYPE_BOOLEAN, G_TYPE_POINTER, G_TYPE_POINTER ); g_signal_new( "message", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__STRING, G_TYPE_NONE, 1, G_TYPE_STRING ); g_signal_new( "error", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__STRING, G_TYPE_NONE, 1, G_TYPE_STRING ); g_signal_new( "shutdown", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__VOID, G_TYPE_NONE, 0 ); } static void gmpv_model_init(GmpvModel *model) { model->player = NULL; model->ready = FALSE; model->cache = NULL; model->playlist = NULL; model->metadata = NULL; model->track_list = NULL; model->update_mpv_properties = TRUE; model->aid = NULL; model->vid = NULL; model->sid = NULL; model->chapters = 0; model->core_idle = FALSE; model->idle_active = FALSE; model->fullscreen = FALSE; model->pause = TRUE; model->loop_playlist = NULL; model->duration = 0.0; model->media_title = NULL; model->playlist_count = 0; model->playlist_pos = 0; model->speed = 1.0; model->volume = 1.0; } GmpvModel *gmpv_model_new(gint64 wid) { return GMPV_MODEL(g_object_new( gmpv_model_get_type(), "mpv", gmpv_player_new(wid), NULL )); } void gmpv_model_initialize(GmpvModel *model) { GmpvMpv *mpv = GMPV_MPV(model->player); gmpv_mpv_initialize(mpv); gmpv_mpv_set_opengl_cb_callback(mpv, opengl_cb_update_callback, model); } void gmpv_model_reset(GmpvModel *model) { model->ready = FALSE; g_object_notify(G_OBJECT(model), "ready"); gmpv_mpv_reset(GMPV_MPV(model->player)); } void gmpv_model_quit(GmpvModel *model) { if(model->ready) { model->ready = FALSE; g_object_notify(G_OBJECT(model), "ready"); gmpv_mpv_quit(GMPV_MPV(model->player)); } } void gmpv_model_mouse(GmpvModel *model, gint x, gint y) { gchar *x_str = g_strdup_printf("%d", x); gchar *y_str = g_strdup_printf("%d", y); const gchar *cmd[] = {"mouse", x_str, y_str, NULL}; g_debug("Set mouse location to (%s, %s)", x_str, y_str); gmpv_mpv_command(GMPV_MPV(model->player), cmd); g_free(x_str); g_free(y_str); } void gmpv_model_key_down(GmpvModel *model, const gchar* keystr) { const gchar *cmd[] = {"keydown", keystr, NULL}; g_debug("Sent '%s' key down to mpv", keystr); gmpv_mpv_command(GMPV_MPV(model->player), cmd); } void gmpv_model_key_up(GmpvModel *model, const gchar* keystr) { const gchar *cmd[] = {"keyup", keystr, NULL}; g_debug("Sent '%s' key up to mpv", keystr); gmpv_mpv_command(GMPV_MPV(model->player), cmd); } void gmpv_model_key_press(GmpvModel *model, const gchar* keystr) { const gchar *cmd[] = {"keypress", keystr, NULL}; g_debug("Sent '%s' key press to mpv", keystr); gmpv_mpv_command(GMPV_MPV(model->player), cmd); } void gmpv_model_reset_keys(GmpvModel *model) { g_debug("Sent global key up to mpv"); gmpv_mpv_command_string(GMPV_MPV(model->player), "keyup"); } void gmpv_model_play(GmpvModel *model) { gmpv_mpv_set_property_flag(GMPV_MPV(model->player), "pause", FALSE); } void gmpv_model_pause(GmpvModel *model) { gmpv_mpv_set_property_flag(GMPV_MPV(model->player), "pause", TRUE); } void gmpv_model_stop(GmpvModel *model) { const gchar *cmd[] = {"stop", NULL}; gmpv_mpv_command(GMPV_MPV(model->player), cmd); } void gmpv_model_forward(GmpvModel *model) { const gchar *cmd[] = {"seek", "10", NULL}; gmpv_mpv_command(GMPV_MPV(model->player), cmd); } void gmpv_model_rewind(GmpvModel *model) { const gchar *cmd[] = {"seek", "-10", NULL}; gmpv_mpv_command(GMPV_MPV(model->player), cmd); } void gmpv_model_next_chapter(GmpvModel *model) { const gchar *cmd[] = {"osd-msg", "cycle", "chapter", NULL}; gmpv_mpv_command(GMPV_MPV(model->player), cmd); } void gmpv_model_previous_chapter(GmpvModel *model) { const gchar *cmd[] = {"osd-msg", "cycle", "chapter", "down", NULL}; gmpv_mpv_command(GMPV_MPV(model->player), cmd); } void gmpv_model_next_playlist_entry(GmpvModel *model) { const gchar *cmd[] = {"osd-msg", "playlist-next", "weak", NULL}; gmpv_mpv_command(GMPV_MPV(model->player), cmd); } void gmpv_model_previous_playlist_entry(GmpvModel *model) { const gchar *cmd[] = {"osd-msg", "playlist-prev", "weak", NULL}; gmpv_mpv_command(GMPV_MPV(model->player), cmd); } void gmpv_model_shuffle_playlist(GmpvModel *model) { const gchar *cmd[] = {"osd-msg", "playlist-shuffle", NULL}; gmpv_mpv_command(GMPV_MPV(model->player), cmd); } void gmpv_model_seek(GmpvModel *model, gdouble value) { gmpv_mpv_set_property(GMPV_MPV(model->player), "time-pos", MPV_FORMAT_DOUBLE, &value); } void gmpv_model_seek_offset(GmpvModel *model, gdouble offset) { const gchar *cmd[] = {"seek", NULL, NULL}; gchar buf[G_ASCII_DTOSTR_BUF_SIZE]; g_ascii_dtostr(buf, G_ASCII_DTOSTR_BUF_SIZE, offset); cmd[1] = buf; gmpv_mpv_command(GMPV_MPV(model->player), cmd); } void gmpv_model_load_audio_track(GmpvModel *model, const gchar *filename) { gmpv_mpv_load_track (GMPV_MPV(model->player), filename, TRACK_TYPE_AUDIO); } void gmpv_model_load_subtitle_track(GmpvModel *model, const gchar *filename) { gmpv_mpv_load_track (GMPV_MPV(model->player), filename, TRACK_TYPE_SUBTITLE); } gdouble gmpv_model_get_time_position(GmpvModel *model) { gdouble time_pos = 0.0; if(!model->idle_active) { gmpv_mpv_get_property( GMPV_MPV(model->player), "time-pos", MPV_FORMAT_DOUBLE, &time_pos ); } /* time-pos may become negative during seeks */ return MAX(0, time_pos); } void gmpv_model_set_playlist_position(GmpvModel *model, gint64 position) { if(position != model->playlist_pos) { gmpv_mpv_set_property( GMPV_MPV(model->player), "playlist-pos", MPV_FORMAT_INT64, &position ); } } void gmpv_model_remove_playlist_entry(GmpvModel *model, gint64 position) { const gchar *cmd[] = {"playlist_remove", NULL, NULL}; gchar *index_str = g_strdup_printf("%" G_GINT64_FORMAT, position); cmd[1] = index_str; gmpv_mpv_command(GMPV_MPV(model->player), cmd); g_free(index_str); } void gmpv_model_move_playlist_entry(GmpvModel *model, gint64 src, gint64 dst) { const gchar *cmd[] = {"playlist_move", NULL, NULL, NULL}; gchar *src_str = g_strdup_printf ("%" G_GINT64_FORMAT, (src > dst)?--src:src); gchar *dst_str = g_strdup_printf ("%" G_GINT64_FORMAT, dst); cmd[1] = src_str; cmd[2] = dst_str; gmpv_mpv_command(GMPV_MPV(model->player), cmd); g_free(src_str); g_free(dst_str); } void gmpv_model_load_file(GmpvModel *model, const gchar *uri, gboolean append) { gmpv_mpv_load(GMPV_MPV(model->player), uri, append); /* Start playing when replacing the playlist, ie. not appending, or * adding the first file to the playlist. */ if(!append || model->playlist->len == 1) { gmpv_model_play(model); } } gboolean gmpv_model_get_use_opengl_cb(GmpvModel *model) { return gmpv_mpv_get_use_opengl_cb(GMPV_MPV(model->player)); } void gmpv_model_initialize_gl(GmpvModel *model) { gmpv_mpv_init_gl(GMPV_MPV(model->player)); } void gmpv_model_render_frame(GmpvModel *model, gint width, gint height) { mpv_opengl_cb_context *opengl_ctx; opengl_ctx = gmpv_mpv_get_opengl_cb_context(GMPV_MPV(model->player)); if(opengl_ctx) { int fbo = -1; glGetIntegerv(GL_FRAMEBUFFER_BINDING, &fbo); mpv_opengl_cb_draw(opengl_ctx, fbo, width, (-1)*height); } } void gmpv_model_get_video_geometry( GmpvModel *model, gint64 *width, gint64 *height ) { GmpvMpv *mpv = GMPV_MPV(model->player); gmpv_mpv_get_property(mpv, "dwidth", MPV_FORMAT_INT64, width); gmpv_mpv_get_property(mpv, "dheight", MPV_FORMAT_INT64, height); } gchar *gmpv_model_get_current_path(GmpvModel *model) { GmpvMpv *mpv = GMPV_MPV(model->player); gchar *path = gmpv_mpv_get_property_string(mpv, "path"); gchar *buf = g_strdup(path); mpv_free(path); return buf; } gnome-mpv-0.13/src/gmpv_model.h000066400000000000000000000054341317030365200164410ustar00rootroot00000000000000/* * Copyright (c) 2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef MODEL_H #define MODEL_H #include #include "gmpv_mpv.h" G_BEGIN_DECLS #define GMPV_TYPE_MODEL (gmpv_model_get_type()) G_DECLARE_FINAL_TYPE(GmpvModel, gmpv_model, GMPV, MODEL, GObject) GmpvModel *gmpv_model_new(gint64 wid); void gmpv_model_initialize(GmpvModel *model); void gmpv_model_reset(GmpvModel *model); void gmpv_model_quit(GmpvModel *model); void gmpv_model_mouse(GmpvModel *model, gint x, gint y); void gmpv_model_key_down(GmpvModel *model, const gchar* keystr); void gmpv_model_key_up(GmpvModel *model, const gchar* keystr); void gmpv_model_key_press(GmpvModel *model, const gchar* keystr); void gmpv_model_reset_keys(GmpvModel *model); void gmpv_model_play(GmpvModel *model); void gmpv_model_pause(GmpvModel *model); void gmpv_model_stop(GmpvModel *model); void gmpv_model_forward(GmpvModel *model); void gmpv_model_rewind(GmpvModel *model); void gmpv_model_next_chapter(GmpvModel *model); void gmpv_model_previous_chapter(GmpvModel *model); void gmpv_model_next_playlist_entry(GmpvModel *model); void gmpv_model_previous_playlist_entry(GmpvModel *model); void gmpv_model_shuffle_playlist(GmpvModel *model); void gmpv_model_seek(GmpvModel *model, gdouble value); void gmpv_model_seek_offset(GmpvModel *model, gdouble offset); void gmpv_model_load_audio_track(GmpvModel *model, const gchar *filename); void gmpv_model_load_subtitle_track(GmpvModel *model, const gchar *filename); gdouble gmpv_model_get_time_position(GmpvModel *model); void gmpv_model_set_playlist_position(GmpvModel *model, gint64 position); void gmpv_model_remove_playlist_entry(GmpvModel *model, gint64 position); void gmpv_model_move_playlist_entry(GmpvModel *model, gint64 src, gint64 dst); void gmpv_model_load_file(GmpvModel *model, const gchar *uri, gboolean append); gboolean gmpv_model_get_use_opengl_cb(GmpvModel *model); void gmpv_model_initialize_gl(GmpvModel *model); void gmpv_model_render_frame(GmpvModel *model, gint width, gint height); void gmpv_model_get_video_geometry( GmpvModel *model, gint64 *width, gint64 *height ); gchar *gmpv_model_get_current_path(GmpvModel *model); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_mpv.c000066400000000000000000000345131317030365200161360ustar00rootroot00000000000000/* * Copyright (c) 2014-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include #include #include #include #include #include #include #ifdef GDK_WINDOWING_X11 #include #include #endif #ifdef GDK_WINDOWING_WAYLAND #include #include #endif #ifdef GDK_WINDOWING_WIN32 #include #include #endif #include "gmpv_mpv.h" #include "gmpv_mpv_private.h" #include "gmpv_mpv_wrapper.h" #include "gmpv_common.h" #include "gmpv_def.h" #include "gmpv_marshal.h" static void *GLAPIENTRY glMPGetNativeDisplay(const gchar *name); static void *get_proc_address(void *fn_ctx, const gchar *name); static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ); static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ); static void dispose(GObject *object); static void finalize(GObject *object); static void wakeup_callback(void *data); static void mpv_property_changed( GmpvMpv *mpv, const gchar *name, gpointer value ); static void mpv_log_message( GmpvMpv *mpv, mpv_log_level log_level, const gchar *prefix, const gchar *text ); static void mpv_event_notify(GmpvMpv *mpv, gint event_id, gpointer event_data); static gboolean process_mpv_events(gpointer data); static void initialize(GmpvMpv *mpv); static void load_file(GmpvMpv *mpv, const gchar *uri, gboolean append); static void reset(GmpvMpv *mpv); G_DEFINE_TYPE_WITH_PRIVATE(GmpvMpv, gmpv_mpv, G_TYPE_OBJECT) static void *GLAPIENTRY glMPGetNativeDisplay(const gchar *name) { GdkDisplay *display = gdk_display_get_default(); #ifdef GDK_WINDOWING_WAYLAND if(GDK_IS_WAYLAND_DISPLAY(display) && g_strcmp0(name, "wl") == 0) return gdk_wayland_display_get_wl_display(display); #endif #ifdef GDK_WINDOWING_X11 if(GDK_IS_X11_DISPLAY(display) && g_strcmp0(name, "x11") == 0) return gdk_x11_display_get_xdisplay(display); #endif return NULL; } static void *get_proc_address(void *fn_ctx, const gchar *name) { GdkDisplay *display = gdk_display_get_default(); if(g_strcmp0(name, "glMPGetNativeDisplay") == 0) return glMPGetNativeDisplay; #ifdef GDK_WINDOWING_WAYLAND if (GDK_IS_WAYLAND_DISPLAY(display)) return eglGetProcAddress(name); #endif #ifdef GDK_WINDOWING_X11 if (GDK_IS_X11_DISPLAY(display)) return (void *)(intptr_t) glXGetProcAddressARB((const GLubyte *)name); #endif #ifdef GDK_WINDOWING_WIN32 if (GDK_IS_WIN32_DISPLAY(display)) return wglGetProcAddress(name); #endif g_assert_not_reached(); } static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ) { GmpvMpvPrivate *priv = get_private(GMPV_MPV(object)); if(property_id == PROP_WID) { priv->wid = g_value_get_int64(value); } else if(property_id == PROP_READY) { priv->ready = g_value_get_boolean(value); } else { G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); } } static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ) { GmpvMpvPrivate *priv = get_private(GMPV_MPV(object)); if(property_id == PROP_WID) { g_value_set_int64(value, priv->wid); } else if(property_id == PROP_READY) { g_value_set_boolean(value, priv->ready); } else { G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); } } static void dispose(GObject *object) { GmpvMpv *mpv = GMPV_MPV(object); if(get_private(mpv)->mpv_ctx) { gmpv_mpv_quit(mpv); while(g_source_remove_by_user_data(object)); } G_OBJECT_CLASS(gmpv_mpv_parent_class)->dispose(object); } static void finalize(GObject *object) { G_OBJECT_CLASS(gmpv_mpv_parent_class)->finalize(object); } static void wakeup_callback(void *data) { g_idle_add_full(G_PRIORITY_HIGH_IDLE, process_mpv_events, data, NULL); } static void mpv_property_changed( GmpvMpv *mpv, const gchar *name, gpointer value ) { g_debug("Received mpv property change event for \"%s\"", name); } static void mpv_event_notify(GmpvMpv *mpv, gint event_id, gpointer event_data) { if(event_id == MPV_EVENT_PROPERTY_CHANGE) { mpv_event_property *prop = event_data; g_signal_emit_by_name( mpv, "mpv-property-changed", prop->name, prop->data ); } else if(event_id == MPV_EVENT_IDLE) { gmpv_mpv_set_property_flag(mpv, "pause", TRUE); } else if(event_id == MPV_EVENT_END_FILE) { mpv_event_end_file *ef_event = event_data; if(ef_event->reason == MPV_END_FILE_REASON_ERROR) { const gchar *err; gchar *msg; err = mpv_error_string(ef_event->error); msg = g_strdup_printf ( _("Playback was terminated " "abnormally. Reason: %s."), err ); gmpv_mpv_set_property_flag(mpv, "pause", TRUE); g_signal_emit_by_name(mpv, "error", msg); g_free(msg); } } else if(event_id == MPV_EVENT_LOG_MESSAGE) { mpv_event_log_message* message = event_data; g_signal_emit_by_name( mpv, "mpv-log-message", message->log_level, message->prefix, message->text ); } else if(event_id == MPV_EVENT_CLIENT_MESSAGE) { mpv_event_client_message *event_cmsg = event_data; gchar* msg = strnjoinv( " ", event_cmsg->args, (gsize)event_cmsg->num_args ); g_signal_emit_by_name(mpv, "message", msg); g_free(msg); } else if(event_id == MPV_EVENT_SHUTDOWN) { g_signal_emit_by_name(mpv, "shutdown"); } } static gboolean process_mpv_events(gpointer data) { GmpvMpv *mpv = data; GmpvMpvPrivate *priv = get_private(mpv); gboolean done = !mpv; while(!done) { mpv_event *event = priv->mpv_ctx? mpv_wait_event(priv->mpv_ctx, 0): NULL; if(event) { if( !priv->mpv_ctx || event->event_id == MPV_EVENT_SHUTDOWN || event->event_id == MPV_EVENT_NONE ) { done = TRUE; } g_signal_emit_by_name( mpv, "mpv-event-notify", event->event_id, event->data ); } else { done = TRUE; } } return FALSE; } static void initialize(GmpvMpv *mpv) { GmpvMpvPrivate *priv = get_private(mpv); gchar *current_vo = NULL; gchar *mpv_version = NULL; if(priv->wid < 0) { g_info("Forcing --vo=opengl-cb"); mpv_set_option_string(priv->mpv_ctx, "vo", "opengl-cb"); } else if(priv->wid == 0) { g_info("Forcing --vo=null"); mpv_set_option_string(priv->mpv_ctx, "vo", "null"); } else { g_debug("Attaching mpv window to wid %#x", (guint)priv->wid); mpv_set_option(priv->mpv_ctx, "wid", MPV_FORMAT_INT64, &priv->wid); } mpv_set_wakeup_callback(priv->mpv_ctx, wakeup_callback, mpv); mpv_initialize(priv->mpv_ctx); mpv_version = gmpv_mpv_get_property_string(mpv, "mpv-version"); current_vo = gmpv_mpv_get_property_string(mpv, "current-vo"); priv->use_opengl = (!current_vo && priv->wid != 0); g_info("Using %s", mpv_version); if(priv->use_opengl) { priv->opengl_ctx = mpv_get_sub_api ( priv->mpv_ctx, MPV_SUB_API_OPENGL_CB ); } priv->ready = TRUE; g_object_notify(G_OBJECT(mpv), "ready"); mpv_free(current_vo); mpv_free(mpv_version); } static void load_file(GmpvMpv *mpv, const gchar *uri, gboolean append) { GmpvMpvPrivate *priv = get_private(mpv); gchar *path = get_path_from_uri(uri); const gchar *load_cmd[] = {"loadfile", path, NULL, NULL}; gint64 playlist_count = 0; g_assert(uri); g_info( "Loading file (append=%s): %s", append?"TRUE":"FALSE", uri); mpv_get_property( priv->mpv_ctx, "playlist-count", MPV_FORMAT_INT64, &playlist_count ); load_cmd[2] = (append && playlist_count > 0)?"append":"replace"; if(!append) { gmpv_mpv_set_property_flag(mpv, "pause", FALSE); } g_assert(priv->mpv_ctx); mpv_request_event(priv->mpv_ctx, MPV_EVENT_END_FILE, 0); mpv_command(priv->mpv_ctx, load_cmd); mpv_request_event(priv->mpv_ctx, MPV_EVENT_END_FILE, 1); g_free(path); } static void reset(GmpvMpv *mpv) { GmpvMpvPrivate *priv = get_private(mpv); const gchar *quit_cmd[] = {"quit_watch_later", NULL}; gchar *loop_str; gboolean loop; gboolean pause; loop_str = gmpv_mpv_get_property_string(mpv, "loop"); loop = (g_strcmp0(loop_str, "inf") == 0); mpv_free(loop_str); /* Reset priv->mpv_ctx */ priv->ready = FALSE; g_object_notify(G_OBJECT(mpv), "ready"); gmpv_mpv_command(mpv, quit_cmd); gmpv_mpv_quit(mpv); priv->mpv_ctx = mpv_create(); gmpv_mpv_initialize(mpv); gmpv_mpv_set_opengl_cb_callback ( mpv, priv->opengl_cb_callback, priv->opengl_cb_callback_data ); gmpv_mpv_set_property_string(mpv, "loop", loop?"inf":"no"); gmpv_mpv_set_property(mpv, "pause", MPV_FORMAT_FLAG, &pause); } static void mpv_log_message( GmpvMpv *mpv, mpv_log_level log_level, const gchar *prefix, const gchar *text ) { } static void gmpv_mpv_class_init(GmpvMpvClass* klass) { GObjectClass *obj_class = G_OBJECT_CLASS(klass); GParamSpec *pspec = NULL; klass->mpv_event_notify = mpv_event_notify; klass->mpv_log_message = mpv_log_message; klass->mpv_property_changed = mpv_property_changed; klass->initialize = initialize; klass->load_file = load_file; klass->reset = reset; obj_class->set_property = set_property; obj_class->get_property = get_property; obj_class->dispose = dispose; obj_class->finalize = finalize; pspec = g_param_spec_int64 ( "wid", "WID", "The ID of the window to attach to", G_MININT64, G_MAXINT64, -1, G_PARAM_CONSTRUCT_ONLY|G_PARAM_READWRITE ); g_object_class_install_property(obj_class, PROP_WID, pspec); pspec = g_param_spec_boolean ( "ready", "Ready", "Whether mpv is initialized and ready to recieve commands", FALSE, G_PARAM_READABLE ); g_object_class_install_property(obj_class, PROP_READY, pspec); g_signal_new( "error", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__STRING, G_TYPE_NONE, 1, G_TYPE_STRING ); g_signal_new( "mpv-event-notify", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, G_STRUCT_OFFSET(GmpvMpvClass, mpv_event_notify), NULL, NULL, g_cclosure_gen_marshal_VOID__INT_POINTER, G_TYPE_NONE, 2, G_TYPE_INT, G_TYPE_POINTER ); g_signal_new( "mpv-log-message", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, G_STRUCT_OFFSET(GmpvMpvClass, mpv_log_message), NULL, NULL, g_cclosure_gen_marshal_VOID__INT_STRING_STRING, G_TYPE_NONE, 3, G_TYPE_INT, G_TYPE_STRING, G_TYPE_STRING ); g_signal_new( "mpv-property-changed", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, G_STRUCT_OFFSET(GmpvMpvClass, mpv_property_changed), NULL, NULL, g_cclosure_gen_marshal_VOID__STRING_POINTER, G_TYPE_NONE, 2, G_TYPE_STRING, G_TYPE_POINTER ); g_signal_new( "message", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__STRING, G_TYPE_NONE, 1, G_TYPE_STRING ); g_signal_new( "window-resize", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_gen_marshal_VOID__INT64_INT64, G_TYPE_NONE, 2, G_TYPE_INT64, G_TYPE_INT64 ); g_signal_new( "window-move", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_gen_marshal_VOID__BOOLEAN_BOOLEAN_POINTER_POINTER, G_TYPE_NONE, 4, G_TYPE_BOOLEAN, G_TYPE_BOOLEAN, G_TYPE_POINTER, G_TYPE_POINTER ); g_signal_new( "shutdown", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__VOID, G_TYPE_NONE, 0 ); } static void gmpv_mpv_init(GmpvMpv *mpv) { GmpvMpvPrivate *priv = get_private(mpv); priv->mpv_ctx = mpv_create(); priv->opengl_ctx = NULL; priv->ready = FALSE; priv->init_vo_config = TRUE; priv->use_opengl = FALSE; priv->wid = -1; priv->opengl_cb_callback_data = NULL; priv->opengl_cb_callback = NULL; } GmpvMpv *gmpv_mpv_new(gint64 wid) { return GMPV_MPV(g_object_new(gmpv_mpv_get_type(), "wid", wid, NULL)); } inline mpv_opengl_cb_context *gmpv_mpv_get_opengl_cb_context(GmpvMpv *mpv) { return get_private(mpv)->opengl_ctx; } inline gboolean gmpv_mpv_get_use_opengl_cb(GmpvMpv *mpv) { return get_private(mpv)->use_opengl; } void gmpv_mpv_initialize(GmpvMpv *mpv) { GMPV_MPV_GET_CLASS(mpv)->initialize(mpv); } void gmpv_mpv_init_gl(GmpvMpv *mpv) { mpv_opengl_cb_context *opengl_ctx = gmpv_mpv_get_opengl_cb_context(mpv); gint rc = mpv_opengl_cb_init_gl( opengl_ctx, "GL_MP_MPGetNativeDisplay", get_proc_address, NULL ); if(rc >= 0) { g_debug("Initialized opengl-cb"); } else { g_critical("Failed to initialize opengl-cb"); } } void gmpv_mpv_reset(GmpvMpv *mpv) { GMPV_MPV_GET_CLASS(mpv)->reset(mpv); } void gmpv_mpv_quit(GmpvMpv *mpv) { GmpvMpvPrivate *priv = get_private(mpv); g_info("Terminating mpv"); if(priv->opengl_ctx) { g_debug("Uninitializing opengl-cb"); mpv_opengl_cb_uninit_gl(priv->opengl_ctx); priv->opengl_ctx = NULL; } g_assert(priv->mpv_ctx); mpv_terminate_destroy(priv->mpv_ctx); priv->mpv_ctx = NULL; } void gmpv_mpv_load_track(GmpvMpv *mpv, const gchar *uri, TrackType type) { const gchar *cmd[3] = {NULL}; gchar *path = g_filename_from_uri(uri, NULL, NULL); if(type == TRACK_TYPE_AUDIO) { cmd[0] = "audio-add"; } else if(type == TRACK_TYPE_SUBTITLE) { cmd[0] = "sub-add"; } else { g_assert_not_reached(); } cmd[1] = path?:uri; g_debug("Loading external track %s with type %d", cmd[1], type); gmpv_mpv_command(mpv, cmd); g_free(path); } void gmpv_mpv_load_file(GmpvMpv *mpv, const gchar *uri, gboolean append) { GMPV_MPV_GET_CLASS(mpv)->load_file(mpv, uri, append); } void gmpv_mpv_load(GmpvMpv *mpv, const gchar *uri, gboolean append) { const gchar *subtitle_exts[] = SUBTITLE_EXTS; if(extension_matches(uri, subtitle_exts)) { gmpv_mpv_load_track(mpv, uri, TRACK_TYPE_SUBTITLE); } else { gmpv_mpv_load_file(mpv, uri, append); } } gnome-mpv-0.13/src/gmpv_mpv.h000066400000000000000000000037631317030365200161460ustar00rootroot00000000000000/* * Copyright (c) 2014, 2016-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef MPV_H #define MPV_H #include #include #include #include #include "gmpv_common.h" G_BEGIN_DECLS #define GMPV_TYPE_MPV (gmpv_mpv_get_type()) G_DECLARE_DERIVABLE_TYPE(GmpvMpv, gmpv_mpv, GMPV, MPV, GObject) struct _GmpvMpvClass { GObjectClass parent_class; void (*mpv_event_notify)( GmpvMpv *mpv, gint event_id, gpointer event_data ); void (*mpv_log_message)( GmpvMpv *mpv, mpv_log_level log_level, const gchar *prefix, const gchar *text ); void (*mpv_property_changed)( GmpvMpv *mpv, const gchar *name, gpointer value ); void (*initialize)(GmpvMpv *mpv); void (*load_file)(GmpvMpv *mpv, const gchar *uri, gboolean append); void (*reset)(GmpvMpv *mpv); }; GmpvMpv *gmpv_mpv_new(gint64 wid); mpv_opengl_cb_context *gmpv_mpv_get_opengl_cb_context(GmpvMpv *mpv); gboolean gmpv_mpv_get_use_opengl_cb(GmpvMpv *mpv); void gmpv_mpv_initialize(GmpvMpv *mpv); void gmpv_mpv_init_gl(GmpvMpv *mpv); void gmpv_mpv_reset(GmpvMpv *mpv); void gmpv_mpv_quit(GmpvMpv *mpv); void gmpv_mpv_load_track(GmpvMpv *mpv, const gchar *uri, TrackType type); void gmpv_mpv_load_file(GmpvMpv *mpv, const gchar *uri, gboolean append); void gmpv_mpv_load(GmpvMpv *mpv, const gchar *uri, gboolean append); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_mpv_private.h000066400000000000000000000025421317030365200176720ustar00rootroot00000000000000/* * Copyright (c) 2016-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef MPV_OBJ_PRIVATE_H #define MPV_OBJ_PRIVATE_H #include G_BEGIN_DECLS typedef struct _GmpvMpvPrivate GmpvMpvPrivate; enum { PROP_0, PROP_WID, PROP_READY, N_PROPERTIES }; struct _GmpvMpvPrivate { mpv_handle *mpv_ctx; mpv_opengl_cb_context *opengl_ctx; gboolean ready; gchar *tmp_input_file; GSList *log_level_list; gboolean init_vo_config; gboolean force_opengl; gboolean use_opengl; gint64 wid; void *opengl_cb_callback_data; void (*opengl_cb_callback)(void *data); }; #define get_private(mpv) \ G_TYPE_INSTANCE_GET_PRIVATE(mpv, GMPV_TYPE_MPV, GmpvMpvPrivate) void mpv_check_error(int status); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_mpv_wrapper.c000066400000000000000000000116061317030365200176740ustar00rootroot00000000000000/* * Copyright (c) 2016-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include "gmpv_mpv_wrapper.h" #include "gmpv_mpv_private.h" gint gmpv_mpv_command(GmpvMpv *mpv, const gchar **cmd) { GmpvMpvPrivate *priv = get_private(mpv); gint rc = MPV_ERROR_UNINITIALIZED; if(priv->mpv_ctx) { rc = mpv_command(priv->mpv_ctx, cmd); } if(rc < 0) { gchar *cmd_str = g_strjoinv(" ", (gchar **)cmd); g_warning( "Failed to run mpv command \"%s\". Reason: %s.", cmd_str, mpv_error_string(rc) ); g_free(cmd_str); } return rc; } gint gmpv_mpv_command_string(GmpvMpv *mpv, const gchar *cmd) { GmpvMpvPrivate *priv = get_private(mpv); gint rc = MPV_ERROR_UNINITIALIZED; if(priv->mpv_ctx) { rc = mpv_command_string(priv->mpv_ctx, cmd); } if(rc < 0) { g_warning( "Failed to run mpv command string \"%s\". " "Reason: %s.", cmd, mpv_error_string(rc) ); } return rc; } gint gmpv_mpv_set_option_string( GmpvMpv *mpv, const gchar *name, const gchar *value ) { return mpv_set_option_string(get_private(mpv)->mpv_ctx, name, value); } gint gmpv_mpv_get_property( GmpvMpv *mpv, const gchar *name, mpv_format format, void *data ) { GmpvMpvPrivate *priv = get_private(mpv); gint rc = MPV_ERROR_UNINITIALIZED; if(priv->mpv_ctx) { rc = mpv_get_property(priv->mpv_ctx, name, format, data); } if(rc < 0) { g_info( "Failed to retrieve property \"%s\" " "using mpv format %d. Reason: %s.", name, format, mpv_error_string(rc) ); } return rc; } gchar *gmpv_mpv_get_property_string(GmpvMpv *mpv, const gchar *name) { GmpvMpvPrivate *priv = get_private(mpv); gchar *value = NULL; if(priv->mpv_ctx) { value = mpv_get_property_string(priv->mpv_ctx, name); } if(!value) { g_info("Failed to retrieve property \"%s\" as string.", name); } return value; } gboolean gmpv_mpv_get_property_flag(GmpvMpv *mpv, const gchar *name) { GmpvMpvPrivate *priv = get_private(mpv); gboolean value = FALSE; gint rc = MPV_ERROR_UNINITIALIZED; if(priv->mpv_ctx) { rc = mpv_get_property (priv->mpv_ctx, name, MPV_FORMAT_FLAG, &value); } if(rc < 0) { g_info( "Failed to retrieve property \"%s\" as flag. " "Reason: %s.", name, mpv_error_string(rc) ); } return value; } gint gmpv_mpv_set_property( GmpvMpv *mpv, const gchar *name, mpv_format format, void *data ) { GmpvMpvPrivate *priv = get_private(mpv); gint rc = MPV_ERROR_UNINITIALIZED; if(priv->mpv_ctx) { rc = mpv_set_property(priv->mpv_ctx, name, format, data); } if(rc < 0) { g_info( "Failed to set property \"%s\" using mpv format %d. " "Reason: %s.", name, format, mpv_error_string(rc) ); } return rc; } gint gmpv_mpv_set_property_string( GmpvMpv *mpv, const gchar *name, const char *data ) { GmpvMpvPrivate *priv = get_private(mpv); gint rc = MPV_ERROR_UNINITIALIZED; if(priv->mpv_ctx) { rc = mpv_set_property_string(priv->mpv_ctx, name, data); } if(rc < 0) { g_info( "Failed to set property \"%s\" as string. Reason: %s.", name, mpv_error_string(rc) ); } return rc; } gint gmpv_mpv_set_property_flag( GmpvMpv *mpv, const gchar *name, gboolean value ) { GmpvMpvPrivate *priv = get_private(mpv); gint rc = MPV_ERROR_UNINITIALIZED; if(priv->mpv_ctx) { rc = mpv_set_property (priv->mpv_ctx, name, MPV_FORMAT_FLAG, &value); } if(rc < 0) { g_info( "Failed to set property \"%s\" as flag. Reason: %s.", name, mpv_error_string(rc) ); } return rc; } void gmpv_mpv_set_opengl_cb_callback( GmpvMpv *mpv, mpv_opengl_cb_update_fn func, void *data ) { GmpvMpvPrivate *priv = get_private(mpv); priv->opengl_cb_callback = func; priv->opengl_cb_callback_data = data; if(priv->opengl_ctx) { mpv_opengl_cb_set_update_callback(priv->opengl_ctx, func, data); } } gint gmpv_mpv_load_config_file(GmpvMpv *mpv, const gchar *filename) { return mpv_load_config_file(get_private(mpv)->mpv_ctx, filename); } gint gmpv_mpv_observe_property( GmpvMpv *mpv, guint64 reply_userdata, const gchar *name, mpv_format format ) { return mpv_observe_property( get_private(mpv)->mpv_ctx, reply_userdata, name, format ); } gint gmpv_mpv_request_log_messages(GmpvMpv *mpv, const gchar *min_level) { return mpv_request_log_messages(get_private(mpv)->mpv_ctx, min_level); } gnome-mpv-0.13/src/gmpv_mpv_wrapper.h000066400000000000000000000040721317030365200177000ustar00rootroot00000000000000/* * Copyright (c) 2016-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef MPV_WRAPPER_H #define MPV_WRAPPER_H #include #include #include #include "gmpv_mpv.h" gint gmpv_mpv_command(GmpvMpv *mpv, const gchar **cmd); gint gmpv_mpv_command_string(GmpvMpv *mpv, const gchar *cmd); gint gmpv_mpv_set_option_string( GmpvMpv *mpv, const gchar *name, const gchar *value ); gint gmpv_mpv_get_property( GmpvMpv *mpv, const gchar *name, mpv_format format, void *data ); gchar *gmpv_mpv_get_property_string(GmpvMpv *mpv, const gchar *name); gboolean gmpv_mpv_get_property_flag(GmpvMpv *mpv, const gchar *name); gint gmpv_mpv_set_property( GmpvMpv *mpv, const gchar *name, mpv_format format, void *data ); gint gmpv_mpv_set_property_flag( GmpvMpv *mpv, const gchar *name, gboolean value); gint gmpv_mpv_set_property_string( GmpvMpv *mpv, const gchar *name, const char *data ); void gmpv_mpv_set_event_callback( GmpvMpv *mpv, void (*func)(mpv_event *, void *), void *data ); void gmpv_mpv_set_opengl_cb_callback( GmpvMpv *mpv, mpv_opengl_cb_update_fn func, void *data ); gint gmpv_mpv_load_config_file(GmpvMpv *mpv, const gchar *filename); gint gmpv_mpv_observe_property( GmpvMpv *mpv, guint64 reply_userdata, const gchar *name, mpv_format format ); gint gmpv_mpv_request_log_messages(GmpvMpv *mpv, const gchar *min_level); #endif gnome-mpv-0.13/src/gmpv_open_location_dialog.c000066400000000000000000000125531317030365200215040ustar00rootroot00000000000000/* * Copyright (c) 2014, 2016-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include "gmpv_open_location_dialog.h" #include "gmpv_main_window.h" struct _GmpvOpenLocationDialog { GtkDialog parent_instance; GtkWidget *content_area; GtkWidget *content_box; GtkWidget *loc_label; GtkWidget *loc_entry; }; struct _GmpvOpenLocationDialogClass { GtkDialogClass parent_class; }; G_DEFINE_TYPE(GmpvOpenLocationDialog, gmpv_open_location_dialog, GTK_TYPE_DIALOG) static gboolean key_press_handler (GtkWidget *widget, GdkEventKey *event) { guint keyval = event->keyval; guint state = event->state; const guint mod_mask = GDK_MODIFIER_MASK &~(GDK_SHIFT_MASK |GDK_LOCK_MASK |GDK_MOD2_MASK |GDK_MOD3_MASK |GDK_MOD4_MASK |GDK_MOD5_MASK); if((state&mod_mask) == 0 && keyval == GDK_KEY_Return) { gtk_dialog_response(GTK_DIALOG(widget), GTK_RESPONSE_ACCEPT); } return GTK_WIDGET_CLASS(gmpv_open_location_dialog_parent_class) ->key_press_event (widget, event); } static GtkClipboard *get_clipboard(GmpvOpenLocationDialog *dlg) { const gchar *const clipboard_names[] = {"CLIPBOARD", "PRIMARY", NULL}; GtkClipboard *clipboard = NULL; for(gint i = 0; clipboard_names[i] && !clipboard; i++) { GdkAtom atom = gdk_atom_intern(clipboard_names[i], FALSE); clipboard = gtk_clipboard_get(atom); if(!gtk_clipboard_wait_is_text_available(clipboard)) { clipboard = NULL; } } return clipboard; } static void clipboard_text_received_handler( GtkClipboard *clipboard, const gchar *text, gpointer data ) { GmpvOpenLocationDialog *dlg = data; if(text && *text && (g_path_is_absolute(text) || strstr(text, "://") != NULL)) { gtk_entry_set_text(GTK_ENTRY(dlg->loc_entry), text); gtk_editable_select_region(GTK_EDITABLE(dlg->loc_entry), 0, -1); } g_object_unref(dlg); } static void load_text_from_clipboard(GmpvOpenLocationDialog *dlg) { g_object_ref(dlg); gtk_clipboard_request_text( get_clipboard(dlg), clipboard_text_received_handler, dlg ); } static void gmpv_open_location_dialog_class_init(GmpvOpenLocationDialogClass *klass) { GtkWidgetClass *wid_class = GTK_WIDGET_CLASS(klass); wid_class->key_press_event = key_press_handler; } static void gmpv_open_location_dialog_init(GmpvOpenLocationDialog *dlg) { GdkGeometry geom; geom.max_width = G_MAXINT; geom.max_height = 0; dlg->content_box = gtk_box_new(GTK_ORIENTATION_HORIZONTAL, 6); dlg->content_area = gtk_dialog_get_content_area(GTK_DIALOG(dlg)); dlg->loc_label = gtk_label_new(_("Location:")); dlg->loc_entry = gtk_entry_new(); gtk_dialog_add_buttons( GTK_DIALOG(dlg), _("_Cancel"), GTK_RESPONSE_REJECT, _("_Open"), GTK_RESPONSE_ACCEPT, NULL ); gtk_window_set_geometry_hints( GTK_WINDOW(dlg), GTK_WIDGET(dlg), &geom, GDK_HINT_MAX_SIZE ); gtk_window_set_modal(GTK_WINDOW(dlg), 1); gtk_container_set_border_width(GTK_CONTAINER(dlg->content_area), 12); if(!gtk_dialog_get_header_bar(GTK_DIALOG(dlg))) { gtk_widget_set_margin_bottom(dlg->content_box, 6); } gtk_window_set_geometry_hints( GTK_WINDOW(dlg), GTK_WIDGET(dlg), &geom, GDK_HINT_MAX_SIZE ); gtk_container_add(GTK_CONTAINER(dlg->content_area), dlg->content_box); gtk_box_pack_start( GTK_BOX(dlg->content_box), dlg->loc_label, FALSE, FALSE, 0 ); gtk_box_pack_start( GTK_BOX(dlg->content_box), dlg->loc_entry, TRUE, TRUE, 0 ); gtk_window_set_default_size(GTK_WINDOW(dlg), 350, -1); gtk_dialog_set_default_response (GTK_DIALOG(dlg), GTK_RESPONSE_ACCEPT); } GtkWidget *gmpv_open_location_dialog_new(GtkWindow *parent, const gchar *title) { GtkWidget *dlg; GtkWidget *header_bar; gboolean csd_enabled; csd_enabled = gmpv_main_window_get_csd_enabled(GMPV_MAIN_WINDOW(parent)); dlg = g_object_new( gmpv_open_location_dialog_get_type(), "use-header-bar", csd_enabled, "title", title, NULL ); header_bar = gtk_dialog_get_header_bar(GTK_DIALOG(dlg)); if(header_bar) { GtkWidget *cancel_btn = gtk_dialog_get_widget_for_response (GTK_DIALOG(dlg), GTK_RESPONSE_REJECT); gtk_container_child_set( GTK_CONTAINER(header_bar), cancel_btn, "pack-type", GTK_PACK_START, NULL ); gtk_header_bar_set_show_close_button (GTK_HEADER_BAR(header_bar), FALSE); } load_text_from_clipboard(GMPV_OPEN_LOCATION_DIALOG(dlg)); gtk_widget_hide_on_delete(dlg); gtk_window_set_transient_for(GTK_WINDOW(dlg), parent); gtk_widget_show_all(dlg); return dlg; } const gchar *gmpv_open_location_dialog_get_string(GmpvOpenLocationDialog *dlg) { return gtk_entry_get_text(GTK_ENTRY(dlg->loc_entry)); } guint64 gmpv_open_location_dialog_get_string_length(GmpvOpenLocationDialog *dlg) { return gtk_entry_get_text_length(GTK_ENTRY(dlg->loc_entry)); } gnome-mpv-0.13/src/gmpv_open_location_dialog.h000066400000000000000000000024531317030365200215070ustar00rootroot00000000000000/* * Copyright (c) 2014, 2016-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef OPEN_LOCATION_DIALOG_H #define OPEN_LOCATION_DIALOG_H #include #include #include G_BEGIN_DECLS #define GMPV_TYPE_OPEN_LOC_DIALOG (gmpv_open_location_dialog_get_type ()) G_DECLARE_FINAL_TYPE(GmpvOpenLocationDialog, gmpv_open_location_dialog, GMPV, OPEN_LOCATION_DIALOG, GtkDialog) GtkWidget *gmpv_open_location_dialog_new(GtkWindow *parent, const gchar *title); const gchar *gmpv_open_location_dialog_get_string(GmpvOpenLocationDialog *dlg); guint64 gmpv_open_location_dialog_get_string_length(GmpvOpenLocationDialog *dlg); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_player.c000066400000000000000000000622411317030365200166270ustar00rootroot00000000000000/* * Copyright (c) 2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include "gmpv_player.h" #include "gmpv_player_options.h" #include "gmpv_marshal.h" #include "gmpv_metadata_cache.h" #include "gmpv_mpv_wrapper.h" #include "gmpv_def.h" typedef struct _GmpvLogLevel GmpvLogLevel; enum { PROP_0, PROP_PLAYLIST, PROP_METADATA, PROP_TRACK_LIST, N_PROPERTIES }; struct _GmpvLogLevel { const gchar *prefix; mpv_log_level level; }; struct _GmpvPlayer { GmpvMpv parent; GmpvMetadataCache *cache; GPtrArray *playlist; GPtrArray *metadata; GPtrArray *track_list; GHashTable *log_levels; gboolean loaded; gboolean new_file; gboolean init_vo_config; gchar *tmp_input_config; }; struct _GmpvPlayerClass { GmpvMpvClass parent_class; }; static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ); static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ); static void finalize(GObject *object); static void mpv_event_notify(GmpvMpv *mpv, gint event_id, gpointer event_data); static void mpv_log_message( GmpvMpv *mpv, mpv_log_level log_level, const gchar *prefix, const gchar *text ); static void mpv_property_changed( GmpvMpv *mpv, const gchar *name, gpointer value ); static void observe_properties(GmpvMpv *mpv); static void apply_default_options(GmpvMpv *mpv); static void initialize(GmpvMpv *mpv); static gint apply_options_array_string(GmpvMpv *mpv, gchar *args); static void apply_extra_options(GmpvMpv *mpv); static void load_file(GmpvMpv *mpv, const gchar *uri, gboolean append); static void reset(GmpvMpv *mpv); static void load_input_conf(GmpvPlayer *player, const gchar *input_conf); static void load_config_file(GmpvMpv *mpv); static void load_input_config_file(GmpvPlayer *player); static void load_scripts(GmpvPlayer *player); static GmpvTrack *parse_track_entry(mpv_node_list *node); static void add_file_to_playlist(GmpvPlayer *player, const gchar *uri); static void load_from_playlist(GmpvPlayer *player); static GmpvPlaylistEntry *parse_playlist_entry(mpv_node_list *node); static void update_playlist(GmpvPlayer *player); static void update_metadata(GmpvPlayer *player); static void update_track_list(GmpvPlayer *player); static void cache_update_handler( GmpvMetadataCache *cache, const gchar *uri, gpointer data ); G_DEFINE_TYPE(GmpvPlayer, gmpv_player, GMPV_TYPE_MPV) static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ) { switch(property_id) { case PROP_PLAYLIST: case PROP_METADATA: case PROP_TRACK_LIST: g_critical("Attempted to set read-only property"); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ) { GmpvPlayer *self = GMPV_PLAYER(object); switch(property_id) { case PROP_PLAYLIST: g_value_set_pointer(value, self->playlist); break; case PROP_METADATA: g_value_set_pointer(value, self->metadata); break; case PROP_TRACK_LIST: g_value_set_pointer(value, self->track_list); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void finalize(GObject *object) { GmpvPlayer *player = GMPV_PLAYER(object); if(player->tmp_input_config) { g_unlink(player->tmp_input_config); } g_free(player->tmp_input_config); g_ptr_array_free(player->playlist, TRUE); g_ptr_array_free(player->metadata, TRUE); g_ptr_array_free(player->track_list, TRUE); G_OBJECT_CLASS(gmpv_player_parent_class)->finalize(object); } static void mpv_event_notify(GmpvMpv *mpv, gint event_id, gpointer event_data) { GmpvPlayer *player = GMPV_PLAYER(mpv); if(event_id == MPV_EVENT_START_FILE) { gboolean vo_configured = FALSE; gmpv_mpv_get_property( mpv, "vo-configured", MPV_FORMAT_FLAG, &vo_configured ); /* If the vo is not configured yet, save the content of mpv's * playlist. This will be loaded again when the vo is * configured. */ if(!vo_configured) { update_playlist(GMPV_PLAYER(mpv)); } } else if(event_id == MPV_EVENT_END_FILE) { if(player->loaded) { player->new_file = FALSE; } } else if(event_id == MPV_EVENT_IDLE) { player->loaded = FALSE; } else if(event_id == MPV_EVENT_FILE_LOADED) { player->loaded = TRUE; } else if(event_id == MPV_EVENT_VIDEO_RECONFIG) { if(player->new_file) { g_signal_emit_by_name(player, "autofit"); } } GMPV_MPV_CLASS(gmpv_player_parent_class) ->mpv_event_notify(mpv, event_id, event_data); } static void mpv_log_message( GmpvMpv *mpv, mpv_log_level log_level, const gchar *prefix, const gchar *text ) { GmpvPlayer *player = GMPV_PLAYER(mpv); gsize prefix_len = strlen(prefix); gboolean found = FALSE; const gchar *iter_prefix; mpv_log_level iter_level; GHashTableIter iter; g_hash_table_iter_init(&iter, player->log_levels); while( !found && g_hash_table_iter_next( &iter, (gpointer *)&iter_prefix, (gpointer *)&iter_level) ) { gsize iter_prefix_len = strlen(iter_prefix); gint cmp = strncmp( iter_prefix, prefix, (prefix_len < iter_prefix_len)? prefix_len:iter_prefix_len ); /* Allow both exact match and prefix match */ if(cmp == 0 && (iter_prefix_len == prefix_len || (iter_prefix_len < prefix_len && prefix[iter_prefix_len] == '/'))) { found = TRUE; } } if(!found || (log_level <= iter_level)) { gchar *buf = g_strdup(text); gsize len = strlen(buf); if(len > 1) { /* g_message() automatically adds a newline * character when using the default log handler, * but log messages from mpv already come * terminated with a newline character so we * need to take it out. */ if(buf[len-1] == '\n') { buf[len-1] = '\0'; } g_message("[%s] %s", prefix, buf); } g_free(buf); } GMPV_MPV_CLASS(gmpv_player_parent_class) ->mpv_log_message(mpv, log_level, prefix, text); } static void mpv_property_changed( GmpvMpv *mpv, const gchar *name, gpointer value ) { GmpvPlayer *player = GMPV_PLAYER(mpv); if(g_strcmp0(name, "pause") == 0) { gboolean idle_active = FALSE; gboolean pause = value?*((int *)value):TRUE; gmpv_mpv_get_property( mpv, "idle-active", MPV_FORMAT_FLAG, &idle_active ); if(idle_active && !pause && !player->init_vo_config) { load_from_playlist(player); } } else if(g_strcmp0(name, "playlist") == 0) { gint64 playlist_count = 0; gboolean idle_active = FALSE; gboolean was_empty = FALSE; gmpv_mpv_get_property( mpv, "playlist-count", MPV_FORMAT_INT64, &playlist_count ); gmpv_mpv_get_property( mpv, "idle-active", MPV_FORMAT_FLAG, &idle_active ); was_empty = (player->playlist->len == 0); if(!idle_active) { update_playlist(player); } /* Check if we're transitioning from empty playlist to non-empty * playlist. */ if(was_empty && player->playlist->len > 0) { gmpv_mpv_set_property_flag(mpv, "pause", FALSE); } } else if(g_strcmp0(name, "metadata") == 0) { update_metadata(player); } else if(g_strcmp0(name, "track-list") == 0) { update_track_list(player); } else if(g_strcmp0(name, "vo-configured") == 0) { if(player->init_vo_config) { player->init_vo_config = FALSE; load_scripts(player); load_from_playlist(player); } } GMPV_MPV_CLASS(gmpv_player_parent_class) ->mpv_property_changed(mpv, name, value); } static void observe_properties(GmpvMpv *mpv) { gmpv_mpv_observe_property(mpv, 0, "aid", MPV_FORMAT_STRING); gmpv_mpv_observe_property(mpv, 0, "vid", MPV_FORMAT_STRING); gmpv_mpv_observe_property(mpv, 0, "sid", MPV_FORMAT_STRING); gmpv_mpv_observe_property(mpv, 0, "chapters", MPV_FORMAT_INT64); gmpv_mpv_observe_property(mpv, 0, "core-idle", MPV_FORMAT_FLAG); gmpv_mpv_observe_property(mpv, 0, "idle-active", MPV_FORMAT_FLAG); gmpv_mpv_observe_property(mpv, 0, "fullscreen", MPV_FORMAT_FLAG); gmpv_mpv_observe_property(mpv, 0, "pause", MPV_FORMAT_FLAG); gmpv_mpv_observe_property(mpv, 0, "loop", MPV_FORMAT_STRING); gmpv_mpv_observe_property(mpv, 0, "duration", MPV_FORMAT_DOUBLE); gmpv_mpv_observe_property(mpv, 0, "media-title", MPV_FORMAT_STRING); gmpv_mpv_observe_property(mpv, 0, "metadata", MPV_FORMAT_NODE); gmpv_mpv_observe_property(mpv, 0, "playlist", MPV_FORMAT_NODE); gmpv_mpv_observe_property(mpv, 0, "playlist-count", MPV_FORMAT_INT64); gmpv_mpv_observe_property(mpv, 0, "playlist-pos", MPV_FORMAT_INT64); gmpv_mpv_observe_property(mpv, 0, "speed", MPV_FORMAT_DOUBLE); gmpv_mpv_observe_property(mpv, 0, "track-list", MPV_FORMAT_NODE); gmpv_mpv_observe_property(mpv, 0, "vo-configured", MPV_FORMAT_FLAG); gmpv_mpv_observe_property(mpv, 0, "volume", MPV_FORMAT_DOUBLE); } static void apply_default_options(GmpvMpv *mpv) { gchar *config_dir = get_config_dir_path(); gchar *watch_dir = get_watch_dir_path(); const struct { const gchar *name; const gchar *value; } options[] = { {"vo", "opengl,vdpau,vaapi,xv,x11,opengl-cb,"}, {"osd-level", "1"}, {"softvol", "yes"}, {"force-window", "immediate"}, {"input-default-bindings", "yes"}, {"audio-client-name", ICON_NAME}, {"title", "${media-title}"}, {"autofit-larger", "75%"}, {"window-scale", "1"}, {"pause", "yes"}, {"ytdl", "yes"}, {"load-scripts", "no"}, {"osd-bar", "no"}, {"input-cursor", "no"}, {"cursor-autohide", "no"}, {"softvol-max", "100"}, {"config", "no"}, {"config-dir", config_dir}, {"watch-later-directory", watch_dir}, {"screenshot-template", "gnome-mpv-shot%n"}, {NULL, NULL} }; for(gint i = 0; options[i].name; i++) { g_debug( "Applying default option --%s=%s", options[i].name, options[i].value ); gmpv_mpv_set_option_string( mpv, options[i].name, options[i].value ); } g_free(config_dir); g_free(watch_dir); } static void initialize(GmpvMpv *mpv) { GSettings *win_settings = g_settings_new(CONFIG_WIN_STATE); gdouble volume = g_settings_get_double(win_settings, "volume")*100; apply_default_options(mpv); load_config_file(mpv); load_input_config_file(GMPV_PLAYER(mpv)); apply_extra_options(mpv); observe_properties(mpv); gmpv_player_options_init(GMPV_PLAYER(mpv)); GMPV_MPV_CLASS(gmpv_player_parent_class)->initialize(mpv); g_debug("Setting volume to %f", volume); gmpv_mpv_set_property(mpv, "volume", MPV_FORMAT_DOUBLE, &volume); gmpv_player_options_init(GMPV_PLAYER(mpv)); g_object_unref(win_settings); } static gint apply_options_array_string(GmpvMpv *mpv, gchar *args) { gint fail_count = 0; gchar **tokens = g_regex_split_simple( "(^|\\s+)--", args, G_REGEX_NO_AUTO_CAPTURE, 0 ); /* Skip the first token if it's non-NULL, since it is just going to be * empty string for any valid args. */ for(gint i = tokens[0]?1:0; tokens[i]; i++) { gchar **parts = g_strsplit(g_strchomp(tokens[i]), "=", 2); const gchar *option = parts[0]; const gchar *value = (option?parts[1]:NULL)?:""; g_debug("Applying option: --%s", tokens[i]); if(gmpv_mpv_set_option_string(mpv, option, value) < 0) { fail_count++; g_warning("Failed to apply option: --%s\n", tokens[i]); } g_strfreev(parts); } g_strfreev(tokens); return fail_count*(-1); } static void apply_extra_options(GmpvMpv *mpv) { GSettings *settings = g_settings_new(CONFIG_ROOT); gchar *extra_options = g_settings_get_string(settings, "mpv-options"); g_debug("Applying extra mpv options: %s", extra_options); /* Apply extra options */ if(apply_options_array_string(mpv, extra_options) < 0) { const gchar *msg = _("Failed to apply one or more MPV options."); g_signal_emit_by_name(mpv, "error", msg); } g_free(extra_options); g_object_unref(settings); } static void load_file(GmpvMpv *mpv, const gchar *uri, gboolean append) { GmpvPlayer *player = GMPV_PLAYER(mpv); gboolean ready = FALSE; gboolean idle_active = FALSE; g_object_get(mpv, "ready", &ready, NULL); gmpv_mpv_get_property( mpv, "idle-active", MPV_FORMAT_FLAG, &idle_active ); if(idle_active || !ready) { if(!append) { g_ptr_array_set_size(player->playlist, 0); } add_file_to_playlist(player, uri); } else { if(!append) { player->new_file = TRUE; player->loaded = FALSE; } GMPV_MPV_CLASS(gmpv_player_parent_class) ->load_file(mpv, uri, append); } /* Playlist items added when mpv is idle doesn't get added directly to * its internal playlist, so the property change signal won't be fired. * We need to emit notify signal here manually to ensure that the * playlist widget gets updated. */ if(idle_active) { g_object_notify(G_OBJECT(player), "playlist"); } } static void reset(GmpvMpv *mpv) { gboolean idle_active = FALSE; gint64 playlist_pos = 0; gmpv_mpv_get_property( mpv, "idle-active", MPV_FORMAT_FLAG, &idle_active ); gmpv_mpv_get_property( mpv, "playlist-pos", MPV_FORMAT_INT64, &playlist_pos ); GMPV_MPV_CLASS(gmpv_player_parent_class)->reset(mpv); if(!idle_active) { load_from_playlist(GMPV_PLAYER(mpv)); } if(playlist_pos > 0) { gmpv_mpv_set_property( mpv, "playlist-pos", MPV_FORMAT_INT64, &playlist_pos ); } } static void load_input_conf(GmpvPlayer *player, const gchar *input_conf) { const gchar *default_keybinds[] = DEFAULT_KEYBINDS; gchar *tmp_path; FILE *tmp_file; gint tmp_fd; if(player->tmp_input_config) { g_unlink(player->tmp_input_config); g_free(player->tmp_input_config); } tmp_fd = g_file_open_tmp(NULL, &tmp_path, NULL); tmp_file = fdopen(tmp_fd, "w"); player->tmp_input_config = tmp_path; if(!tmp_file) { g_error("Failed to open temporary input config file"); } for(gint i = 0; default_keybinds[i]; i++) { const gsize len = strlen(default_keybinds[i]); gsize write_size = fwrite(default_keybinds[i], len, 1, tmp_file); gint rc = fputc('\n', tmp_file); if(write_size != 1 || rc != '\n') { g_error( "Error writing default keybindings to " "temporary input config file" ); } } g_debug("Using temporary input config file: %s", tmp_path); gmpv_mpv_set_option_string(GMPV_MPV(player), "input-conf", tmp_path); if(input_conf && strlen(input_conf) > 0) { const gsize buf_size = 65536; void *buf = g_malloc(buf_size); FILE *src_file = g_fopen(input_conf, "r"); gsize read_size = buf_size; if(!src_file) { g_warning( "Cannot open input config file: %s", input_conf ); } while(src_file && read_size == buf_size) { read_size = fread(buf, 1, buf_size, src_file); if(read_size != fwrite(buf, 1, read_size, tmp_file)) { g_error( "Error writing requested input " "config file to temporary " "input config file" ); } } g_info("Loaded input config file: %s", input_conf); g_free(buf); } fclose(tmp_file); } static void load_config_file(GmpvMpv *mpv) { GSettings *settings = g_settings_new(CONFIG_ROOT); if(g_settings_get_boolean(settings, "mpv-config-enable")) { gchar *mpv_conf = g_settings_get_string (settings, "mpv-config-file"); g_info("Loading config file: %s", mpv_conf); gmpv_mpv_load_config_file(mpv, mpv_conf); g_free(mpv_conf); } g_object_unref(settings); } static void load_input_config_file(GmpvPlayer *player) { GSettings *settings = g_settings_new(CONFIG_ROOT); gchar *input_conf = NULL; if(g_settings_get_boolean(settings, "mpv-input-config-enable")) { input_conf = g_settings_get_string (settings, "mpv-input-config-file"); g_info("Loading input config file: %s", input_conf); } load_input_conf(player, input_conf); g_free(input_conf); g_object_unref(settings); } static void load_scripts(GmpvPlayer *player) { gchar *path = get_scripts_dir_path(); GDir *dir = g_dir_open(path, 0, NULL); if(dir) { const gchar *name; do { gchar *full_path; name = g_dir_read_name(dir); full_path = g_build_filename(path, name, NULL); if(g_file_test(full_path, G_FILE_TEST_IS_REGULAR)) { const gchar *cmd[] = {"load-script", full_path, NULL}; g_info("Loading script: %s", full_path); gmpv_mpv_command(GMPV_MPV(player), cmd); } g_free(full_path); } while(name); g_dir_close(dir); } else { g_warning("Failed to open scripts directory: %s", path); } g_free(path); } static GmpvTrack *parse_track_entry(mpv_node_list *node) { GmpvTrack *entry = gmpv_track_new(); for(gint i = 0; i < node->num; i++) { if(g_strcmp0(node->keys[i], "type") == 0) { const gchar *type = node->values[i].u.string; if(g_strcmp0(type, "audio") == 0) { entry->type = TRACK_TYPE_AUDIO; } else if(g_strcmp0(type, "video") == 0) { entry->type = TRACK_TYPE_VIDEO; } else if(g_strcmp0(type, "sub") == 0) { entry->type = TRACK_TYPE_SUBTITLE; } } else if(g_strcmp0(node->keys[i], "title") == 0) { entry->title = g_strdup(node->values[i].u.string); } else if(g_strcmp0(node->keys[i], "lang") == 0) { entry->lang = g_strdup(node->values[i].u.string); } else if(g_strcmp0(node->keys[i], "id") == 0) { entry->id = node->values[i].u.int64; } } return entry; } static void add_file_to_playlist(GmpvPlayer *player, const gchar *uri) { GmpvPlaylistEntry *entry = gmpv_playlist_entry_new(uri, NULL); g_ptr_array_add(player->playlist, entry); } static void load_from_playlist(GmpvPlayer *player) { GmpvMpv *mpv = GMPV_MPV(player); GPtrArray *playlist = player->playlist; for(guint i = 0; playlist && i < playlist->len; i++) { GmpvPlaylistEntry *entry = g_ptr_array_index(playlist, i); /* Do not append on first iteration */ GMPV_MPV_CLASS(gmpv_player_parent_class) ->load_file(mpv, entry->filename, i != 0); } } static GmpvPlaylistEntry *parse_playlist_entry(mpv_node_list *node) { const gchar *filename = NULL; const gchar *title = NULL; for(gint i = 0; i < node->num; i++) { if(g_strcmp0(node->keys[i], "filename") == 0) { filename = node->values[i].u.string; } else if(g_strcmp0(node->keys[i], "title") == 0) { title = node->values[i].u.string; } } return gmpv_playlist_entry_new(filename, title); } static void update_playlist(GmpvPlayer *player) { GSettings *settings; gboolean prefetch_metadata; const mpv_node_list *org_list; mpv_node playlist; settings = g_settings_new(CONFIG_ROOT); prefetch_metadata = g_settings_get_boolean(settings, "prefetch-metadata"); g_ptr_array_set_size(player->playlist, 0); gmpv_mpv_get_property (GMPV_MPV(player), "playlist", MPV_FORMAT_NODE, &playlist); org_list = playlist.u.list; if(playlist.format == MPV_FORMAT_NODE_ARRAY) { for(gint i = 0; i < org_list->num; i++) { GmpvPlaylistEntry *entry; entry = parse_playlist_entry(org_list->values[i].u.list); if(!entry->title && prefetch_metadata) { GmpvMetadataCacheEntry *cache_entry; cache_entry = gmpv_metadata_cache_lookup (player->cache, entry->filename); entry->title = g_strdup(cache_entry->title); } g_ptr_array_add(player->playlist, entry); } mpv_free_node_contents(&playlist); g_object_notify(G_OBJECT(player), "playlist"); } if(prefetch_metadata) { gmpv_metadata_cache_load_playlist (player->cache, player->playlist); } g_object_unref(settings); } static void update_metadata(GmpvPlayer *player) { mpv_node_list *org_list = NULL; mpv_node metadata; g_ptr_array_set_size(player->metadata, 0); gmpv_mpv_get_property( GMPV_MPV(player), "metadata", MPV_FORMAT_NODE, &metadata ); org_list = metadata.u.list; if(metadata.format == MPV_FORMAT_NODE_MAP && org_list->num > 0) { for(gint i = 0; i < org_list->num; i++) { const gchar *key; mpv_node value; key = org_list->keys[i]; value = org_list->values[i]; if(value.format == MPV_FORMAT_STRING) { GmpvMetadataEntry *entry; entry = gmpv_metadata_entry_new (key, value.u.string); g_ptr_array_add(player->metadata, entry); } else { g_warning( "Ignored metadata field %s " "with unexpected format %d", key, value.format ); } } mpv_free_node_contents(&metadata); g_object_notify(G_OBJECT(player), "metadata"); } } static void update_track_list(GmpvPlayer *player) { mpv_node_list *org_list = NULL; mpv_node track_list; g_ptr_array_set_size(player->track_list, 0); gmpv_mpv_get_property( GMPV_MPV(player), "track-list", MPV_FORMAT_NODE, &track_list ); org_list = track_list.u.list; if(track_list.format == MPV_FORMAT_NODE_ARRAY) { for(gint i = 0; i < org_list->num; i++) { GmpvTrack *entry = parse_track_entry (org_list->values[i].u.list); g_ptr_array_add(player->track_list, entry); } mpv_free_node_contents(&track_list); g_object_notify(G_OBJECT(player), "track-list"); } } static void cache_update_handler( GmpvMetadataCache *cache, const gchar *uri, gpointer data ) { GmpvPlayer *player = data; for(guint i = 0; i < player->playlist->len; i++) { GmpvPlaylistEntry *entry = g_ptr_array_index(player->playlist, i); if(g_strcmp0(entry->filename, uri) == 0) { GmpvMetadataCacheEntry *cache_entry; cache_entry = gmpv_metadata_cache_lookup(cache, uri); g_free(entry->title); entry->title = g_strdup(cache_entry->title); g_signal_emit_by_name(data, "metadata-update", i); } } } static void gmpv_player_class_init(GmpvPlayerClass *klass) { GmpvMpvClass *mpv_class = GMPV_MPV_CLASS(klass); GObjectClass *obj_class = G_OBJECT_CLASS(klass); GParamSpec *pspec = NULL; mpv_class->mpv_event_notify = mpv_event_notify; mpv_class->mpv_log_message = mpv_log_message; mpv_class->mpv_property_changed = mpv_property_changed; mpv_class->initialize = initialize; mpv_class->load_file = load_file; mpv_class->reset = reset; obj_class->set_property = set_property; obj_class->get_property = get_property; obj_class->finalize = finalize; pspec = g_param_spec_pointer ( "playlist", "Playlist", "The playlist", G_PARAM_READABLE ); g_object_class_install_property(obj_class, PROP_PLAYLIST, pspec); pspec = g_param_spec_pointer ( "metadata", "Metadata", "The metadata tags of the current file", G_PARAM_READABLE ); g_object_class_install_property(obj_class, PROP_METADATA, pspec); pspec = g_param_spec_pointer ( "track-list", "Track list", "Audio, video, and subtitle tracks of the current file", G_PARAM_READABLE ); g_object_class_install_property(obj_class, PROP_TRACK_LIST, pspec); g_signal_new( "autofit", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__VOID, G_TYPE_NONE, 0 ); g_signal_new( "metadata-update", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_gen_marshal_VOID__INT64, G_TYPE_NONE, 1, G_TYPE_INT64 ); } static void gmpv_player_init(GmpvPlayer *player) { player->cache = gmpv_metadata_cache_new(); player->playlist = g_ptr_array_new_with_free_func ((GDestroyNotify)gmpv_playlist_entry_free); player->metadata = g_ptr_array_new_with_free_func ((GDestroyNotify)gmpv_metadata_entry_free); player->track_list = g_ptr_array_new_with_free_func ((GDestroyNotify)gmpv_track_free); player->log_levels = g_hash_table_new_full( g_str_hash, g_str_equal, g_free, NULL ); player->loaded = FALSE; player->new_file = TRUE; player->init_vo_config = TRUE; player->tmp_input_config = NULL; g_signal_connect( player->cache, "update", G_CALLBACK(cache_update_handler), player ); } GmpvPlayer *gmpv_player_new(gint64 wid) { return GMPV_PLAYER(g_object_new( gmpv_player_get_type(), "wid", wid, NULL )); } void gmpv_player_set_log_level( GmpvPlayer *player, const gchar *prefix, const gchar *level ) { const struct { gchar *name; mpv_log_level level; } level_map[] = { {"no", MPV_LOG_LEVEL_NONE}, {"fatal", MPV_LOG_LEVEL_FATAL}, {"error", MPV_LOG_LEVEL_ERROR}, {"warn", MPV_LOG_LEVEL_WARN}, {"info", MPV_LOG_LEVEL_INFO}, {"v", MPV_LOG_LEVEL_V}, {"debug", MPV_LOG_LEVEL_DEBUG}, {"trace", MPV_LOG_LEVEL_TRACE}, {NULL, MPV_LOG_LEVEL_NONE} }; GHashTableIter iter; mpv_log_level iter_level = DEFAULT_LOG_LEVEL; mpv_log_level max_level = DEFAULT_LOG_LEVEL; gboolean found = FALSE; gint i = 0; for(i = 0; level_map[i].name && !found; i++) { if(g_strcmp0(level, level_map[i].name) == 0) { found = TRUE; } } if(found && g_strcmp0(prefix, "all") != 0) { g_hash_table_replace( player->log_levels, g_strdup(prefix), GINT_TO_POINTER(level_map[i].level) ); } max_level = level_map[i].level; g_hash_table_iter_init(&iter, player->log_levels); while(g_hash_table_iter_next(&iter, NULL, (gpointer *)&iter_level)) { if(iter_level > max_level) { iter_level = max_level; } } for(i = 0; level_map[i].level != max_level; i++) gmpv_mpv_request_log_messages(GMPV_MPV(player), level_map[i].name); } gnome-mpv-0.13/src/gmpv_player.h000066400000000000000000000021171317030365200166300ustar00rootroot00000000000000/* * Copyright (c) 2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef PLAYER_H #define PLAYER_H #include #include "gmpv_mpv.h" G_BEGIN_DECLS #define GMPV_TYPE_PLAYER (gmpv_player_get_type()) G_DECLARE_FINAL_TYPE(GmpvPlayer, gmpv_player, GMPV, PLAYER, GmpvMpv) GmpvPlayer *gmpv_player_new(gint64 wid); void gmpv_player_set_log_level( GmpvPlayer *player, const gchar *prefix, const gchar *level ); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_player_options.c000066400000000000000000000230761317030365200204050ustar00rootroot00000000000000/* * Copyright (c) 2016-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include #include #include "gmpv_player_options.h" #include "gmpv_mpv.h" #include "gmpv_mpv_private.h" #include "gmpv_mpv_wrapper.h" #include "gmpv_def.h" static gboolean parse_geom_token(const gchar **iter, GValue *value); static gboolean parse_dim_string(const gchar *geom_str, gint64 dim[2]); static gboolean parse_pos_token_prefix(const gchar **iter, gchar **prefix); static gboolean parse_pos_token( const gchar **iter, GValue *value, gboolean *flip ); static gboolean parse_pos_string( const gchar *geom_str, gboolean flip[2], GValue pos[2] ); static void parse_geom_string( GmpvMpv *mpv, const gchar *geom_str, gboolean flip[2], GValue pos[2], gint64 dim[2] ); static gboolean get_video_dimensions(GmpvMpv *mpv, gint64 dim[2]); static void handle_window_scale(GmpvMpv *mpv, gint64 dim[2]); static void handle_autofit(GmpvMpv *mpv, gint64 dim[2]); static void handle_geometry(GmpvPlayer *player); static void handle_fs(GmpvPlayer *player); static void handle_msg_level(GmpvPlayer *player); static void ready_handler(GObject *object, GParamSpec *pspec, gpointer data); static void autofit_handler(GmpvMpv *mpv, gpointer data); static gboolean parse_geom_token(const gchar **iter, GValue *value) { gchar *end = NULL; gint64 token_value = g_ascii_strtoll(*iter, &end, 10); gboolean rc = FALSE; if(end) { if(*end == '%') { g_value_init(value, G_TYPE_DOUBLE); g_value_set_double(value, (gdouble)token_value/100.0); end++; } else { g_value_init(value, G_TYPE_INT64); g_value_set_int64(value, token_value); } rc = !!end && *iter != end; *iter = end; } return rc; } static gboolean parse_dim_string(const gchar *geom_str, gint64 dim[2]) { GdkScreen *screen = gdk_screen_get_default(); gint screen_dim[2] = {0, 0}; gdouble multiplier[2] = {-1, -1}; gchar **tokens = g_strsplit(geom_str, "x", 2); gint i = -1; dim[0] = -1; dim[1] = -1; screen_dim[0] = gdk_screen_get_width(screen); screen_dim[1] = gdk_screen_get_height(screen); while(tokens && tokens[++i] && i < 3) { gint value = (gint)g_ascii_strtoll(tokens[i], NULL, 0); if((i == 0 && value > 0) || i == 1) { if(tokens[i][strnlen(tokens[i], 256)-1] == '%') { multiplier[i] = value/100.0; } else if(i == 1 && multiplier[0] != -1) { multiplier[i] = multiplier[0]; } if(multiplier[i] == -1) { dim[i] = value; } else { dim[i] = (gint)(multiplier[i]*screen_dim[i]); } } } g_strfreev(tokens); return (dim[0] > 0 && dim[1] > 0); } static gboolean parse_pos_token_prefix(const gchar **iter, gchar **prefix) { const gchar *start = *iter; const gchar *end = *iter; gboolean rc = FALSE; while(*end && (*end == '+' || *end == '-')) { end++; } rc = (end-start <= 2); if(rc) { if(end-start == 2) { end--; } *prefix = g_strndup(start, (gsize)(end-start)); *iter = end; } return rc; } static gboolean parse_pos_token( const gchar **iter, GValue *value, gboolean *flip ) { gchar *prefix = NULL; gboolean rc = TRUE; rc = rc && parse_pos_token_prefix(iter, &prefix); rc = rc && parse_geom_token(iter, value); *flip = (prefix && *prefix == '-'); g_free(prefix); return rc; } static gboolean parse_pos_string( const gchar *geom_str, gboolean flip[2], GValue pos[2] ) { gboolean rc = TRUE; rc = rc && parse_pos_token(&geom_str, &pos[0], &flip[0]); rc = rc && parse_pos_token(&geom_str, &pos[1], &flip[1]); return rc; } static void parse_geom_string( GmpvMpv *mpv, const gchar *geom_str, gboolean flip[2], GValue pos[2], gint64 dim[2] ) { if(!!geom_str) { if(geom_str[0] != '+' && geom_str[0] != '-') { parse_dim_string(geom_str, dim); } /* Move the beginning of the string to the 'position' section */ while(*geom_str && *geom_str != '+' && *geom_str != '-') { geom_str++; } parse_pos_string(geom_str, flip, pos); } } static gboolean get_video_dimensions(GmpvMpv *mpv, gint64 dim[2]) { GmpvMpvPrivate *priv = get_private(mpv); gint rc = 0; rc |= mpv_get_property(priv->mpv_ctx, "dwidth", MPV_FORMAT_INT64, &dim[0]); rc |= mpv_get_property(priv->mpv_ctx, "dheight", MPV_FORMAT_INT64, &dim[1]); return (rc >= 0); } static void ready_handler(GObject *object, GParamSpec *pspec, gpointer data) { GmpvPlayer *player = GMPV_PLAYER(object); handle_geometry(player); handle_fs(player); handle_msg_level(player); } static void autofit_handler(GmpvMpv *mpv, gpointer data) { gint64 dim[2] = {0, 0}; handle_window_scale(mpv, dim); handle_autofit(mpv, dim); if(dim[0] > 0 && dim[1] > 0) { g_signal_emit_by_name(mpv, "window-resize", dim[0], dim[1]); } } static void handle_window_scale(GmpvMpv *mpv, gint64 dim[2]) { gint64 vid_dim[2] = {0, 0}; gchar *scale_str; gboolean scale_set; scale_str = mpv_get_property_string (get_private(mpv)->mpv_ctx, "options/window-scale"); scale_set = scale_str && *scale_str; get_video_dimensions(mpv, vid_dim); if(scale_set) { gdouble scale; g_debug("Retrieved option --window-scale=%s", scale_str); /* This should never fail since mpv_set_option() will * refuse to set invalid values. */ scale = g_ascii_strtod(scale_str, NULL); dim[0] = (gint64)(scale*(gdouble)vid_dim[0]); dim[1] = (gint64)(scale*(gdouble)vid_dim[1]); } mpv_free(scale_str); } static void handle_autofit(GmpvMpv *mpv, gint64 dim[2]) { GmpvMpvPrivate *priv = get_private(mpv); gint64 vid_dim[2] = {0, 0}; gint64 autofit_dim[2] = {0, 0}; gint64 larger_dim[2] = {G_MAXINT64, G_MAXINT64}; gint64 smaller_dim[2] = {0, 0}; gchar *autofit_str = NULL; gchar *larger_str = NULL; gchar *smaller_str = NULL; gboolean autofit_set = FALSE; gboolean larger_set = FALSE; gboolean smaller_set = FALSE; autofit_str = mpv_get_property_string (priv->mpv_ctx, "options/autofit"); larger_str = mpv_get_property_string (priv->mpv_ctx, "options/autofit-larger"); smaller_str = mpv_get_property_string (priv->mpv_ctx, "options/autofit-smaller"); autofit_set = autofit_str && *autofit_str; larger_set = larger_str && *larger_str; smaller_set = smaller_str && *smaller_str; if(autofit_set) { g_debug("Retrieved option --autofit=%s", autofit_str); parse_dim_string(autofit_str, autofit_dim); } if(larger_set) { g_debug("Retrieved option --autofit-larger=%s", larger_str); parse_dim_string(larger_str, larger_dim); } if(smaller_set) { g_debug("Retrieved option --autofit-smaller=%s", smaller_str); parse_dim_string(smaller_str, smaller_dim); } if( (autofit_set || larger_set || smaller_set) && get_video_dimensions(mpv, vid_dim) ) { gdouble ratio = 1.0; autofit_dim[0] = CLAMP( autofit_dim[0], smaller_dim[0], larger_dim[0] ); autofit_dim[1] = CLAMP( autofit_dim[1], smaller_dim[1], larger_dim[1] ); dim[0] = CLAMP(vid_dim[0], autofit_dim[0], larger_dim[0]); dim[1] = CLAMP(vid_dim[1], autofit_dim[1], larger_dim[1]); ratio = MIN( (gdouble)dim[0]/(gdouble)vid_dim[0], (gdouble)dim[1]/(gdouble)vid_dim[1] ); dim[0] = (gint64)(ratio*(gdouble)vid_dim[0]); dim[1] = (gint64)(ratio*(gdouble)vid_dim[1]); } mpv_free(autofit_str); mpv_free(larger_str); mpv_free(smaller_str); } static void handle_geometry(GmpvPlayer *player) { gchar *geometry_str = gmpv_mpv_get_property_string (GMPV_MPV(player), "options/geometry"); if(geometry_str) { gint64 dim[2] = {0, 0}; GValue pos[2] = {G_VALUE_INIT, G_VALUE_INIT}; gboolean flip[2] = {FALSE, FALSE}; parse_geom_string(GMPV_MPV(player), geometry_str, flip, pos, dim); if(G_IS_VALUE(&pos[0]) && G_IS_VALUE(&pos[1])) { g_signal_emit_by_name( player, "window-move", flip[0], flip[1], &pos[0], &pos[1] ); } if(dim[0] > 0 && dim[1] > 0) { g_signal_emit_by_name( player, "window-resize", dim[0], dim[1] ); } } mpv_free(geometry_str); } static void handle_fs(GmpvPlayer *player) { GmpvMpv *mpv = GMPV_MPV(player); gchar *fs_str = gmpv_mpv_get_property_string(mpv, "options/fs"); if(g_strcmp0(fs_str, "yes") == 0) { gmpv_mpv_command_string (mpv, "script-message gmpv-action win.enter-fullscreen"); } mpv_free(fs_str); } static void handle_msg_level(GmpvPlayer *player) { GmpvMpv *mpv = GMPV_MPV(player); gchar *optbuf = NULL; gchar **tokens = NULL; gint i; optbuf = gmpv_mpv_get_property_string(mpv, "options/msg-level"); if(optbuf) { tokens = g_strsplit(optbuf, ",", 0); } for(i = 0; tokens && tokens[i]; i++) { gchar **pair = g_strsplit(tokens[i], "=", 2); gmpv_player_set_log_level(player, pair[0], pair[1]); g_strfreev(pair); } mpv_free(optbuf); g_strfreev(tokens); } void module_log_level_free(module_log_level *level) { g_free(level->prefix); g_free(level); } void gmpv_player_options_init(GmpvPlayer *player) { g_signal_connect( player, "notify::ready", G_CALLBACK(ready_handler), NULL ); g_signal_connect( player, "autofit", G_CALLBACK(autofit_handler), NULL ); } gnome-mpv-0.13/src/gmpv_player_options.h000066400000000000000000000021161317030365200204020ustar00rootroot00000000000000/* * Copyright (c) 2016-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef PLAYER_OPTIONS_H #define PLAYER_OPTIONS_H #include #include #include "gmpv_player.h" G_BEGIN_DECLS typedef struct module_log_level module_log_level; struct module_log_level { gchar *prefix; mpv_log_level level; }; void module_log_level_free(module_log_level *level); void gmpv_player_options_init(GmpvPlayer *player); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_playlist_widget.c000066400000000000000000000507151317030365200205420ustar00rootroot00000000000000/* * Copyright (c) 2014-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include #include #include #include "gmpv_playlist_widget.h" #include "gmpv_metadata_cache.h" #include "gmpv_marshal.h" #include "gmpv_common.h" #include "gmpv_def.h" enum { PROP_0, PROP_PLAYLIST_COUNT, N_PROPERTIES }; enum PlaylistColumn { PLAYLIST_NAME_COLUMN, PLAYLIST_URI_COLUMN, PLAYLIST_WEIGHT_COLUMN, PLAYLIST_N_COLUMNS }; struct _GmpvPlaylistWidget { GtkScrolledWindow parent_instance; gint64 playlist_count; GtkListStore *store; GtkWidget *tree_view; GtkTreeViewColumn *title_column; GtkCellRenderer *title_renderer; gint last_x; gint last_y; gboolean dnd_delete; }; struct _GmpvPlaylistWidgetClass { GtkScrolledWindowClass parent_class; }; static void constructed(GObject *object); static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ); static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ); static void drag_begin_handler( GtkWidget *widget, GdkDragContext *context, gpointer data ); static void drag_data_get_handler( GtkWidget *widget, GdkDragContext *context, GtkSelectionData *sel_data, guint info, guint time, gpointer data ); static void drag_data_received_handler( GtkWidget *widget, GdkDragContext *context, gint x, gint y, GtkSelectionData *sel_data, guint info, guint time, gpointer data ); static void drag_data_delete_handler( GtkWidget *widget, GdkDragContext *context, gpointer data ); static void row_activated_handler( GtkTreeView *tree_view, GtkTreePath *path, GtkTreeViewColumn *column, gpointer data ); static void row_inserted_handler( GtkTreeModel *tree_model, GtkTreePath *path, GtkTreeIter *iter, gpointer data ); static void row_deleted_handler( GtkTreeModel *tree_model, GtkTreePath *path, gpointer data ); static gboolean mouse_press_handler( GtkWidget *widget, GdkEvent *event, gpointer data ); static gchar *get_uri_selected(GmpvPlaylistWidget *wgt); G_DEFINE_TYPE(GmpvPlaylistWidget, gmpv_playlist_widget, GTK_TYPE_SCROLLED_WINDOW) static void constructed(GObject *object) { GmpvPlaylistWidget *self = GMPV_PLAYLIST_WIDGET(object); GtkTargetEntry targets[] = DND_TARGETS; self->store = gtk_list_store_new( 3, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_INT ); self->tree_view = gtk_tree_view_new_with_model (GTK_TREE_MODEL(self->store)); g_signal_connect( self->tree_view, "button-press-event", G_CALLBACK(mouse_press_handler), self ); g_signal_connect_after( self->tree_view, "drag-begin", G_CALLBACK(drag_begin_handler), self ); g_signal_connect( self->tree_view, "drag-data-get", G_CALLBACK(drag_data_get_handler), self ); g_signal_connect( self->tree_view, "drag-data-received", G_CALLBACK(drag_data_received_handler), self ); g_signal_connect( self->tree_view, "drag-data-delete", G_CALLBACK(drag_data_delete_handler), self ); g_signal_connect( self->tree_view, "row-activated", G_CALLBACK(row_activated_handler), self ); g_signal_connect( self->store, "row-inserted", G_CALLBACK(row_inserted_handler), self ); g_signal_connect( self->store, "row-deleted", G_CALLBACK(row_deleted_handler), self ); gtk_tree_view_enable_model_drag_source( GTK_TREE_VIEW(self->tree_view), GDK_BUTTON1_MASK, targets, G_N_ELEMENTS(targets), GDK_ACTION_COPY| GDK_ACTION_LINK| GDK_ACTION_MOVE ); gtk_tree_view_enable_model_drag_dest( GTK_TREE_VIEW(self->tree_view), targets, G_N_ELEMENTS(targets), GDK_ACTION_MOVE ); gtk_widget_set_can_focus(self->tree_view, FALSE); gtk_tree_view_set_reorderable(GTK_TREE_VIEW(self->tree_view), FALSE); gtk_tree_view_append_column (GTK_TREE_VIEW(self->tree_view), self->title_column); gtk_container_add(GTK_CONTAINER(self), self->tree_view); G_OBJECT_CLASS(gmpv_playlist_widget_parent_class)->constructed(object); } static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ) { GmpvPlaylistWidget *self = GMPV_PLAYLIST_WIDGET(object); if(property_id == PROP_PLAYLIST_COUNT) { self->playlist_count = g_value_get_int64(value); } else { G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); } } static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ) { GmpvPlaylistWidget *self = GMPV_PLAYLIST_WIDGET(object); if(property_id == PROP_PLAYLIST_COUNT) { g_value_set_int64(value, self->playlist_count); } else { G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); } } static void drag_begin_handler( GtkWidget *widget, GdkDragContext *context, gpointer data ) { const gint padding = 6; const gint border_width = 1; GmpvPlaylistWidget *wgt = data; GtkTreeView *tree_view = GTK_TREE_VIEW(widget); GtkStyleContext *style = gtk_widget_get_style_context(widget); GtkTreeModel *model = gtk_tree_view_get_model(tree_view); GtkTreePath *path = NULL; GtkTreeIter iter; GdkWindow *window = gtk_widget_get_window(widget); PangoContext *pango_ctx = gtk_widget_get_pango_context(widget); PangoLayout *layout = pango_layout_new(pango_ctx); gint width = 0, height = 0; gint text_width = 0, text_height = 0; gint cell_x = 0, cell_y = 0; gchar *name = NULL; GdkRGBA *border_color = NULL; GdkRGBA *fg_color = NULL; cairo_surface_t *surface = NULL; cairo_t *cr = NULL; gtk_tree_view_get_path_at_pos( tree_view, wgt->last_x, wgt->last_y, NULL, NULL, &cell_x, &cell_y ); gtk_tree_view_get_cursor(tree_view, &path, NULL); gtk_tree_model_get_iter(model, &iter, path); gtk_tree_model_get(model, &iter, PLAYLIST_NAME_COLUMN, &name, -1); pango_layout_set_text(layout, name, (gint)strlen(name)); pango_layout_get_pixel_size(layout, &text_width, &text_height); gtk_cell_renderer_get_preferred_height( wgt->title_renderer, widget, NULL, &height ); width = text_width+2*(padding+border_width); height += 2*border_width; surface = gdk_window_create_similar_surface (window, CAIRO_CONTENT_COLOR, width, height); cr = cairo_create(surface); gtk_style_context_get( style, GTK_STATE_FLAG_NORMAL, GTK_STYLE_PROPERTY_COLOR, &fg_color, GTK_STYLE_PROPERTY_BORDER_COLOR, &border_color, NULL); gtk_render_background(style, cr, 0, 0, width, height); /* Draw border */ gdk_cairo_set_source_rgba(cr, border_color); cairo_set_line_width(cr, border_width); cairo_rectangle( cr, border_width/2.0, border_width/2.0, width-border_width, height-border_width ); cairo_stroke(cr); /* Draw text */ gdk_cairo_set_source_rgba(cr, fg_color); cairo_translate(cr, padding, (height-text_height)/2.0); pango_cairo_show_layout(cr, layout); cairo_surface_set_device_offset ( surface, (-1)*(MIN(cell_x+border_width, width-border_width)), (-1)*(cell_y+border_width) ); gtk_drag_set_icon_surface(context, surface); gdk_rgba_free(fg_color); gdk_rgba_free(border_color); cairo_destroy(cr); g_object_unref(layout); } static void drag_data_get_handler( GtkWidget *widget, GdkDragContext *context, GtkSelectionData *sel_data, guint info, guint time, gpointer data ) { gchar *type = gdk_atom_name(gtk_selection_data_get_target(sel_data)); gchar *text = get_uri_selected(data); if(g_strcmp0(type, "PLAYLIST_PATH") == 0) { GmpvPlaylistWidget *wgt = data; GtkTreePath *path = NULL; gchar *path_str = NULL; GdkAtom atom = gdk_atom_intern_static_string("PLAYLIST_PATH"); gtk_tree_view_get_cursor (GTK_TREE_VIEW(wgt->tree_view), &path, NULL); path_str = gtk_tree_path_to_string(path); gtk_selection_data_set( sel_data, atom, 8, (const guchar *)path_str, (gint)strlen(path_str) ); g_free(path_str); } else if(g_strcmp0(type, "text/uri-list") == 0) { /* Only one URI can be selected at a time */ gchar *uris[] = {text, NULL}; gtk_selection_data_set_uris(sel_data, uris); } else { gtk_selection_data_set_text(sel_data, text, -1); } g_free(type); g_free(text); } static void drag_data_received_handler( GtkWidget *widget, GdkDragContext *context, gint x, gint y, GtkSelectionData *sel_data, guint info, guint time, gpointer data) { GmpvPlaylistWidget *wgt = data; gchar *type = gdk_atom_name(gtk_selection_data_get_target(sel_data)); gboolean reorder = (widget == gtk_drag_get_source_widget(context)); if(reorder) { GtkListStore *store; const guchar *raw_data; gint src_index, dest_index; GtkTreeIter src_iter, dest_iter; GtkTreePath *src_path, *dest_path; GtkTreeViewDropPosition before_mask; GtkTreeViewDropPosition drop_pos; gboolean insert_before; gboolean dest_row_exist; store = wgt->store; raw_data = gtk_selection_data_get_data(sel_data); src_path = gtk_tree_path_new_from_string ((const gchar *)raw_data); src_index = gtk_tree_path_get_indices(src_path)[0]; before_mask = GTK_TREE_VIEW_DROP_BEFORE| GTK_TREE_VIEW_DROP_INTO_OR_BEFORE; dest_row_exist = gtk_tree_view_get_dest_row_at_pos ( GTK_TREE_VIEW(widget), x, y, &dest_path, &drop_pos ); wgt->dnd_delete = FALSE; g_assert(g_strcmp0(type, "PLAYLIST_PATH") == 0); g_assert(src_path); gtk_tree_model_get_iter( GTK_TREE_MODEL(store), &src_iter, src_path ); if(dest_row_exist) { g_assert(dest_path); dest_index = gtk_tree_path_get_indices(dest_path)[0]; gtk_tree_model_get_iter( GTK_TREE_MODEL(store), &dest_iter, dest_path ); } else { /* Set dest_iter to the last child */ GtkTreeIter iter; gboolean has_next; drop_pos = GTK_TREE_VIEW_DROP_AFTER; dest_index = -1; gtk_tree_model_get_iter_first (GTK_TREE_MODEL(store), &iter); do { dest_iter = iter; has_next = gtk_tree_model_iter_next (GTK_TREE_MODEL(store), &iter); dest_index++; } while(has_next); } insert_before = (drop_pos&before_mask || drop_pos == 0); if(insert_before) { gtk_list_store_move_before(store, &src_iter, &dest_iter); } else { gtk_list_store_move_after(store, &src_iter, &dest_iter); } g_signal_emit_by_name( wgt, "rows-reordered", src_index+(src_index>dest_index), dest_index+!insert_before ); gtk_tree_path_free(src_path); gtk_tree_path_free(dest_path); } else { g_signal_emit_by_name( wgt, "drag-data-received", context, x, y, sel_data, info, time, data ); } } static void drag_data_delete_handler( GtkWidget *widget, GdkDragContext *context, gpointer data ) { GmpvPlaylistWidget *wgt = data; /* Prevent default handler from deleting the source row when reordering. * When reordering, dnd_delete will be set to FALSE in * drag_data_received_handler(). */ if(!wgt->dnd_delete) { g_signal_stop_emission_by_name(widget, "drag-data-delete"); } wgt->dnd_delete = TRUE; } static void row_activated_handler( GtkTreeView *tree_view, GtkTreePath *path, GtkTreeViewColumn *column, gpointer data ) { gint *indices = gtk_tree_path_get_indices(path); gint64 index = indices?indices[0]:-1; g_signal_emit_by_name(data, "row-activated", index); } static void row_inserted_handler( GtkTreeModel *tree_model, GtkTreePath *path, GtkTreeIter *iter, gpointer data ) { const gint pos = gtk_tree_path_get_indices(path)[0]; GMPV_PLAYLIST_WIDGET(data)->playlist_count++; g_signal_emit_by_name(data, "row-inserted", pos); g_object_notify(data, "playlist-count"); } static void row_deleted_handler( GtkTreeModel *tree_model, GtkTreePath *path, gpointer data ) { const gint pos = gtk_tree_path_get_indices(path)[0]; GMPV_PLAYLIST_WIDGET(data)->playlist_count--; g_signal_emit_by_name(data, "row-deleted", pos); g_object_notify(data, "playlist-count"); } static gboolean mouse_press_handler( GtkWidget *widget, GdkEvent *event, gpointer data ) { GmpvPlaylistWidget *wgt = data; GdkEventButton *btn_event = (GdkEventButton *)event; gboolean handled; wgt->last_x = (gint)btn_event->x; wgt->last_y = (gint)btn_event->y; handled = ( btn_event->type == GDK_BUTTON_PRESS && btn_event->button == 3 ); if(handled) { GMenu *menu; GMenuItem *add_menu_item; GMenuItem *add_loc_menu_item; GMenuItem *shuffle_menu_item; GMenuItem *loop_menu_item; GtkWidget *ctx_menu; menu = g_menu_new(); add_menu_item = g_menu_item_new ( _("_Add…"), "win.show-open-dialog(true)" ); add_loc_menu_item = g_menu_item_new ( _("Add _Location…"), "win.show-open-location-dialog(true)" ); shuffle_menu_item = g_menu_item_new(_("_Shuffle"), "win.shuffle-playlist"); loop_menu_item = g_menu_item_new(_("L_oop"), "win.toggle-loop"); g_menu_append_item(menu, add_menu_item); g_menu_append_item(menu, add_loc_menu_item); g_menu_append_item(menu, shuffle_menu_item); g_menu_append_item(menu, loop_menu_item); g_menu_freeze(menu); ctx_menu = gtk_menu_new_from_model(G_MENU_MODEL(menu)); gtk_menu_attach_to_widget(GTK_MENU(ctx_menu), widget, NULL); gtk_widget_show_all(ctx_menu); gtk_menu_popup( GTK_MENU(ctx_menu), NULL, NULL, NULL, NULL, btn_event->button, btn_event->time ); } return handled; } static gchar *get_uri_selected(GmpvPlaylistWidget *wgt) { GtkTreeIter iter; GtkTreePath *path = NULL; gchar *result = NULL; gboolean rc = FALSE; gtk_tree_view_get_cursor(GTK_TREE_VIEW(wgt->tree_view), &path, NULL); if(path) { rc = gtk_tree_model_get_iter (GTK_TREE_MODEL(wgt->store), &iter, path); } if(rc) { gtk_tree_model_get( GTK_TREE_MODEL(wgt->store), &iter, PLAYLIST_URI_COLUMN, &result, -1 ); } return result; } static void gmpv_playlist_widget_class_init(GmpvPlaylistWidgetClass *klass) { GObjectClass *obj_class = G_OBJECT_CLASS(klass); GParamSpec *pspec = NULL; obj_class->constructed = constructed; obj_class->set_property = set_property; obj_class->get_property = get_property; pspec = g_param_spec_int64 ( "playlist-count", "Playlist count", "The number of items in the playlist", 0, G_MAXINT64, 0, G_PARAM_READABLE ); g_object_class_install_property(obj_class, PROP_PLAYLIST_COUNT, pspec); g_signal_new( "row-activated", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_gen_marshal_VOID__INT64, G_TYPE_NONE, 1, G_TYPE_INT ); g_signal_new( "row-inserted", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__INT, G_TYPE_NONE, 1, G_TYPE_INT ); g_signal_new( "row-deleted", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__INT, G_TYPE_NONE, 1, G_TYPE_INT ); g_signal_new( "rows-reordered", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_gen_marshal_VOID__INT_INT, G_TYPE_NONE, 2, G_TYPE_INT, G_TYPE_INT ); } static void gmpv_playlist_widget_init(GmpvPlaylistWidget *wgt) { wgt->playlist_count = 0; wgt->title_renderer = gtk_cell_renderer_text_new(); wgt->title_column = gtk_tree_view_column_new_with_attributes ( _("Playlist"), wgt->title_renderer, "text", PLAYLIST_NAME_COLUMN, "weight", PLAYLIST_WEIGHT_COLUMN, NULL ); wgt->dnd_delete = TRUE; gtk_widget_set_size_request (GTK_WIDGET(wgt), PLAYLIST_MIN_WIDTH, -1); gtk_tree_view_column_set_sizing (wgt->title_column, GTK_TREE_VIEW_COLUMN_AUTOSIZE); } GtkWidget *gmpv_playlist_widget_new() { return GTK_WIDGET(g_object_new(gmpv_playlist_widget_get_type(), NULL)); } gboolean gmpv_playlist_widget_empty(GmpvPlaylistWidget *wgt) { GtkTreeIter iter; return !gtk_tree_model_get_iter_first(GTK_TREE_MODEL(wgt->store), &iter); } void gmpv_playlist_widget_set_indicator_pos( GmpvPlaylistWidget *wgt, gint pos ) { GtkTreeIter iter; gboolean rc; rc = gtk_tree_model_get_iter_first(GTK_TREE_MODEL(wgt->store), &iter); while(rc) { const PangoWeight weight = (pos-- == 0)? PANGO_WEIGHT_BOLD: PANGO_WEIGHT_NORMAL; gtk_list_store_set( wgt->store, &iter, PLAYLIST_WEIGHT_COLUMN, weight, -1 ); rc = gtk_tree_model_iter_next(GTK_TREE_MODEL(wgt->store), &iter); } } void gmpv_playlist_widget_remove_selected(GmpvPlaylistWidget *wgt) { GtkTreePath *path = NULL; gtk_tree_view_get_cursor ( GTK_TREE_VIEW(wgt->tree_view), &path, NULL ); if(path) { GtkTreeIter iter; GtkTreeModel *model; model = GTK_TREE_MODEL(wgt->store); if(gtk_tree_model_get_iter(model, &iter, path)) { gtk_list_store_remove(wgt->store, &iter); } } } void gmpv_playlist_widget_queue_draw(GmpvPlaylistWidget *wgt) { gtk_widget_queue_draw(GTK_WIDGET(wgt)); gtk_widget_queue_draw(wgt->tree_view); } void gmpv_playlist_widget_update_contents( GmpvPlaylistWidget *wgt, GPtrArray* playlist ) { GtkListStore *store = wgt->store; gboolean iter_end = FALSE; GtkTreeIter iter; g_assert(playlist); g_signal_handlers_block_by_func(wgt->store, row_inserted_handler, wgt); g_signal_handlers_block_by_func(wgt->store, row_deleted_handler, wgt); iter_end = !gtk_tree_model_get_iter_first(GTK_TREE_MODEL(store), &iter); for(guint i = 0; i < playlist->len; i++) { GmpvPlaylistEntry *entry= g_ptr_array_index(playlist, i); gchar *uri = entry->filename; gchar *title = entry->title; gchar *name = title?g_strdup(title):get_name_from_path(uri); /* Overwrite current entry if it doesn't match the new value */ if(!iter_end) { gchar *old_name = NULL; gchar *old_uri = NULL; gboolean name_update = FALSE; gboolean uri_update = FALSE; gtk_tree_model_get( GTK_TREE_MODEL(store), &iter, PLAYLIST_NAME_COLUMN, &old_name, PLAYLIST_URI_COLUMN, &old_uri, -1 ); name_update = (g_strcmp0(name, old_name) != 0); uri_update = (g_strcmp0(uri, old_uri) != 0); /* Only set the name if either the title can be * retrieved or the name is unset. This preserves the * correct title if it becomes unavailable later such as * when restarting mpv. */ if(name_update && (!old_name || title || uri_update)) { gtk_list_store_set( store, &iter, PLAYLIST_NAME_COLUMN, name, -1 ); } if(uri_update) { gtk_list_store_set( store, &iter, PLAYLIST_URI_COLUMN, uri, -1 ); } iter_end = !gtk_tree_model_iter_next (GTK_TREE_MODEL(store), &iter); g_free(old_name); g_free(old_uri); } /* Append entries to the playlist if there are fewer entries in * the playlist widget than given playlist. */ else { gtk_list_store_append(store, &iter); gtk_list_store_set( store, &iter, PLAYLIST_NAME_COLUMN, name, -1 ); gtk_list_store_set( store, &iter, PLAYLIST_URI_COLUMN, uri, -1 ); wgt->playlist_count++; } g_free(name); } /* If there are more entries in the playlist widget than given playlist, * remove the excess entries from the playlist widget. */ if(!iter_end) { while(gtk_list_store_remove(store, &iter)) { wgt->playlist_count--; } } g_signal_handlers_unblock_by_func(wgt->store, row_inserted_handler, wgt); g_signal_handlers_unblock_by_func(wgt->store, row_deleted_handler, wgt); g_object_notify(G_OBJECT(wgt), "playlist-count"); } GPtrArray *gmpv_playlist_widget_get_contents(GmpvPlaylistWidget *wgt) { gboolean rc = TRUE; GtkTreeModel *model = GTK_TREE_MODEL(wgt->store); GtkTreeIter iter; GPtrArray *result = NULL; rc = gtk_tree_model_get_iter_first(model, &iter); result = g_ptr_array_new_full( 1, (GDestroyNotify) gmpv_playlist_entry_free ); while(rc) { gchar *uri = NULL; gchar *name = NULL; gtk_tree_model_get( model, &iter, PLAYLIST_URI_COLUMN, &uri, PLAYLIST_NAME_COLUMN, &name, -1 ); g_ptr_array_add(result, gmpv_playlist_entry_new(uri, name)); rc = gtk_tree_model_iter_next(model, &iter); } return result; } gnome-mpv-0.13/src/gmpv_playlist_widget.h000066400000000000000000000030431317030365200205370ustar00rootroot00000000000000/* * Copyright (c) 2014-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef PLAYLIST_WIDGET_H #define PLAYLIST_WIDGET_H #include #include #include #include "gmpv_metadata_cache.h" G_BEGIN_DECLS #define GMPV_TYPE_PLAYLIST_WIDGET (gmpv_playlist_widget_get_type ()) G_DECLARE_FINAL_TYPE(GmpvPlaylistWidget, gmpv_playlist_widget, GMPV, PLAYLIST_WIDGET, GtkScrolledWindow) GtkWidget *gmpv_playlist_widget_new(void); gboolean gmpv_playlist_widget_empty(GmpvPlaylistWidget *wgt); void gmpv_playlist_widget_set_indicator_pos(GmpvPlaylistWidget *wgt, gint pos); void gmpv_playlist_widget_remove_selected(GmpvPlaylistWidget *wgt); void gmpv_playlist_widget_queue_draw(GmpvPlaylistWidget *wgt); void gmpv_playlist_widget_update_contents( GmpvPlaylistWidget *wgt, GPtrArray* playlist ); GPtrArray *gmpv_playlist_widget_get_contents(GmpvPlaylistWidget *wgt); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_plugins_manager.c000066400000000000000000000240711317030365200205050ustar00rootroot00000000000000/* * Copyright (c) 2016-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include "gmpv_plugins_manager.h" #include "gmpv_plugins_manager_item.h" #include "gmpv_file_chooser.h" #include "gmpv_common.h" enum { PROP_0, PROP_PARENT, N_PROPERTIES }; struct _GmpvPluginsManager { GtkGrid parent; GtkWindow *parent_window; GtkWidget *list_box; GtkWidget *placeholder_label; GFileMonitor *monitor; gchar *directory; }; struct _GmpvPluginsManagerClass { GtkGridClass parent_class; }; G_DEFINE_TYPE(GmpvPluginsManager, gmpv_plugins_manager, GTK_TYPE_GRID) static void gmpv_plugins_manager_constructed(GObject *object); static void gmpv_plugins_manager_finalize(GObject *object); static void gmpv_plugins_manager_set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ); static void gmpv_plugins_manager_get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ); static void add_handler(GtkButton *button, gpointer data); static void drag_data_handler( GtkWidget *widget, GdkDragContext *context, gint x, gint y, GtkSelectionData *sel_data, guint info, guint time, gpointer data); static void changed_handler( GFileMonitor *monitor, GFile *file, GFile *other_file, GFileMonitorEvent event_type, gpointer data ); static void copy_file_to_directory(GmpvPluginsManager *pmgr, GFile *src); static void gmpv_plugins_manager_constructed(GObject *object) { GmpvPluginsManager *self = GMPV_PLUGINS_MANAGER(object); gchar *scripts_dir = get_scripts_dir_path(); gmpv_plugins_manager_set_directory(self, scripts_dir); g_free(scripts_dir); G_OBJECT_CLASS(gmpv_plugins_manager_parent_class)->constructed(object); } static void gmpv_plugins_manager_finalize(GObject *object) { GmpvPluginsManager *pmgr = GMPV_PLUGINS_MANAGER(object); g_clear_object(&pmgr->monitor); g_free(pmgr->directory); G_OBJECT_CLASS(gmpv_plugins_manager_parent_class)->finalize(object); } static void gmpv_plugins_manager_set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ) { GmpvPluginsManager *self = GMPV_PLUGINS_MANAGER(object); if(property_id == PROP_PARENT) { self->parent_window = g_value_get_pointer(value); } else { G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); } } static void gmpv_plugins_manager_get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ) { GmpvPluginsManager *self = GMPV_PLUGINS_MANAGER(object); if(property_id == PROP_PARENT) { g_value_set_pointer(value, self->parent_window); } else { G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); } } static void add_handler(GtkButton *button, gpointer data) { GmpvPluginsManager *pmgr = data; GmpvFileChooser *dialog = NULL; GtkFileFilter *filter; GtkFileChooser *chooser; GFile *src = NULL; dialog = gmpv_file_chooser_new( _("Add Lua Script"), pmgr->parent_window, GTK_FILE_CHOOSER_ACTION_OPEN ); filter = NULL; chooser = GTK_FILE_CHOOSER(dialog); filter = gtk_file_filter_new(); gtk_file_filter_set_name(filter, _("All Files")); gtk_file_filter_add_pattern(filter, "*"); gtk_file_chooser_add_filter(chooser, filter); filter = gtk_file_filter_new(); gtk_file_filter_set_name(filter, _("Lua Scripts")); gtk_file_filter_add_mime_type(filter, "text/x-lua"); gtk_file_chooser_add_filter(chooser, filter); gtk_file_chooser_set_filter(chooser, filter); if(gmpv_file_chooser_run(dialog) == GTK_RESPONSE_ACCEPT) { src = gtk_file_chooser_get_file(chooser); } gmpv_file_chooser_destroy(dialog); copy_file_to_directory(pmgr, src); g_clear_object(&src); } static void drag_data_handler( GtkWidget *widget, GdkDragContext *context, gint x, gint y, GtkSelectionData *sel_data, guint info, guint time, gpointer data) { gchar **uri_list = gtk_selection_data_get_uris(sel_data); g_assert(uri_list); for(gint i = 0; uri_list[i]; i++) { GFile *file = g_file_new_for_uri(uri_list[i]); copy_file_to_directory(data, file); g_clear_object(&file); } g_strfreev(uri_list); } static void changed_handler( GFileMonitor *monitor, GFile *file, GFile *other_file, GFileMonitorEvent event_type, gpointer data ) { GmpvPluginsManager *pmgr = data; GDir *dir = NULL; const gchar *filename = NULL; gboolean empty = TRUE; const GFileMonitorEvent mask = G_FILE_MONITOR_EVENT_CREATED| G_FILE_MONITOR_EVENT_DELETED| G_FILE_MONITOR_EVENT_UNMOUNTED; if(event_type&mask) { g_assert(pmgr->directory); dir = g_dir_open(pmgr->directory, 0, NULL); } if(dir) { GtkContainer *list_box; GList *iter; list_box = GTK_CONTAINER(pmgr->list_box); iter = gtk_container_get_children(list_box); while(iter) { gtk_widget_destroy(iter->data); iter = g_list_next(iter); } do { gchar *full_path; filename = g_dir_read_name(dir); full_path = g_build_filename (pmgr->directory, filename, NULL); if(g_file_test(full_path, G_FILE_TEST_IS_REGULAR)) { GtkWidget *item; item = gmpv_plugins_manager_item_new ( pmgr->parent_window, filename, full_path ); gtk_container_add (GTK_CONTAINER(pmgr->list_box), item); empty = FALSE; } g_free(full_path); } while(filename); gtk_widget_show_all(pmgr->list_box); gtk_widget_set_visible(pmgr->placeholder_label, empty); g_dir_close(dir); } } static void copy_file_to_directory(GmpvPluginsManager *pmgr, GFile *src) { gchar *dest_path = NULL; GFile *dest = NULL; GError *error = NULL; if(src) { g_assert(pmgr->directory); dest_path = g_build_filename( pmgr->directory, g_file_get_basename(src), NULL ); dest = g_file_new_for_path(dest_path); g_file_copy( src, dest, G_FILE_COPY_NONE, NULL, NULL, NULL, &error ); } if(error) { GtkWidget *error_dialog = NULL; gchar *src_path = NULL; src_path = g_file_get_path(src)?:g_file_get_uri(src); error_dialog = gtk_message_dialog_new ( pmgr->parent_window, GTK_DIALOG_MODAL| GTK_DIALOG_DESTROY_WITH_PARENT, GTK_MESSAGE_ERROR, GTK_BUTTONS_OK, _("Failed to copy file from '%s' " "to '%s'. Reason: %s"), src_path, dest_path, error->message ); g_warning( "Failed to copy file from '%s' to '%s'. " "Reason: %s", src_path, dest_path, error->message ); gtk_dialog_run(GTK_DIALOG(error_dialog)); gtk_widget_destroy(error_dialog); g_error_free(error); g_free(src_path); } g_clear_object(&dest); g_free(dest_path); } static void gmpv_plugins_manager_class_init(GmpvPluginsManagerClass *klass) { GObjectClass *obj_class = G_OBJECT_CLASS(klass); GParamSpec *pspec = NULL; obj_class->constructed = gmpv_plugins_manager_constructed; obj_class->finalize = gmpv_plugins_manager_finalize; obj_class->set_property = gmpv_plugins_manager_set_property; obj_class->get_property = gmpv_plugins_manager_get_property; pspec = g_param_spec_pointer ( "parent", "Parent", "Parent window for the dialogs", G_PARAM_CONSTRUCT_ONLY|G_PARAM_READWRITE ); g_object_class_install_property(obj_class, PROP_PARENT, pspec); } static void gmpv_plugins_manager_init(GmpvPluginsManager *pmgr) { GtkWidget *scrolled_window = gtk_scrolled_window_new(NULL, NULL); GtkWidget *overlay = gtk_overlay_new(); GtkWidget *add_button = gtk_button_new_with_label("+"); pmgr->list_box = gtk_list_box_new(); pmgr->placeholder_label = gtk_label_new(_("No Lua script found")); pmgr->parent_window = NULL; pmgr->monitor = NULL; pmgr->directory = NULL; g_signal_connect( add_button, "clicked", G_CALLBACK(add_handler), pmgr ); g_signal_connect( pmgr->list_box, "drag-data-received", G_CALLBACK(drag_data_handler), pmgr ); gtk_drag_dest_set( pmgr->list_box, GTK_DEST_DEFAULT_ALL, NULL, 0, GDK_ACTION_LINK ); gtk_drag_dest_add_uri_targets(pmgr->list_box); gtk_widget_set_hexpand(GTK_WIDGET(scrolled_window), TRUE); gtk_widget_set_vexpand(GTK_WIDGET(scrolled_window), TRUE); gtk_widget_set_tooltip_text(add_button, _("Add Lua Script")); gtk_widget_set_sensitive(pmgr->placeholder_label, FALSE); gtk_widget_set_no_show_all(pmgr->placeholder_label, TRUE); gtk_widget_show(pmgr->placeholder_label); gtk_container_add(GTK_CONTAINER(overlay), scrolled_window); gtk_overlay_add_overlay(GTK_OVERLAY(overlay), pmgr->placeholder_label); gtk_overlay_set_overlay_pass_through( GTK_OVERLAY(overlay), pmgr->placeholder_label, TRUE ); gtk_grid_attach( GTK_GRID(pmgr), overlay, 0, 0, 1, 1 ); gtk_grid_attach( GTK_GRID(pmgr), add_button, 0, 1, 1, 1 ); gtk_container_add(GTK_CONTAINER(scrolled_window), pmgr->list_box); } GtkWidget *gmpv_plugins_manager_new(GtkWindow *parent) { return g_object_new( gmpv_plugins_manager_get_type(), "parent", parent, NULL); } void gmpv_plugins_manager_set_directory( GmpvPluginsManager *pmgr, const gchar *path ) { GFile *directory = g_file_new_for_path(path); g_clear_object(&pmgr->monitor); g_free(pmgr->directory); pmgr->monitor = g_file_monitor_directory( directory, G_FILE_MONITOR_NONE, NULL, NULL ); pmgr->directory = g_strdup(path); if(pmgr->monitor) { g_signal_connect( pmgr->monitor, "changed", G_CALLBACK(changed_handler), pmgr ); changed_handler( pmgr->monitor, NULL, NULL, G_FILE_MONITOR_EVENT_CREATED, pmgr ); } else { g_warning("Failed to monitor directory %s", path); } g_object_unref(directory); } gnome-mpv-0.13/src/gmpv_plugins_manager.h000066400000000000000000000022441317030365200205100ustar00rootroot00000000000000/* * Copyright (c) 2016 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef PLUGINS_MANAGER_H #define PLUGINS_MANAGER_H #include #include #include G_BEGIN_DECLS #define GMPV_TYPE_PLUGINS_MANAGER (gmpv_plugins_manager_get_type ()) G_DECLARE_FINAL_TYPE(GmpvPluginsManager, gmpv_plugins_manager, GMPV, PLUGINS_MANAGER, GtkGrid) GtkWidget *gmpv_plugins_manager_new(GtkWindow *parent); void gmpv_plugins_manager_set_directory( GmpvPluginsManager *pmgr, const gchar *path ); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_plugins_manager_item.c000066400000000000000000000147451317030365200215320ustar00rootroot00000000000000/* * Copyright (c) 2016 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include #include #include "gmpv_plugins_manager_item.h" enum { PROP_0, PROP_PARENT, PROP_TITLE, PROP_PATH, N_PROPERTIES }; struct _GmpvPluginsManagerItem { GtkListBoxRow parent; GtkWindow *parent_window; gchar *title; gchar *path; }; struct _GmpvPluginsManagerItemClass { GtkListBoxRowClass parent_class; }; G_DEFINE_TYPE(GmpvPluginsManagerItem, gmpv_plugins_manager_item, GTK_TYPE_LIST_BOX_ROW) static void gmpv_plugins_manager_item_constructed(GObject *object); static void gmpv_plugins_manager_item_finalize(GObject *object); static void gmpv_plugins_manager_item_set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ); static void gmpv_plugins_manager_item_get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ); static void remove_handler(GtkButton *button, gpointer data); static void gmpv_plugins_manager_item_constructed(GObject *object) { GmpvPluginsManagerItem *self = GMPV_PLUGINS_MANAGER_ITEM(object); GtkWidget *box = gtk_box_new(GTK_ORIENTATION_HORIZONTAL, 0); GtkWidget *title_label = gtk_label_new(self->title); GtkWidget *remove_button = gtk_button_new_with_label(_("Remove")); g_signal_connect( remove_button, "clicked", G_CALLBACK(remove_handler), self ); gtk_widget_set_halign(title_label, GTK_ALIGN_START); gtk_label_set_ellipsize(GTK_LABEL(title_label), PANGO_ELLIPSIZE_END); gtk_list_box_row_set_selectable(GTK_LIST_BOX_ROW(self), FALSE); gtk_box_pack_start(GTK_BOX(box), title_label, TRUE, TRUE, 6); gtk_box_pack_end(GTK_BOX(box), remove_button, FALSE, FALSE, 0); gtk_container_add(GTK_CONTAINER(self), box); G_OBJECT_CLASS(gmpv_plugins_manager_item_parent_class) ->constructed(object); } static void gmpv_plugins_manager_item_finalize(GObject *object) { GmpvPluginsManagerItem *self = GMPV_PLUGINS_MANAGER_ITEM(object); g_free(self->title); g_free(self->path); G_OBJECT_CLASS(gmpv_plugins_manager_item_parent_class)->finalize(object); } static void gmpv_plugins_manager_item_set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ) { GmpvPluginsManagerItem *self = GMPV_PLUGINS_MANAGER_ITEM(object); if(property_id == PROP_PARENT) { self->parent_window = g_value_get_pointer(value); } else if(property_id == PROP_TITLE) { g_free(self->title); self->title = g_value_dup_string(value); } else if(property_id == PROP_PATH) { g_free(self->path); self->path = g_value_dup_string(value); } else { G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); } } static void gmpv_plugins_manager_item_get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ) { GmpvPluginsManagerItem *self = GMPV_PLUGINS_MANAGER_ITEM(object); if(property_id == PROP_PARENT) { g_value_set_pointer(value, self->parent_window); } else if(property_id == PROP_TITLE) { g_value_set_string(value, self->title); } else if(property_id == PROP_PATH) { g_value_set_string(value, self->path); } else { G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); } } static void remove_handler(GtkButton *button, gpointer data) { GmpvPluginsManagerItem *item = data; GFile *file = g_file_new_for_path(item->path); GError *error = NULL; GtkWidget *confirm_dialog = gtk_message_dialog_new ( item->parent_window, GTK_DIALOG_MODAL| GTK_DIALOG_DESTROY_WITH_PARENT, GTK_MESSAGE_QUESTION, GTK_BUTTONS_YES_NO, _("Are you sure you want to " "remove this script? This " "action cannot be undone.")); if(gtk_dialog_run(GTK_DIALOG(confirm_dialog)) == GTK_RESPONSE_YES) { g_file_delete(file, NULL, &error); } gtk_widget_destroy(confirm_dialog); if(error) { GtkWidget *error_dialog; error_dialog = gtk_message_dialog_new ( item->parent_window, GTK_DIALOG_MODAL| GTK_DIALOG_DESTROY_WITH_PARENT, GTK_MESSAGE_ERROR, GTK_BUTTONS_OK, _("Failed to delete file '%s'. " "Reason: %s"), g_file_get_uri(file), error->message ); g_warning( "Failed to delete file '%s'. Reason: %s", g_file_get_uri(file), error->message ); gtk_dialog_run(GTK_DIALOG(error_dialog)); gtk_widget_destroy(error_dialog); g_error_free(error); } } static void gmpv_plugins_manager_item_class_init(GmpvPluginsManagerItemClass *klass) { GObjectClass *obj_class = G_OBJECT_CLASS(klass); GParamSpec *pspec = NULL; obj_class->constructed = gmpv_plugins_manager_item_constructed; obj_class->finalize = gmpv_plugins_manager_item_finalize; obj_class->set_property = gmpv_plugins_manager_item_set_property; obj_class->get_property = gmpv_plugins_manager_item_get_property; pspec = g_param_spec_pointer ( "parent", "Parent", "Parent window for the dialogs", G_PARAM_CONSTRUCT_ONLY|G_PARAM_READWRITE ); g_object_class_install_property(obj_class, PROP_PARENT, pspec); pspec = g_param_spec_string ( "title", "Title", "The string to display as the title of the item", "", G_PARAM_CONSTRUCT_ONLY|G_PARAM_READWRITE ); g_object_class_install_property(obj_class, PROP_TITLE, pspec); pspec = g_param_spec_string ( "path", "Path", "The path to the file that this item references", "", G_PARAM_CONSTRUCT_ONLY|G_PARAM_READWRITE ); g_object_class_install_property(obj_class, PROP_PATH, pspec); } static void gmpv_plugins_manager_item_init(GmpvPluginsManagerItem *item) { item->parent_window = NULL; item->title = NULL; item->path = NULL; } GtkWidget *gmpv_plugins_manager_item_new( GtkWindow *parent, const gchar *title, const gchar *path ) { return GTK_WIDGET(g_object_new( gmpv_plugins_manager_item_get_type(), "parent", parent, "title", title, "path", path, NULL)); } gnome-mpv-0.13/src/gmpv_plugins_manager_item.h000066400000000000000000000022501317030365200215230ustar00rootroot00000000000000/* * Copyright (c) 2016 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef PLUGINS_MANAGER_ITEM_H #define PLUGINS_MANAGER_ITEM_H #include #include #include G_BEGIN_DECLS #define GMPV_TYPE_PLUGINS_MANAGER_ITEM (gmpv_plugins_manager_item_get_type ()) G_DECLARE_FINAL_TYPE(GmpvPluginsManagerItem, gmpv_plugins_manager_item, GMPV, PLUGINS_MANAGER_ITEM, GtkListBoxRow) GtkWidget *gmpv_plugins_manager_item_new( GtkWindow *parent, const gchar *title, const gchar *path ); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_preferences_dialog.c000066400000000000000000000246111317030365200211520ustar00rootroot00000000000000/* * Copyright (c) 2014-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include #include #include "gmpv_preferences_dialog.h" #include "gmpv_plugins_manager.h" #include "gmpv_main_window.h" #include "gmpv_def.h" typedef struct PreferencesDialogItem PreferencesDialogItem; typedef enum PreferencesDialogItemType PreferencesDialogItemType; struct _GmpvPreferencesDialog { GtkDialog parent_instance; GSettings *settings; GtkWidget *notebook; }; struct _GmpvPreferencesDialogClass { GtkDialogClass parent_class; }; enum PreferencesDialogItemType { ITEM_TYPE_INVALID, ITEM_TYPE_GROUP, ITEM_TYPE_CHECK_BOX, ITEM_TYPE_FILE_CHOOSER, ITEM_TYPE_LABEL, ITEM_TYPE_TEXT_BOX }; struct PreferencesDialogItem { const gchar *label; const gchar *key; PreferencesDialogItemType type; }; G_DEFINE_TYPE(GmpvPreferencesDialog, gmpv_preferences_dialog, GTK_TYPE_DIALOG) static void file_set_handler(GtkFileChooserButton *widget, gpointer data) { GtkWidget *toplevel = gtk_widget_get_toplevel(GTK_WIDGET(widget)); GmpvPreferencesDialog *dlg = GMPV_PREFERENCES_DIALOG(toplevel); GtkFileChooser *chooser = GTK_FILE_CHOOSER(widget); const gchar *key = data; gchar *filename = gtk_file_chooser_get_filename(chooser)?:g_strdup(""); g_settings_set_string(dlg->settings, key, filename); g_free(filename); } static void response_handler(GtkDialog *dialog, gint response_id) { GmpvPreferencesDialog *dlg = GMPV_PREFERENCES_DIALOG(dialog); if(response_id == GTK_RESPONSE_ACCEPT) { g_settings_apply(dlg->settings); } else { g_settings_revert(dlg->settings); } g_object_unref(dlg->settings); } static gboolean key_press_handler(GtkWidget *widget, GdkEventKey *event) { guint keyval = event->keyval; guint state = event->state; const guint mod_mask = GDK_MODIFIER_MASK &~(GDK_SHIFT_MASK |GDK_LOCK_MASK |GDK_MOD2_MASK |GDK_MOD3_MASK |GDK_MOD4_MASK |GDK_MOD5_MASK); if((state&mod_mask) == 0 && keyval == GDK_KEY_Return) { gtk_dialog_response(GTK_DIALOG(widget), GTK_RESPONSE_ACCEPT); } return GTK_WIDGET_CLASS(gmpv_preferences_dialog_parent_class) ->key_press_event(widget, event); } static GtkWidget *build_page( const PreferencesDialogItem *items, GSettings *settings ) { GtkWidget *grid = gtk_grid_new(); gtk_container_set_border_width(GTK_CONTAINER(grid), 12); gtk_grid_set_row_spacing(GTK_GRID(grid), 6); gtk_grid_set_column_spacing(GTK_GRID(grid), 12); for(gint i = 0; items[i].type != ITEM_TYPE_INVALID; i++) { const gchar *label = items[i].label; const gchar *key = items[i].key; const PreferencesDialogItemType type = items[i].type; GtkWidget *widget = NULL; gboolean separate_label = FALSE; gint width = 1; gint xpos = 0; if(type == ITEM_TYPE_GROUP) { widget = gtk_label_new(label); width = 2; gtk_label_set_use_markup(GTK_LABEL(widget), TRUE); gtk_widget_set_halign(widget, GTK_ALIGN_START); gtk_widget_set_margin_top(widget, 12); } else if(type == ITEM_TYPE_CHECK_BOX) { widget = gtk_check_button_new_with_label(label); width = 2; g_settings_bind( settings, key, widget, "active", G_SETTINGS_BIND_DEFAULT ); } else if(type == ITEM_TYPE_FILE_CHOOSER) { GtkFileChooser *chooser; GtkFileFilter *filter; gchar *filename; widget = gtk_file_chooser_button_new (label, GTK_FILE_CHOOSER_ACTION_OPEN); chooser = GTK_FILE_CHOOSER(widget); filter = gtk_file_filter_new(); filename = g_settings_get_string(settings, key); separate_label = TRUE; xpos = 1; gtk_file_filter_add_mime_type(filter, "text/plain"); gtk_file_chooser_set_filter(chooser, filter); gtk_widget_set_hexpand(widget, TRUE); gtk_widget_set_size_request(widget, 100, -1); gtk_file_chooser_set_filename(chooser, filename); /* For simplicity, changes made to the GSettings * database externally won't be reflected immediately * for this type of widget. */ g_signal_connect_data( widget, "file-set", G_CALLBACK(file_set_handler), g_strdup(key), (GClosureNotify)g_free, 0 ); g_free(filename); } else if(type == ITEM_TYPE_TEXT_BOX) { widget = gtk_entry_new(); separate_label = TRUE; xpos = 1; gtk_widget_set_hexpand(widget, TRUE); g_settings_bind( settings, key, widget, "text", G_SETTINGS_BIND_DEFAULT ); } else if(type == ITEM_TYPE_LABEL) { widget = gtk_label_new(label); gtk_widget_set_halign(widget, GTK_ALIGN_START); } g_assert(widget); g_assert(xpos == 0 || xpos == 1); if(i == 0) { gtk_widget_set_margin_top(widget, 0); } if(type != ITEM_TYPE_GROUP) { gtk_widget_set_margin_start(widget, 12); } /* Expand the widget to fill both columns if it usually needs a * separate label but none is provided. */ if(separate_label && !label) { width = 2; xpos = 0; } gtk_grid_attach(GTK_GRID(grid), widget, xpos, i, width, 1); if(separate_label && label) { GtkWidget *label_widget = gtk_label_new(label); /* The grid should only have 2 columns, so the previous * widget connot be wider than 1 column if it needs a * seperate label. */ g_assert(width == 1); gtk_grid_attach( GTK_GRID(grid), label_widget, 1-xpos, i, 1, 1 ); gtk_widget_set_halign(label_widget, GTK_ALIGN_START); gtk_widget_set_hexpand(label_widget, FALSE); gtk_widget_set_margin_start(label_widget, 12); } } return grid; } static void preferences_dialog_constructed(GObject *obj) { gboolean csd_enabled; g_object_get(obj, "use-header-bar", &csd_enabled, NULL); if(!csd_enabled) { GtkWidget *content_area; GtkWidget *notebook; content_area = gtk_dialog_get_content_area(GTK_DIALOG(obj)); notebook = GMPV_PREFERENCES_DIALOG(obj)->notebook; gtk_widget_set_margin_bottom(content_area, 12); gtk_widget_set_margin_bottom(notebook, 6); } G_OBJECT_CLASS(gmpv_preferences_dialog_parent_class)->constructed(obj); } static void gmpv_preferences_dialog_class_init(GmpvPreferencesDialogClass *klass) { GtkWidgetClass *wid_class = GTK_WIDGET_CLASS(klass); wid_class->key_press_event = key_press_handler; GTK_DIALOG_CLASS(klass)->response = response_handler; G_OBJECT_CLASS(klass)->constructed = preferences_dialog_constructed; } static void gmpv_preferences_dialog_init(GmpvPreferencesDialog *dlg) { const PreferencesDialogItem general_items[] = { {_("User Interface"), NULL, ITEM_TYPE_GROUP}, {_("Enable client-side decorations"), "csd-enable", ITEM_TYPE_CHECK_BOX}, {_("Enable dark theme"), "dark-theme-enable", ITEM_TYPE_CHECK_BOX}, {_("Use floating controls in windowed mode"), "always-use-floating-controls", ITEM_TYPE_CHECK_BOX}, {_("Remember last file's location"), "last-folder-enable", ITEM_TYPE_CHECK_BOX}, {_("MPV Configuration"), NULL, ITEM_TYPE_GROUP}, {_("Load MPV configuration file"), "mpv-config-enable", ITEM_TYPE_CHECK_BOX}, {_("MPV configuration file:"), "mpv-config-file", ITEM_TYPE_FILE_CHOOSER}, {_("Keybindings"), NULL, ITEM_TYPE_GROUP}, {_("Load MPV input configuration file"), "mpv-input-config-enable", ITEM_TYPE_CHECK_BOX}, {_("MPV input configuration file:"), "mpv-input-config-file", ITEM_TYPE_FILE_CHOOSER}, {_("Miscellaneous"), NULL, ITEM_TYPE_GROUP}, {_("Always open new window"), "always-open-new-window", ITEM_TYPE_CHECK_BOX}, {_("Prefetch metadata"), "prefetch-metadata", ITEM_TYPE_CHECK_BOX}, {_("Enable MPRIS support"), "mpris-enable", ITEM_TYPE_CHECK_BOX}, {_("Enable media keys support"), "media-keys-enable", ITEM_TYPE_CHECK_BOX}, {_("Extra MPV options:"), NULL, ITEM_TYPE_LABEL}, {NULL, "mpv-options", ITEM_TYPE_TEXT_BOX}, {NULL, NULL, ITEM_TYPE_INVALID} }; GtkWidget *content_area; GdkGeometry geom; /* This 'locks' the height of the dialog while allowing the width to be * freely adjusted. */ geom.max_width = G_MAXINT; geom.max_height = 0; dlg->settings = g_settings_new(CONFIG_ROOT); dlg->notebook = gtk_notebook_new(); content_area = gtk_dialog_get_content_area(GTK_DIALOG(dlg)); g_settings_delay(dlg->settings); gtk_window_set_geometry_hints( GTK_WINDOW(dlg), GTK_WIDGET(dlg), &geom, GDK_HINT_MAX_SIZE ); gtk_container_set_border_width(GTK_CONTAINER(content_area), 0); gtk_container_add(GTK_CONTAINER(content_area), dlg->notebook); gtk_notebook_append_page( GTK_NOTEBOOK(dlg->notebook), build_page(general_items, dlg->settings), gtk_label_new(_("General")) ); gtk_notebook_append_page( GTK_NOTEBOOK(dlg->notebook), gmpv_plugins_manager_new(GTK_WINDOW(dlg)), gtk_label_new(_("Lua Scripts")) ); gtk_dialog_add_buttons( GTK_DIALOG(dlg), _("_Cancel"), GTK_RESPONSE_REJECT, _("_Save"), GTK_RESPONSE_ACCEPT, NULL ); gtk_dialog_set_default_response(GTK_DIALOG(dlg), GTK_RESPONSE_ACCEPT); } GtkWidget *gmpv_preferences_dialog_new(GtkWindow *parent) { GtkWidget *dlg; GtkWidget *header_bar; gboolean csd_enabled; csd_enabled = gmpv_main_window_get_csd_enabled(GMPV_MAIN_WINDOW(parent)); dlg = g_object_new( gmpv_preferences_dialog_get_type(), "title", _("Preferences"), "modal", TRUE, "transient-for", parent, "use-header-bar", csd_enabled, NULL ); header_bar = gtk_dialog_get_header_bar(GTK_DIALOG(dlg)); if(header_bar) { /* The defaults use PACK_END which is ugly with multiple buttons */ GtkWidget *cancel_btn = gtk_dialog_get_widget_for_response (GTK_DIALOG(dlg), GTK_RESPONSE_REJECT); gtk_container_child_set( GTK_CONTAINER(header_bar), cancel_btn, "pack-type", GTK_PACK_START, NULL ); gtk_header_bar_set_show_close_button (GTK_HEADER_BAR(header_bar), FALSE); } gtk_widget_hide_on_delete(dlg); gtk_widget_show_all(dlg); return dlg; } gnome-mpv-0.13/src/gmpv_preferences_dialog.h000066400000000000000000000021451317030365200211550ustar00rootroot00000000000000/* * Copyright (c) 2014-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef PREFERENCES_DIALOG_H #define PREFERENCES_DIALOG_H #include #include #include G_BEGIN_DECLS #define GMPV_TYPE_PREFERENCES_DIALOG (gmpv_preferences_dialog_get_type ()) G_DECLARE_FINAL_TYPE(GmpvPreferencesDialog, gmpv_preferences_dialog, GMPV, PREFERENCES_DIALOG, GtkDialog) GtkWidget *gmpv_preferences_dialog_new(GtkWindow *parent); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_seek_bar.c000066400000000000000000000066611317030365200171120ustar00rootroot00000000000000/* * Copyright (c) 2016 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include "gmpv_seek_bar.h" struct _GmpvSeekBar { GtkBox parent_instance; GtkWidget *seek_bar; GtkWidget *label; gdouble pos; gdouble duration; }; struct _GmpvSeekBarClass { GtkBoxClass parent_class; }; static void change_value_handler( GtkWidget *widget, GtkScrollType scroll, gdouble value, gpointer data ); static void update_label(GmpvSeekBar *bar); G_DEFINE_TYPE(GmpvSeekBar, gmpv_seek_bar, GTK_TYPE_BOX) static void change_value_handler( GtkWidget *widget, GtkScrollType scroll, gdouble value, gpointer data ) { GmpvSeekBar *bar = data; if(bar->duration > 0) { update_label(data); g_signal_emit_by_name(data, "seek", value); } } static void update_label(GmpvSeekBar *bar) { gint sec = (gint)bar->pos; gint duration = (gint)bar->duration; gchar *output; /* Longer than one hour */ if(duration > 3600) { output = g_strdup_printf( "%02d:%02d:%02d/" "%02d:%02d:%02d", sec/3600, (sec%3600)/60, sec%60, duration/3600, (duration%3600)/60, duration%60 ); } else if(duration > 0) { output = g_strdup_printf( "%02d:%02d/" "%02d:%02d", (sec%3600)/60, sec%60, (duration%3600)/60, duration%60 ); } else { output = g_strdup_printf("%02d:%02d", (sec%3600)/60, sec%60); } gtk_label_set_text(GTK_LABEL(bar->label), output); } static void gmpv_seek_bar_class_init(GmpvSeekBarClass *klass) { g_signal_new( "seek", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__DOUBLE, G_TYPE_NONE, 1, G_TYPE_DOUBLE ); } static void gmpv_seek_bar_init(GmpvSeekBar *bar) { bar->seek_bar = gtk_scale_new(GTK_ORIENTATION_HORIZONTAL, NULL); bar->label = gtk_label_new(""); bar->duration = 0; bar->pos = 0; update_label(bar); gtk_scale_set_draw_value(GTK_SCALE(bar->seek_bar), FALSE); gtk_range_set_increments(GTK_RANGE(bar->seek_bar), 10, 10); gtk_widget_set_can_focus(bar->seek_bar, FALSE); g_signal_connect( bar->seek_bar, "change-value", G_CALLBACK(change_value_handler), bar ); gtk_box_pack_start(GTK_BOX(bar), bar->seek_bar, TRUE, TRUE, 0); gtk_box_pack_end(GTK_BOX(bar), bar->label, FALSE, FALSE, 0); } GtkWidget *gmpv_seek_bar_new() { return GTK_WIDGET(g_object_new(gmpv_seek_bar_get_type(), NULL)); } void gmpv_seek_bar_set_duration(GmpvSeekBar *bar, gdouble duration) { bar->duration = duration; update_label(bar); gtk_range_set_range(GTK_RANGE(bar->seek_bar), 0, duration); } void gmpv_seek_bar_set_pos(GmpvSeekBar *bar, gdouble pos) { gdouble old_pos = bar->pos; bar->pos = pos; gtk_range_set_value(GTK_RANGE(bar->seek_bar), pos); if((gint)old_pos != (gint)pos) { update_label(bar); } } gnome-mpv-0.13/src/gmpv_seek_bar.h000066400000000000000000000021771317030365200171150ustar00rootroot00000000000000/* * Copyright (c) 2016 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef SEEK_BAR_H #define SEEK_BAR_H #include #include #include G_BEGIN_DECLS #define GMPV_TYPE_SEEK_BAR (gmpv_seek_bar_get_type()) G_DECLARE_FINAL_TYPE(GmpvSeekBar, gmpv_seek_bar, GMPV, SEEK_BAR, GtkBox) GtkWidget *gmpv_seek_bar_new(void); void gmpv_seek_bar_set_duration(GmpvSeekBar *bar, gdouble duration); void gmpv_seek_bar_set_pos(GmpvSeekBar *bar, gdouble pos); G_END_DECLS #endif gnome-mpv-0.13/src/gmpv_shortcuts_window.c000066400000000000000000000133341317030365200207570ustar00rootroot00000000000000/* * Copyright (c) 2016 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include "gmpv_shortcuts_window.h" struct _GmpvShortcutsWindow { GtkShortcutsWindow parent; }; struct _GmpvShortcutsWindowClass { GtkShortcutsWindowClass parent_class; }; struct ShortcutEntry { const gchar *accel; const gchar *title; }; struct ShortcutGroup { const gchar *title; const struct ShortcutEntry *entries; }; typedef struct ShortcutEntry ShortcutEntry; typedef struct ShortcutGroup ShortcutGroup; G_DEFINE_TYPE(GmpvShortcutsWindow, gmpv_shortcuts_window, GTK_TYPE_SHORTCUTS_WINDOW) static void gmpv_shortcuts_window_init(GmpvShortcutsWindow *wnd) { const ShortcutEntry general[] = { {"o", _("Open file")}, {"l", _("Open location")}, {"o", _("Add file to playlist")}, {"l", _("Add location to playlist")}, {"p", _("Show preferences dialog")}, {"h", _("Toggle controls")}, {"F9", _("Toggle playlist")}, {"F11 f", _("Toggle fullscreen mode")}, {"Escape", _("Leave fullscreen mode")}, {"o", _("Toggle OSD states between normal and playback time/duration")}, {"i", _("Show filename on the OSD")}, {"o p", _("Show progress, elapsed time, and duration on the OSD")}, {NULL, NULL} }; const ShortcutEntry seeking[] = { {"leftarrow rightarrow", _("Seek backward/forward 5 seconds")}, {"leftarrow rightarrow", _("Exact seek backward/forward 1 second")}, {"downarrow uparrow", _("Seek backward/forward 1 minute")}, {"downarrow uparrow", _("Exact seek backward/forward 5 seconds")}, {"leftarrow rightarrow", _("Seek to previous/next subtitle")}, {"comma period", _("Step backward/forward a single frame")}, {"Page_Up Page_Down", _("Seek to the beginning of the previous/next chapter")}, {NULL, NULL} }; const ShortcutEntry playback[] = { {"bracketleft bracketright", _("Decrease/increase playback speed by 10%")}, {"braceleft braceright", _("Halve/double current playback speed")}, {"BackSpace", _("Reset playback speed to normal")}, {"less greater", _("Go backward/forward in the playlist")}, {"Delete", _("Remove selected playlist item")}, {"s", _("Save playlist")}, {"l", _("Set/clear A-B loop points")}, {"l", _("Toggle infinite looping")}, {"p space", _("Pause or unpause")}, {"q q", _("Quit")}, {"q", _("Save current playback position and quit")}, {NULL, NULL} }; const ShortcutEntry audio[] = { {"numbersign", _("Cycle through audio tracks")}, {"slash asterisk", _("Decrease/increase volume")}, {"9 0", _("Decrease/increase volume")}, {"m", _("Mute or unmute")}, {"plus minus", _("Adjust audio delay by +/- 0.1 seconds")}, {NULL, NULL} }; const ShortcutEntry subtitle[] = { {"v", _("Toggle subtitle visibility")}, {"i j", _("Cycle through available subtitles")}, {"x z", _("Adjust subtitle delay by +/- 0.1 seconds")}, {"u", _("Toggle SSA/ASS subtitles style override")}, {"r t", _("Move subtitles up/down")}, {"v", _("Toggle VSFilter aspect compatibility mode")}, {NULL, NULL} }; const ShortcutEntry video[] = { {"underscore", _("Cycle through video tracks")}, {"w e", _("Decrease/increase pan-and-scan range")}, {"s", _("Take a screenshot")}, {"s", _("Take a screenshot, without subtitles")}, {"s", _("Take a screenshot, as the window shows it")}, {"0", _("Resize video to half its original size")}, {"1", _("Resize video to its original size")}, {"2", _("Resize video to double its original size")}, {"1 2", _("Adjust contrast")}, {"3 4", _("Adjust brightness")}, {"5 6", _("Adjust gamma")}, {"7 8", _("Adjust saturation")}, {"d", _("Activate or deactivate deinterlacer")}, {"a", _("Cycle aspect ratio override")}, {NULL, NULL} }; const ShortcutGroup groups[] = { {_("User Interface"), general}, {_("Video"), video}, {_("Audio"), audio}, {_("Subtitle"), subtitle}, {_("Playback"), playback}, {_("Seeking"), seeking}, {NULL, NULL} }; GtkWidget *section = g_object_new ( gtk_shortcuts_section_get_type(), "section-name", "shortcuts", "visible", TRUE, NULL ); for(gint i = 0; groups[i].title; i++) { const ShortcutEntry *entries = groups[i].entries; GtkWidget *group = g_object_new ( gtk_shortcuts_group_get_type(), "title", groups[i].title, NULL ); for(gint j = 0; entries[j].accel; j++) { GtkWidget *entry; entry = g_object_new ( gtk_shortcuts_shortcut_get_type(), "accelerator", entries[j].accel, "title", entries[j].title, NULL ); gtk_container_add(GTK_CONTAINER(group), entry); } gtk_container_add(GTK_CONTAINER(section), group); } gtk_container_add(GTK_CONTAINER(wnd), section); } static void gmpv_shortcuts_window_class_init(GmpvShortcutsWindowClass *klass) { } GtkWidget *gmpv_shortcuts_window_new(GtkWindow *parent) { return GTK_WIDGET(g_object_new( gmpv_shortcuts_window_get_type(), "transient-for", parent, "modal", TRUE, NULL)); } gnome-mpv-0.13/src/gmpv_shortcuts_window.h000066400000000000000000000022021317030365200207540ustar00rootroot00000000000000/* * Copyright (c) 2016 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef SHORTCUTS_WINDOW_H #define SHORTCUTS_WINDOW_H #if GTK_CHECK_VERSION(3, 20, 0) #include #include #include G_BEGIN_DECLS #define GMPV_TYPE_SHORTCUTS_WINDOW (gmpv_shortcuts_window_get_type ()) G_DECLARE_FINAL_TYPE(GmpvShortcutsWindow, gmpv_shortcuts_window, GMPV, SHORTCUTS_WINDOW, GtkShortcutsWindow) GtkWidget *gmpv_shortcuts_window_new(GtkWindow *parent); G_END_DECLS #endif #endif gnome-mpv-0.13/src/gmpv_video_area.c000066400000000000000000000274751317030365200174430ustar00rootroot00000000000000/* * Copyright (c) 2016-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include "gmpv_video_area.h" #include "gmpv_header_bar.h" #include "gmpv_control_box.h" #include "gmpv_def.h" #include #include #include #ifdef GDK_WINDOWING_X11 #include #endif enum { PROP_0, PROP_TITLE, N_PROPERTIES }; struct _GmpvVideoArea { GtkOverlay parent_instance; GtkWidget *stack; GtkWidget *draw_area; GtkWidget *gl_area; GtkWidget *control_box; GtkWidget *header_bar; GtkWidget *control_box_revealer; GtkWidget *header_bar_revealer; guint timeout_tag; gboolean fullscreen; gboolean fs_control_hover; }; struct _GmpvVideoAreaClass { GtkOverlayClass parent_class; }; static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ); static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ); static void destroy(GtkWidget *widget); static void set_cursor_visible(GmpvVideoArea *area, gboolean visible); static gboolean timeout_handler(gpointer data); static gboolean motion_notify_event(GtkWidget *widget, GdkEventMotion *event); static gboolean fs_control_crossing_handler( GtkWidget *widget, GdkEventCrossing *event, gpointer data ); G_DEFINE_TYPE(GmpvVideoArea, gmpv_video_area, GTK_TYPE_OVERLAY) static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ) { GmpvVideoArea *self = GMPV_VIDEO_AREA(object); switch(property_id) { case PROP_TITLE: g_object_set_property( G_OBJECT(self->header_bar), pspec->name, value ); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ) { GmpvVideoArea *self = GMPV_VIDEO_AREA(object); switch(property_id) { case PROP_TITLE: g_object_get_property( G_OBJECT(self->header_bar), pspec->name, value ); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void destroy(GtkWidget *widget) { GmpvVideoArea *area = GMPV_VIDEO_AREA(widget); if(area->timeout_tag > 0) { g_source_remove(area->timeout_tag); area->timeout_tag = 0; } } static void set_cursor_visible(GmpvVideoArea *area, gboolean visible) { GdkWindow *window; GdkCursor *cursor; window = gtk_widget_get_window(GTK_WIDGET(area)); if(visible) { cursor = gdk_cursor_new_from_name (gdk_display_get_default(), "default"); } else { cursor = gdk_cursor_new_for_display (gdk_display_get_default(), GDK_BLANK_CURSOR); } gdk_window_set_cursor(window, cursor); g_object_unref(cursor); } static gboolean timeout_handler(gpointer data) { GmpvVideoArea *area = data; GmpvControlBox *control_box = GMPV_CONTROL_BOX(area->control_box); GmpvHeaderBar *header_bar = GMPV_HEADER_BAR(area->header_bar); if(control_box && !area->fs_control_hover && !gmpv_control_box_get_volume_popup_visible(control_box) && !gmpv_header_bar_get_open_button_popup_visible(header_bar) && !gmpv_header_bar_get_menu_button_popup_visible(header_bar)) { gtk_revealer_set_reveal_child (GTK_REVEALER(area->control_box_revealer), FALSE); gtk_revealer_set_reveal_child (GTK_REVEALER(area->header_bar_revealer), FALSE); set_cursor_visible(area, !area->fullscreen); area->timeout_tag = 0; } else if(!control_box) { area->timeout_tag = 0; } /* Try again later if timeout_tag has not been cleared. This means that * either one of the popups is visible or the cursor is hovering over * the control box, preventing it from being hidden. */ return (area->timeout_tag != 0); } static gboolean motion_notify_event(GtkWidget *widget, GdkEventMotion *event) { GmpvVideoArea *area = GMPV_VIDEO_AREA(widget); GdkCursor *cursor; cursor = gdk_cursor_new_from_name(gdk_display_get_default(), "default"); gdk_window_set_cursor(gtk_widget_get_window(widget), cursor); if(area->control_box) { gtk_revealer_set_reveal_child (GTK_REVEALER(area->control_box_revealer), TRUE); gtk_revealer_set_reveal_child (GTK_REVEALER(area->header_bar_revealer), area->fullscreen); } if(area->timeout_tag > 0) { g_source_remove(area->timeout_tag); area->timeout_tag = 0; } area->timeout_tag = g_timeout_add_seconds( FS_CONTROL_HIDE_DELAY, timeout_handler, area ); return GTK_WIDGET_CLASS(gmpv_video_area_parent_class) ->motion_notify_event(widget, event); } static gboolean render_handler( GtkGLArea *gl_area, GdkGLContext *context, gpointer data ) { g_signal_emit_by_name(data, "render"); return TRUE; } static void notify_handler( GObject *gobject, GParamSpec *pspec, gpointer data ) { /* Due to a GTK+ bug, the header bar isn't hidden completely if hidden * by a GtkRevealer. Workaround this by manually hiding the revealer * along with the header bar when the revealer completes its transition * to hidden state. */ GmpvVideoArea *area = data; gboolean reveal_child = TRUE; gboolean child_revealed = TRUE; g_object_get( gobject, "reveal-child", &reveal_child, "child-revealed", &child_revealed, NULL ); gtk_widget_set_visible( GTK_WIDGET(area->header_bar_revealer), area->fullscreen && (reveal_child || child_revealed) ); } static gboolean fs_control_crossing_handler( GtkWidget *widget, GdkEventCrossing *event, gpointer data ) { GMPV_VIDEO_AREA(data)->fs_control_hover = (event->type == GDK_ENTER_NOTIFY); return FALSE; } static void gmpv_video_area_class_init(GmpvVideoAreaClass *klass) { GObjectClass *obj_class = G_OBJECT_CLASS(klass); GtkWidgetClass *wgt_class = GTK_WIDGET_CLASS(klass); GParamSpec *pspec = NULL; obj_class->set_property = set_property; obj_class->get_property = get_property; wgt_class->destroy = destroy; wgt_class->motion_notify_event = motion_notify_event; g_signal_new( "render", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__VOID, G_TYPE_NONE, 0 ); pspec = g_param_spec_string ( "title", "Title", "The title of the header bar", NULL, G_PARAM_READWRITE ); g_object_class_install_property(obj_class, PROP_TITLE, pspec); } static void gmpv_video_area_init(GmpvVideoArea *area) { GtkTargetEntry targets[] = DND_TARGETS; /* GDK_BUTTON_RELEASE_MASK is needed so that GtkMenuButtons can * hide their menus when vid_area is clicked. */ const gint extra_events = GDK_BUTTON_PRESS_MASK| GDK_BUTTON_RELEASE_MASK| GDK_POINTER_MOTION_MASK| GDK_SMOOTH_SCROLL_MASK| GDK_SCROLL_MASK; area->stack = gtk_stack_new(); area->draw_area = gtk_drawing_area_new(); area->gl_area = gtk_gl_area_new(); area->control_box = gmpv_control_box_new(); area->header_bar = gmpv_header_bar_new(); area->control_box_revealer = gtk_revealer_new(); area->header_bar_revealer = gtk_revealer_new(); area->timeout_tag = 0; area->fullscreen = FALSE; area->fs_control_hover = FALSE; gtk_style_context_add_class ( gtk_widget_get_style_context(area->draw_area), "gmpv-vid-area" ); gtk_drag_dest_set( GTK_WIDGET(area), GTK_DEST_DEFAULT_ALL, targets, G_N_ELEMENTS(targets), GDK_ACTION_COPY ); gtk_widget_add_events(area->draw_area, extra_events); gtk_widget_add_events(area->gl_area, extra_events); gtk_widget_set_valign(area->control_box_revealer, GTK_ALIGN_END); gtk_revealer_set_reveal_child (GTK_REVEALER(area->control_box_revealer), FALSE); gtk_widget_set_valign(area->header_bar_revealer, GTK_ALIGN_START); gtk_revealer_set_reveal_child (GTK_REVEALER(area->header_bar_revealer), FALSE); gtk_widget_show_all(area->control_box); gtk_widget_hide(area->control_box_revealer); gtk_widget_set_no_show_all(area->control_box_revealer, TRUE); gtk_widget_show_all(area->header_bar); gtk_widget_hide(area->header_bar_revealer); gtk_widget_set_no_show_all(area->header_bar_revealer, TRUE); g_signal_connect( area->gl_area, "render", G_CALLBACK(render_handler), area ); g_signal_connect( area->header_bar_revealer, "notify::reveal-child", G_CALLBACK(notify_handler), area ); g_signal_connect( area->header_bar_revealer, "notify::child-revealed", G_CALLBACK(notify_handler), area ); g_signal_connect( area, "enter-notify-event", G_CALLBACK(fs_control_crossing_handler), area ); g_signal_connect( area, "leave-notify-event", G_CALLBACK(fs_control_crossing_handler), area ); gtk_stack_add_named(GTK_STACK(area->stack), area->draw_area, "draw"); gtk_stack_add_named(GTK_STACK(area->stack), area->gl_area, "gl"); gtk_stack_set_visible_child(GTK_STACK(area->stack), area->draw_area); gtk_container_add( GTK_CONTAINER(area->header_bar_revealer), area->header_bar ); gtk_container_add( GTK_CONTAINER(area->control_box_revealer), area->control_box ); gtk_overlay_add_overlay(GTK_OVERLAY(area), area->control_box_revealer); gtk_overlay_add_overlay(GTK_OVERLAY(area), area->header_bar_revealer); gtk_container_add(GTK_CONTAINER(area), area->stack); } GtkWidget *gmpv_video_area_new() { return GTK_WIDGET(g_object_new(gmpv_video_area_get_type(), NULL)); } void gmpv_video_area_update_track_list( GmpvVideoArea *area, const GPtrArray *track_list ) { gmpv_header_bar_update_track_list (GMPV_HEADER_BAR(area->header_bar), track_list); } void gmpv_video_area_set_fullscreen_state( GmpvVideoArea *area, gboolean fullscreen ) { if(area->fullscreen != fullscreen) { area->fullscreen = fullscreen; gtk_widget_hide(area->header_bar_revealer); set_cursor_visible(area, !fullscreen); gtk_revealer_set_reveal_child (GTK_REVEALER(area->control_box_revealer), FALSE); gtk_revealer_set_reveal_child (GTK_REVEALER(area->header_bar_revealer), FALSE); gmpv_header_bar_set_fullscreen_state (GMPV_HEADER_BAR(area->header_bar), fullscreen); if(area->control_box) { gmpv_control_box_set_fullscreen_state (GMPV_CONTROL_BOX(area->control_box), fullscreen); } } } void gmpv_video_area_set_control_box_visible( GmpvVideoArea *area, gboolean visible ) { gtk_widget_set_visible(area->control_box_revealer, visible); } void gmpv_video_area_set_use_opengl(GmpvVideoArea *area, gboolean use_opengl) { gtk_stack_set_visible_child ( GTK_STACK(area->stack), use_opengl?area->gl_area:area->draw_area ); } void gmpv_video_area_queue_render(GmpvVideoArea *area) { gtk_gl_area_queue_render(GTK_GL_AREA(area->gl_area)); } GtkDrawingArea *gmpv_video_area_get_draw_area(GmpvVideoArea *area) { return GTK_DRAWING_AREA(area->draw_area); } GtkGLArea *gmpv_video_area_get_gl_area(GmpvVideoArea *area) { return GTK_GL_AREA(area->gl_area); } GmpvControlBox *gmpv_video_area_get_control_box(GmpvVideoArea *area) { return GMPV_CONTROL_BOX(area->control_box); } gint64 gmpv_video_area_get_xid(GmpvVideoArea *area) { #ifdef GDK_WINDOWING_X11 if(GDK_IS_X11_DISPLAY(gdk_display_get_default())) { GtkWidget *parent = gtk_widget_get_parent(GTK_WIDGET(area)); GdkWindow *window = NULL; if(parent && !gtk_widget_get_realized(area->draw_area)) { gtk_widget_realize(area->draw_area); } window = gtk_widget_get_window(area->draw_area); if(!window) { g_critical("Failed to get XID of video area"); } return window?(gint64)gdk_x11_window_get_xid(window):-1; } #endif return -1; } gnome-mpv-0.13/src/gmpv_video_area.h000066400000000000000000000032711317030365200174340ustar00rootroot00000000000000/* * Copyright (c) 2016-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef VIDEO_AREA_H #define VIDEO_AREA_H #include #include #include #include "gmpv_control_box.h" #define GMPV_TYPE_VIDEO_AREA (gmpv_video_area_get_type ()) G_DECLARE_FINAL_TYPE(GmpvVideoArea, gmpv_video_area, GMPV, VIDEO_AREA, GtkOverlay) GtkWidget *gmpv_video_area_new(void); void gmpv_video_area_update_track_list( GmpvVideoArea *hdr, const GPtrArray *track_list ); void gmpv_video_area_set_fullscreen_state( GmpvVideoArea *area, gboolean fullscreen ); void gmpv_video_area_set_control_box_visible( GmpvVideoArea *area, gboolean visible ); void gmpv_video_area_set_use_opengl(GmpvVideoArea *area, gboolean use_opengl); void gmpv_video_area_queue_render(GmpvVideoArea *area); GtkDrawingArea *gmpv_video_area_get_draw_area(GmpvVideoArea *area); GtkGLArea *gmpv_video_area_get_gl_area(GmpvVideoArea *area); GmpvControlBox *gmpv_video_area_get_control_box(GmpvVideoArea *area); gint64 gmpv_video_area_get_xid(GmpvVideoArea *area); #endif gnome-mpv-0.13/src/gmpv_view.c000066400000000000000000001112731317030365200163050ustar00rootroot00000000000000/* * Copyright (c) 2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include "gmpv_view.h" #include "gmpv_file_chooser.h" #include "gmpv_open_location_dialog.h" #include "gmpv_preferences_dialog.h" #include "gmpv_shortcuts_window.h" #include "gmpv_authors.h" #include "gmpv_marshal.h" #include "gmpv_menu.h" #include "gmpv_common.h" #include "gmpv_def.h" enum { PROP_0, PROP_WINDOW, PROP_PLAYLIST_COUNT, PROP_PAUSE, PROP_TITLE, PROP_VOLUME, PROP_DURATION, PROP_PLAYLIST_POS, PROP_TRACK_LIST, PROP_CHAPTERS_ENABLED, PROP_FULLSCREEN, N_PROPERTIES }; struct _GmpvView { GObject parent; GmpvMainWindow *wnd; /* Properties */ gint playlist_count; gboolean pause; gchar *title; gdouble volume; gdouble duration; gint playlist_pos; GPtrArray *track_list; gboolean chapters_enabled; gboolean control_box_enabled; gboolean fullscreen; }; struct _GmpvViewClass { GObjectClass parent_class; }; G_DEFINE_TYPE(GmpvView, gmpv_view, G_TYPE_OBJECT) static void constructed(GObject *object); static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ); static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ); static void dispose(GObject * object); static void finalize(GObject * object); static void load_css(GmpvView *view); static void save_playlist(GmpvView *view, GFile *file, GError **error); static void show_message_dialog( GmpvMainWindow *wnd, GtkMessageType type, const gchar *title, const gchar *prefix, const gchar *msg ); /* Control box signals */ static void button_clicked_handler( GtkWidget *widget, const gchar *button, gpointer data ); static void seek_handler(GtkWidget *widget, gdouble value, gpointer data); /* Dialog responses */ static void open_dialog_response_handler( GtkDialog *dialog, gint response_id, gpointer data ); static void open_location_dialog_response_handler( GtkDialog *dialog, gint response_id, gpointer data ); static void open_audio_track_dialog_response_handler( GtkDialog *dialog, gint response_id, gpointer data ); static void open_subtitle_track_dialog_response_handler( GtkDialog *dialog, gint response_id, gpointer data ); static void preferences_dialog_response_handler( GtkDialog *dialog, gint response_id, gpointer data ); /* User inputs */ static void key_press_handler( GmpvMainWindow *wnd, GdkEvent *event, gpointer data ); static void key_release_handler( GmpvMainWindow *wnd, GdkEvent *event, gpointer data ); static void button_press_handler( GmpvMainWindow *wnd, GdkEvent *event, gpointer data ); static void button_release_handler( GmpvMainWindow *wnd, GdkEvent *event, gpointer data ); static void motion_notify_handler( GmpvMainWindow *wnd, GdkEvent *event, gpointer data ); static void scroll_handler( GmpvMainWindow *wnd, GdkEvent *event, gpointer data ); static void render_handler(GmpvVideoArea *area, gpointer data); static gboolean draw_handler(GtkWidget *widget, cairo_t *cr, gpointer data); static void drag_data_handler( GtkWidget *widget, GdkDragContext *context, gint x, gint y, GtkSelectionData *sel_data, guint info, guint time, gpointer data ); static gboolean window_state_handler( GtkWidget *widget, GdkEvent *event, gpointer data ); static void grab_handler(GtkWidget *widget, gboolean was_grabbed, gpointer data); static gboolean delete_handler( GtkWidget *widget, GdkEvent *event, gpointer data ); static void playlist_row_activated_handler( GmpvPlaylistWidget *playlist, gint64 pos, gpointer data ); static void playlist_row_inserted_handler( GmpvPlaylistWidget *widget, gint pos, gpointer data ); static void playlist_row_deleted_handler( GmpvPlaylistWidget *widget, gint pos, gpointer data ); static void playlist_row_reordered_handler( GmpvPlaylistWidget *widget, gint src, gint dest, gpointer data ); static void constructed(GObject *object) { GmpvView *view = GMPV_VIEW(object); GmpvVideoArea *video_area = gmpv_main_window_get_video_area(view->wnd); GmpvPlaylistWidget *playlist = gmpv_main_window_get_playlist(view->wnd); GmpvControlBox *control_box; GSettings *settings = g_settings_new(CONFIG_ROOT); gboolean csd_enable; gboolean dark_theme_enable; csd_enable = g_settings_get_boolean (settings, "csd-enable"); dark_theme_enable = g_settings_get_boolean (settings, "dark-theme-enable"); control_box = gmpv_main_window_get_control_box(view->wnd); gmpv_main_window_load_state(view->wnd); load_css(view); gtk_widget_show_all(GTK_WIDGET(view->wnd)); g_object_set( control_box, "show-fullscreen-button", !csd_enable, "chapters-enabled", FALSE, NULL ); g_object_set( gtk_settings_get_default(), "gtk-application-prefer-dark-theme", dark_theme_enable, NULL ); g_object_unref(settings); g_object_bind_property( view, "title", view->wnd, "title", G_BINDING_DEFAULT ); g_object_bind_property( view, "duration", control_box, "duration", G_BINDING_DEFAULT ); g_object_bind_property( view, "pause", control_box, "pause", G_BINDING_DEFAULT ); g_object_bind_property( view, "chapters-enabled", control_box, "chapters-enabled", G_BINDING_DEFAULT ); g_object_bind_property( view, "volume", control_box, "volume", G_BINDING_BIDIRECTIONAL ); g_object_bind_property( playlist, "playlist-count", view, "playlist-count", G_BINDING_DEFAULT ); g_signal_connect( view->wnd, "button-clicked", G_CALLBACK(button_clicked_handler), view ); g_signal_connect( view->wnd, "seek", G_CALLBACK(seek_handler), view ); g_signal_connect( view->wnd, "key-press-event", G_CALLBACK(key_press_handler), view ); g_signal_connect( view->wnd, "key-release-event", G_CALLBACK(key_release_handler), view ); g_signal_connect( video_area, "render", G_CALLBACK(render_handler), view ); g_signal_connect( video_area, "button-press-event", G_CALLBACK(button_press_handler), view ); g_signal_connect( video_area, "button-release-event", G_CALLBACK(button_release_handler), view ); g_signal_connect( video_area, "motion-notify-event", G_CALLBACK(motion_notify_handler), view ); g_signal_connect( video_area, "scroll-event", G_CALLBACK(scroll_handler), view ); g_signal_connect_after( view->wnd, "draw", G_CALLBACK(draw_handler), view ); g_signal_connect( video_area, "drag-data-received", G_CALLBACK(drag_data_handler), view ); g_signal_connect( playlist, "drag-data-received", G_CALLBACK(drag_data_handler), view ); g_signal_connect( view->wnd, "window-state-event", G_CALLBACK(window_state_handler), view ); g_signal_connect( view->wnd, "grab-notify", G_CALLBACK(grab_handler), view ); g_signal_connect( view->wnd, "delete-event", G_CALLBACK(delete_handler), view ); g_signal_connect( playlist, "row-activated", G_CALLBACK(playlist_row_activated_handler), view ); g_signal_connect( playlist, "row-inserted", G_CALLBACK(playlist_row_inserted_handler), view ); g_signal_connect( playlist, "row-deleted", G_CALLBACK(playlist_row_deleted_handler), view ); g_signal_connect( playlist, "rows-reordered", G_CALLBACK(playlist_row_reordered_handler), view ); G_OBJECT_CLASS(gmpv_view_parent_class)->constructed(object); } static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ) { GmpvView *self = GMPV_VIEW(object); GmpvControlBox* control_box = NULL; if(self->wnd) { control_box = gmpv_main_window_get_control_box(self->wnd); } switch(property_id) { case PROP_WINDOW: self->wnd = g_value_get_pointer(value); break; case PROP_PLAYLIST_COUNT: self->playlist_count = g_value_get_int(value); g_object_set( control_box, "enabled", self->playlist_count > 0, NULL ); if(self->playlist_count <= 0) { gmpv_view_reset(self); } break; case PROP_PAUSE: self->pause = g_value_get_boolean(value); break; case PROP_TITLE: g_free(self->title); self->title = g_value_dup_string(value); break; case PROP_VOLUME: self->volume = g_value_get_double(value); break; case PROP_DURATION: self->duration = g_value_get_double(value); break; case PROP_PLAYLIST_POS: self->playlist_pos = g_value_get_int(value); GmpvPlaylistWidget *playlist = gmpv_main_window_get_playlist(self->wnd); gmpv_playlist_widget_set_indicator_pos(playlist, self->playlist_pos); break; case PROP_TRACK_LIST: self->track_list = g_value_get_pointer(value); gmpv_main_window_update_track_list(self->wnd, self->track_list); break; case PROP_CHAPTERS_ENABLED: self->chapters_enabled = g_value_get_boolean(value); break; case PROP_FULLSCREEN: self->fullscreen = g_value_get_boolean(value); gmpv_main_window_set_fullscreen(self->wnd, self->fullscreen); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ) { GmpvView *self = GMPV_VIEW(object); switch(property_id) { case PROP_WINDOW: g_value_set_pointer(value, self->wnd); break; case PROP_PLAYLIST_COUNT: g_value_set_int(value, self->playlist_count); break; case PROP_PAUSE: g_value_set_boolean(value, self->pause); break; case PROP_TITLE: g_value_set_string(value, self->title); break; case PROP_VOLUME: g_value_set_double(value, self->volume); break; case PROP_DURATION: g_value_set_double(value, self->duration); break; case PROP_PLAYLIST_POS: g_value_set_int(value, self->playlist_pos); break; case PROP_TRACK_LIST: g_value_set_pointer(value, self->track_list); break; case PROP_CHAPTERS_ENABLED: g_value_set_boolean(value, self->chapters_enabled); break; case PROP_FULLSCREEN: g_value_set_boolean(value, self->fullscreen); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void dispose(GObject *object) { GmpvView *view = GMPV_VIEW(object); if(view->wnd) { gtk_widget_destroy(GTK_WIDGET(view->wnd)); view->wnd = NULL; } G_OBJECT_CLASS(gmpv_view_parent_class)->dispose(object); } static void finalize(GObject *object) { g_free(GMPV_VIEW(object)->title); G_OBJECT_CLASS(gmpv_view_parent_class)->finalize(object); } static void load_css(GmpvView *view) { const gchar *style; GtkCssProvider *style_provider; gboolean css_loaded; style = ".gmpv-vid-area{background-color: black}"; style_provider = gtk_css_provider_new(); css_loaded = gtk_css_provider_load_from_data (style_provider, style, -1, NULL); if(!css_loaded) { g_warning ("Failed to apply background color css"); } gtk_style_context_add_provider_for_screen ( gtk_window_get_screen(GTK_WINDOW(view->wnd)), GTK_STYLE_PROVIDER(style_provider), GTK_STYLE_PROVIDER_PRIORITY_APPLICATION ); g_object_unref(style_provider); } static void save_playlist(GmpvView *view, GFile *file, GError **error) { GmpvPlaylistWidget *wgt = gmpv_main_window_get_playlist(view->wnd); GPtrArray *playlist = gmpv_playlist_widget_get_contents(wgt); gboolean rc = TRUE; GOutputStream *dest_stream = NULL; if(file) { GFileOutputStream *file_stream; file_stream = g_file_replace( file, NULL, FALSE, G_FILE_CREATE_NONE, NULL, error ); dest_stream = G_OUTPUT_STREAM(file_stream); rc = !!dest_stream; } for(guint i = 0; rc && i < playlist->len; i++) { gsize written; GmpvPlaylistEntry *entry = g_ptr_array_index(playlist, i); rc = g_output_stream_printf( dest_stream, &written, NULL, NULL, "%s\n", entry->filename); } if(dest_stream) { g_output_stream_close(dest_stream, NULL, error); } g_ptr_array_free(playlist, TRUE); } void show_message_dialog( GmpvMainWindow *wnd, GtkMessageType type, const gchar *title, const gchar *prefix, const gchar *msg ) { GtkWidget *dialog; GtkWidget *msg_area; GList *children; if(prefix) { gchar *prefix_escaped = g_markup_printf_escaped("%s", prefix); gchar *msg_escaped = g_markup_printf_escaped("%s", msg); dialog = gtk_message_dialog_new_with_markup ( GTK_WINDOW(wnd), GTK_DIALOG_DESTROY_WITH_PARENT, type, GTK_BUTTONS_OK, "[%s] %s", prefix_escaped, msg_escaped ); g_free(prefix_escaped); g_free(msg_escaped); } else { dialog = gtk_message_dialog_new ( GTK_WINDOW(wnd), GTK_DIALOG_DESTROY_WITH_PARENT, type, GTK_BUTTONS_OK, "%s", msg ); } msg_area = gtk_message_dialog_get_message_area (GTK_MESSAGE_DIALOG(dialog)); children = gtk_container_get_children(GTK_CONTAINER(msg_area)); for(GList *iter = children; iter; iter = g_list_next(iter)) { if(GTK_IS_LABEL(iter->data)) { gtk_label_set_line_wrap_mode (GTK_LABEL(iter->data), PANGO_WRAP_WORD_CHAR); } } g_list_free(children); g_signal_connect( dialog, "response", G_CALLBACK(gtk_widget_destroy), NULL ); gtk_window_set_title(GTK_WINDOW(dialog), title); gtk_window_set_modal(GTK_WINDOW(dialog), TRUE); gtk_widget_show_all(dialog); } static void button_clicked_handler( GtkWidget *widget, const gchar *button, gpointer data ) { gchar *name = g_strconcat("button-clicked::", button, NULL); g_signal_emit_by_name(data, name); g_free(name); } static void seek_handler(GtkWidget *widget, gdouble value, gpointer data) { g_signal_emit_by_name(data, "seek", value); } static void open_dialog_response_handler( GtkDialog *dialog, gint response_id, gpointer data ) { GPtrArray *args = data; GmpvView *view = g_ptr_array_index(args, 0); gboolean *append = g_ptr_array_index(args, 1); if(response_id == GTK_RESPONSE_ACCEPT) { GtkFileChooser *chooser = GTK_FILE_CHOOSER(dialog); GSList *uri_slist = gtk_file_chooser_get_filenames(chooser); if(uri_slist) { const gchar **uris = gslist_to_array(uri_slist); g_signal_emit_by_name(view, "file-open", uris, *append); g_free(uris); } g_slist_free_full(uri_slist, g_free); } gmpv_file_chooser_destroy(dialog); g_free(append); g_ptr_array_free(args, TRUE); } static void open_location_dialog_response_handler( GtkDialog *dialog, gint response_id, gpointer data ) { GPtrArray *args = data; GmpvView *view = g_ptr_array_index(args, 0); gboolean *append = g_ptr_array_index(args, 1); if(response_id == GTK_RESPONSE_ACCEPT) { GmpvOpenLocationDialog *location_dialog; const gchar *uris[2]; location_dialog = GMPV_OPEN_LOCATION_DIALOG(dialog); uris[0] = gmpv_open_location_dialog_get_string(location_dialog); uris[1] = NULL; g_signal_emit_by_name(view, "file-open", uris, *append); } gtk_widget_destroy(GTK_WIDGET(dialog)); g_free(append); g_ptr_array_free(args, TRUE); } static void open_audio_track_dialog_response_handler( GtkDialog *dialog, gint response_id, gpointer data ) { if(response_id == GTK_RESPONSE_ACCEPT) { GtkFileChooser *chooser = GTK_FILE_CHOOSER(dialog); GSList *uri_list = gtk_file_chooser_get_filenames(chooser); for(GSList *iter = uri_list; iter; iter = g_slist_next(iter)) { g_signal_emit_by_name(data, "audio-track-load", *iter); } g_slist_free_full(uri_list, g_free); } gmpv_file_chooser_destroy(GMPV_FILE_CHOOSER(dialog)); } static void open_subtitle_track_dialog_response_handler( GtkDialog *dialog, gint response_id, gpointer data ) { if(response_id == GTK_RESPONSE_ACCEPT) { GtkFileChooser *chooser = GTK_FILE_CHOOSER(dialog); GSList *uri_list = gtk_file_chooser_get_filenames(chooser); for(GSList *iter = uri_list; iter; iter = g_slist_next(iter)) { g_signal_emit_by_name(data, "subtitle-track-load", *iter); } g_slist_free_full(uri_list, g_free); } gmpv_file_chooser_destroy(GMPV_FILE_CHOOSER(dialog)); } static void preferences_dialog_response_handler( GtkDialog *dialog, gint response_id, gpointer data ) { if(response_id == GTK_RESPONSE_ACCEPT) { GmpvView *view; GSettings *settings; gboolean csd_enable; view = data; settings = g_settings_new(CONFIG_ROOT); csd_enable = g_settings_get_boolean(settings, "csd-enable"); if(gmpv_main_window_get_csd_enabled(view->wnd) != csd_enable) { show_message_dialog( view->wnd, GTK_MESSAGE_INFO, g_get_application_name(), NULL, _("Enabling or disabling " "client-side decorations " "requires restarting to " "take effect.") ); } gtk_widget_queue_draw(GTK_WIDGET(view->wnd)); g_signal_emit_by_name(data, "preferences-updated"); g_object_unref(settings); } gtk_widget_destroy(GTK_WIDGET(dialog)); } static void key_press_handler( GmpvMainWindow *wnd, GdkEvent *event, gpointer data ) { g_signal_emit_by_name(data, "key-press-event", event); } static void key_release_handler( GmpvMainWindow *wnd, GdkEvent *event, gpointer data ) { g_signal_emit_by_name(data, "key-release-event", event); } static void button_press_handler( GmpvMainWindow *wnd, GdkEvent *event, gpointer data ) { g_signal_emit_by_name(data, "button-press-event", event); } static void button_release_handler( GmpvMainWindow *wnd, GdkEvent *event, gpointer data ) { g_signal_emit_by_name(data, "button-release-event", event); } static void motion_notify_handler( GmpvMainWindow *wnd, GdkEvent *event, gpointer data ) { g_signal_emit_by_name(data, "motion-notify-event", event); } static void scroll_handler( GmpvMainWindow *wnd, GdkEvent *event, gpointer data ) { g_signal_emit_by_name(data, "scroll-event", event); } static void render_handler(GmpvVideoArea *area, gpointer data) { g_signal_emit_by_name(data, "render"); } static gboolean draw_handler(GtkWidget *widget, cairo_t *cr, gpointer data) { GmpvView *view = data; GmpvPlaylistWidget *playlist = gmpv_main_window_get_playlist(view->wnd); guint signal_id = g_signal_lookup("draw", GMPV_TYPE_MAIN_WINDOW); g_signal_handlers_disconnect_matched( widget, G_SIGNAL_MATCH_ID| G_SIGNAL_MATCH_DATA, signal_id, 0, 0, NULL, view ); if(gmpv_playlist_widget_empty(playlist)) { GmpvControlBox *control_box; control_box = gmpv_main_window_get_control_box(view->wnd); g_object_set(control_box, "enabled", FALSE, NULL); } g_signal_emit_by_name(view, "ready"); return FALSE; } static void drag_data_handler( GtkWidget *widget, GdkDragContext *context, gint x, gint y, GtkSelectionData *sel_data, guint info, guint time, gpointer data ) { GmpvView *view = data; gchar *type = gdk_atom_name(gtk_selection_data_get_target(sel_data)); const guchar *raw_data = gtk_selection_data_get_data(sel_data); gchar **uri_list = gtk_selection_data_get_uris(sel_data); gboolean append = GMPV_IS_PLAYLIST_WIDGET(widget); if(g_strcmp0(type, "PLAYLIST_PATH") == 0) { GtkTreePath *path = gtk_tree_path_new_from_string ((const gchar *)raw_data); gint pos = gtk_tree_path_get_indices(path)[0]; g_assert(path); g_signal_emit_by_name(view, "playlist-item-activated", pos); gtk_tree_path_free(path); } else { if(!uri_list) { uri_list = g_malloc(2*sizeof(gchar *)); uri_list[0] = g_strdup((gchar *)raw_data); uri_list[1] = NULL; } g_signal_emit_by_name(view, "file-open", uri_list, append); } g_strfreev(uri_list); g_free(type); } static gboolean window_state_handler( GtkWidget *widget, GdkEvent *event, gpointer data ) { GmpvView *view = data; GdkEventWindowState *state = (GdkEventWindowState *)event; if(state->changed_mask&GDK_WINDOW_STATE_FULLSCREEN) { view->fullscreen = state->new_window_state& GDK_WINDOW_STATE_FULLSCREEN; g_object_notify(data, "fullscreen"); } return FALSE; } static void grab_handler(GtkWidget *widget, gboolean was_grabbed, gpointer data) { g_signal_emit_by_name(data, "grab-notify", was_grabbed); } static gboolean delete_handler( GtkWidget *widget, GdkEvent *event, gpointer data ) { if(!gmpv_main_window_get_fullscreen(GMPV_MAIN_WINDOW(widget))) { gmpv_main_window_save_state(GMPV_MAIN_WINDOW(widget)); } g_signal_emit_by_name(data, "delete-notify"); return TRUE; } static void playlist_row_activated_handler( GmpvPlaylistWidget *playlist, gint64 pos, gpointer data ) { g_signal_emit_by_name(data, "playlist-item-activated", pos); } static void playlist_row_inserted_handler( GmpvPlaylistWidget *widget, gint pos, gpointer data ) { g_signal_emit_by_name(data, "playlist-item-inserted", pos); } static void playlist_row_deleted_handler( GmpvPlaylistWidget *widget, gint pos, gpointer data ) { if(gmpv_playlist_widget_empty(widget)) { gmpv_view_reset(data); } g_signal_emit_by_name(data, "playlist-item-deleted", pos); } static void playlist_row_reordered_handler( GmpvPlaylistWidget *widget, gint src, gint dest, gpointer data ) { g_signal_emit_by_name(data, "playlist-reordered", src, dest); } static void gmpv_view_class_init(GmpvViewClass *klass) { GObjectClass *object_class = G_OBJECT_CLASS(klass); GParamSpec *pspec = NULL; object_class->constructed = constructed; object_class->set_property = set_property; object_class->get_property = get_property; object_class->dispose = dispose; object_class->finalize = finalize; pspec = g_param_spec_pointer ( "window", "Window", "The GmpvMainWindow to use", G_PARAM_CONSTRUCT_ONLY|G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_WINDOW, pspec); pspec = g_param_spec_int ( "playlist-count", "Playlist count", "The number of items in playlist", 0, G_MAXINT, 0, G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_PLAYLIST_COUNT, pspec); pspec = g_param_spec_boolean ( "pause", "Pause", "Whether or not the player is paused", FALSE, G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_PAUSE, pspec); pspec = g_param_spec_string ( "title", "Title", "The title of the window", _("GNOME MPV"), G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_TITLE, pspec); pspec = g_param_spec_double ( "volume", "Volume", "The volume the volume button is set to", 0.0, G_MAXDOUBLE, 0.0, G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_VOLUME, pspec); pspec = g_param_spec_double ( "duration", "Duration", "The duration the seek bar is using", 0.0, G_MAXDOUBLE, 0.0, G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_DURATION, pspec); pspec = g_param_spec_int ( "playlist-pos", "Playlist position", "The position of the current item in playlist", 0, G_MAXINT, 0, G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_PLAYLIST_POS, pspec); pspec = g_param_spec_pointer ( "track-list", "Track list", "The list of tracks in the playing file", G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_TRACK_LIST, pspec); pspec = g_param_spec_boolean ( "chapters-enabled", "Chapters enabled", "Whether or not the chapter controls are enabled", FALSE, G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_CHAPTERS_ENABLED, pspec); pspec = g_param_spec_boolean ( "fullscreen", "Fullscreen", "Whether or not the player is current in fullscreen mode", FALSE, G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_FULLSCREEN, pspec); /* Controls-related signals */ g_signal_new( "button-clicked", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST|G_SIGNAL_DETAILED, 0, NULL, NULL, g_cclosure_marshal_VOID__VOID, G_TYPE_NONE, 0 ); g_signal_new( "seek", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__DOUBLE, G_TYPE_NONE, 1, G_TYPE_DOUBLE ); g_signal_new( "volume-changed", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__DOUBLE, G_TYPE_NONE, 1, G_TYPE_DOUBLE ); /* User input signals */ g_signal_new( "key-press-event", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__POINTER, G_TYPE_NONE, 1, G_TYPE_POINTER); g_signal_new( "key-release-event", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__POINTER, G_TYPE_NONE, 1, G_TYPE_POINTER ); g_signal_new( "button-press-event", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__POINTER, G_TYPE_NONE, 1, G_TYPE_POINTER ); g_signal_new( "button-release-event", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__POINTER, G_TYPE_NONE, 1, G_TYPE_POINTER ); g_signal_new( "motion-notify-event", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__POINTER, G_TYPE_NONE, 1, G_TYPE_POINTER ); g_signal_new( "scroll-event", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__POINTER, G_TYPE_NONE, 1, G_TYPE_POINTER ); g_signal_new( "ready", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__VOID, G_TYPE_NONE, 0 ); g_signal_new( "render", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__VOID, G_TYPE_NONE, 0 ); g_signal_new( "preferences-updated", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__VOID, G_TYPE_NONE, 0 ); g_signal_new( "audio-track-load", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__STRING, G_TYPE_NONE, 1, G_TYPE_STRING ); g_signal_new( "subtitle-track-load", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__STRING, G_TYPE_NONE, 1, G_TYPE_STRING ); g_signal_new( "file-open", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_gen_marshal_VOID__POINTER_BOOLEAN, G_TYPE_NONE, 2, G_TYPE_POINTER, G_TYPE_BOOLEAN ); g_signal_new( "grab-notify", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__BOOLEAN, G_TYPE_NONE, 1, G_TYPE_BOOLEAN ); g_signal_new( "delete-notify", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__VOID, G_TYPE_NONE, 0 ); g_signal_new( "playlist-item-activated", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__INT, G_TYPE_NONE, 1, G_TYPE_INT ); g_signal_new( "playlist-item-inserted", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__INT, G_TYPE_NONE, 1, G_TYPE_INT ); g_signal_new( "playlist-item-deleted", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_marshal_VOID__INT, G_TYPE_NONE, 1, G_TYPE_INT ); g_signal_new( "playlist-reordered", G_TYPE_FROM_CLASS(klass), G_SIGNAL_RUN_FIRST, 0, NULL, NULL, g_cclosure_gen_marshal_VOID__INT_INT, G_TYPE_NONE, 2, G_TYPE_INT, G_TYPE_INT ); } static void gmpv_view_init(GmpvView *view) { view->wnd = NULL; view->playlist_count = 0; view->pause = FALSE; view->title = NULL; view->volume = 0.0; view->duration = 0.0; view->playlist_pos = 0; view->chapters_enabled = FALSE; view->fullscreen = FALSE; } GmpvView *gmpv_view_new(GmpvApplication *app, gboolean always_floating) { GtkApplication *gtk_app = GTK_APPLICATION(app); GSettings *settings = g_settings_new(CONFIG_ROOT); GtkWidget *window = gmpv_main_window_new(gtk_app, always_floating); if(g_settings_get_boolean(settings, "csd-enable")) { GMenu *app_menu = g_menu_new(); gmpv_menu_build_app_menu(app_menu); gtk_application_set_app_menu(gtk_app, G_MENU_MODEL(app_menu)); gmpv_main_window_enable_csd(GMPV_MAIN_WINDOW(window)); } else { GMenu *full_menu = g_menu_new(); gmpv_menu_build_full(full_menu, NULL); gtk_application_set_app_menu(gtk_app, NULL); gtk_application_set_menubar(gtk_app, G_MENU_MODEL(full_menu)); } g_object_unref(settings); return GMPV_VIEW(g_object_new( gmpv_view_get_type(), "window", window, NULL )); } GmpvMainWindow *gmpv_view_get_main_window(GmpvView *view) { return view->wnd; } void gmpv_view_show_open_dialog(GmpvView *view, gboolean append) { GmpvFileChooser *chooser; GPtrArray *args; gboolean *append_buf; chooser = gmpv_file_chooser_new( append? _("Add File to Playlist"): _("Open File"), GTK_WINDOW(view->wnd), GTK_FILE_CHOOSER_ACTION_OPEN ); args = g_ptr_array_new(); append_buf = g_malloc(sizeof(gboolean)); *append_buf = append; g_ptr_array_add(args, view); g_ptr_array_add(args, append_buf); g_signal_connect( chooser, "response", G_CALLBACK(open_dialog_response_handler), args ); gmpv_file_chooser_set_default_filters(chooser, TRUE, TRUE, TRUE, TRUE); gmpv_file_chooser_show(chooser); } void gmpv_view_show_open_location_dialog(GmpvView *view, gboolean append) { GtkWidget *dlg; GPtrArray *args; gboolean *append_buf; dlg = gmpv_open_location_dialog_new( GTK_WINDOW(view->wnd), append? _("Add Location to Playlist"): _("Open Location") ); args = g_ptr_array_sized_new(2); append_buf = g_malloc(sizeof(gboolean)); *append_buf = append; g_ptr_array_add(args, view); g_ptr_array_add(args, append_buf); g_signal_connect ( dlg, "response", G_CALLBACK(open_location_dialog_response_handler), args ); gtk_widget_show_all(dlg); } void gmpv_view_show_open_audio_track_dialog(GmpvView *view) { GmpvFileChooser *chooser = gmpv_file_chooser_new ( _("Load Audio Track…"), GTK_WINDOW(view->wnd), GTK_FILE_CHOOSER_ACTION_OPEN ); g_signal_connect ( chooser, "response", G_CALLBACK(open_audio_track_dialog_response_handler), view ); gmpv_file_chooser_set_default_filters (chooser, TRUE, FALSE, FALSE, FALSE); gmpv_file_chooser_show(chooser); } void gmpv_view_show_open_subtitle_track_dialog(GmpvView *view) { GmpvFileChooser *chooser = gmpv_file_chooser_new ( _("Load Subtitle Track…"), GTK_WINDOW(view->wnd), GTK_FILE_CHOOSER_ACTION_OPEN ); g_signal_connect ( chooser, "response", G_CALLBACK(open_subtitle_track_dialog_response_handler), view ); gmpv_file_chooser_set_default_filters (chooser, FALSE, FALSE, FALSE, TRUE); gmpv_file_chooser_show(chooser); } void gmpv_view_show_save_playlist_dialog(GmpvView *view) { GFile *dest_file; GmpvFileChooser *file_chooser; GtkFileChooser *gtk_chooser; GError *error; dest_file = NULL; file_chooser = gmpv_file_chooser_new ( _("Save Playlist"), GTK_WINDOW(view->wnd), GTK_FILE_CHOOSER_ACTION_SAVE ); gtk_chooser = GTK_FILE_CHOOSER(file_chooser); error = NULL; gtk_file_chooser_set_current_name(gtk_chooser, "playlist.m3u"); if(gmpv_file_chooser_run(file_chooser) == GTK_RESPONSE_ACCEPT) { /* There should be only one file selected. */ dest_file = gtk_file_chooser_get_file(gtk_chooser); } gmpv_file_chooser_destroy(file_chooser); if(dest_file) { save_playlist(view, dest_file, &error); g_object_unref(dest_file); } if(error) { show_message_dialog( view->wnd, GTK_MESSAGE_ERROR, _("Error"), NULL, error->message ); g_error_free(error); } } void gmpv_view_show_preferences_dialog(GmpvView *view) { GtkWidget *dialog = gmpv_preferences_dialog_new(GTK_WINDOW(view->wnd)); g_signal_connect_after( dialog, "response", G_CALLBACK(preferences_dialog_response_handler), view ); gtk_widget_show_all(dialog); } void gmpv_view_show_shortcuts_dialog(GmpvView *view) { #if GTK_CHECK_VERSION(3, 20, 0) GtkWidget *wnd = gmpv_shortcuts_window_new(GTK_WINDOW(view->wnd)); gtk_widget_show_all(wnd); #endif } void gmpv_view_show_about_dialog(GmpvView *view) { const gchar *const authors[] = AUTHORS; gtk_show_about_dialog( GTK_WINDOW(view->wnd), "logo-icon-name", ICON_NAME, "version", VERSION, "comments", _("A GTK frontend for MPV"), "website", "https://github.com/gnome-mpv/gnome-mpv", "license-type", GTK_LICENSE_GPL_3_0, "copyright", "\u00A9 2014-2017 The GNOME MPV authors", "authors", authors, "translator-credits", _("translator-credits"), NULL ); } void gmpv_view_show_message_dialog( GmpvView *view, GtkMessageType type, const gchar *title, const gchar *prefix, const gchar *msg ) { show_message_dialog(view->wnd, type, title, prefix, msg); } void gmpv_view_present(GmpvView *view) { gtk_window_present(GTK_WINDOW(view->wnd)); } void gmpv_view_quit(GmpvView *view) { gtk_window_close(GTK_WINDOW(view->wnd)); } void gmpv_view_reset(GmpvView *view) { gmpv_main_window_reset(view->wnd); } void gmpv_view_queue_render(GmpvView *view) { GmpvVideoArea *area = gmpv_main_window_get_video_area(view->wnd); gmpv_video_area_queue_render(area); } void gmpv_view_make_gl_context_current(GmpvView *view) { GmpvVideoArea *video_area = gmpv_main_window_get_video_area(view->wnd); GtkGLArea *gl_area = gmpv_video_area_get_gl_area(video_area); gtk_widget_realize(GTK_WIDGET(gl_area)); gtk_gl_area_make_current(gl_area); } void gmpv_view_set_use_opengl_cb(GmpvView *view, gboolean use_opengl_cb) { GmpvVideoArea *area = gmpv_main_window_get_video_area(view->wnd); gmpv_video_area_set_use_opengl(area, use_opengl_cb); } gint gmpv_view_get_scale_factor(GmpvView *view) { GdkWindow *gdk_window = gtk_widget_get_window(GTK_WIDGET(view->wnd)); return gdk_window_get_scale_factor(gdk_window); } void gmpv_view_get_video_area_geometry(GmpvView *view, gint *width, gint *height) { GmpvVideoArea *area = gmpv_main_window_get_video_area(view->wnd); GtkAllocation allocation; gtk_widget_get_allocation(GTK_WIDGET(area), &allocation); *width = allocation.width; *height = allocation.height; } void gmpv_view_move( GmpvView *view, gboolean flip_x, gboolean flip_y, GValue *x, GValue *y ) { GdkScreen *screen = gdk_screen_get_default(); GtkWindow *window = GTK_WINDOW(view->wnd); gint64 x_pos = -1; gint64 y_pos = -1; gint window_width = 0; gint window_height = 0; gint space_x; gint space_y; gtk_window_get_size(window, &window_width, &window_height); space_x = gdk_screen_get_width(screen)-window_width; space_y = gdk_screen_get_height(screen)-window_height; if(G_VALUE_HOLDS_DOUBLE(x)) { x_pos = (gint64)(g_value_get_double(x)*space_x); } else { x_pos = flip_x?space_x-g_value_get_int64(x):g_value_get_int64(x); } if(G_VALUE_HOLDS_DOUBLE(y)) { y_pos = (gint64)(g_value_get_double(y)*space_y); } else { y_pos = flip_y?space_y-g_value_get_int64(y):g_value_get_int64(y); } gtk_window_move(window, (gint)x_pos, (gint)y_pos); } void gmpv_view_resize_video_area(GmpvView *view, gint width, gint height) { gmpv_main_window_resize_video_area(view->wnd, width, height); } void gmpv_view_set_fullscreen(GmpvView *view, gboolean fullscreen) { g_object_set(view, "fullscreen", fullscreen, NULL); gmpv_main_window_set_fullscreen(view->wnd, fullscreen); } void gmpv_view_set_time_position(GmpvView *view, gdouble position) { GmpvControlBox *control_box; control_box = gmpv_main_window_get_control_box(view->wnd); g_object_set(control_box, "time-position", position, NULL); } void gmpv_view_update_playlist(GmpvView *view, GPtrArray *playlist) { GmpvPlaylistWidget *wgt = gmpv_main_window_get_playlist(view->wnd); gmpv_playlist_widget_update_contents(wgt, playlist); } void gmpv_view_set_playlist_pos(GmpvView *view, gint64 pos) { g_object_set(view, "playlist-pos", pos, NULL); } void gmpv_view_set_playlist_visible(GmpvView *view, gboolean visible) { gmpv_main_window_set_playlist_visible(view->wnd, visible); } gboolean gmpv_view_get_playlist_visible(GmpvView *view) { return gmpv_main_window_get_playlist_visible(view->wnd); } void gmpv_view_set_controls_visible(GmpvView *view, gboolean visible) { gmpv_main_window_set_controls_visible(view->wnd, visible); } gboolean gmpv_view_get_controls_visible(GmpvView *view) { return gmpv_main_window_get_controls_visible(view->wnd); } gnome-mpv-0.13/src/gmpv_view.h000066400000000000000000000054321317030365200163110ustar00rootroot00000000000000/* * Copyright (c) 2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef VIEW_H #define VIEW_H #include #include "gmpv_application.h" G_BEGIN_DECLS #define GMPV_TYPE_VIEW (gmpv_view_get_type()) G_DECLARE_FINAL_TYPE(GmpvView, gmpv_view, GMPV, VIEW, GObject) GmpvView *gmpv_view_new(GmpvApplication *app, gboolean always_floating); GmpvMainWindow *gmpv_view_get_main_window(GmpvView *view); void gmpv_view_show_open_dialog(GmpvView *view, gboolean append); void gmpv_view_show_open_location_dialog(GmpvView *view, gboolean append); void gmpv_view_show_open_audio_track_dialog(GmpvView *view); void gmpv_view_show_open_subtitle_track_dialog(GmpvView *view); void gmpv_view_show_save_playlist_dialog(GmpvView *view); void gmpv_view_show_preferences_dialog(GmpvView *view); void gmpv_view_show_shortcuts_dialog(GmpvView *view); void gmpv_view_show_about_dialog(GmpvView *view); void gmpv_view_show_message_dialog( GmpvView *view, GtkMessageType type, const gchar *title, const gchar *prefix, const gchar *msg ); void gmpv_view_present(GmpvView *view); void gmpv_view_quit(GmpvView *view); void gmpv_view_reset(GmpvView *view); void gmpv_view_queue_render(GmpvView *view); void gmpv_view_make_gl_context_current(GmpvView *view); void gmpv_view_set_use_opengl_cb(GmpvView *view, gboolean use_opengl_cb); gint gmpv_view_get_scale_factor(GmpvView *view); void gmpv_view_get_video_area_geometry(GmpvView *view, gint *width, gint *height); void gmpv_view_move( GmpvView *view, gboolean flip_x, gboolean flip_y, GValue *x, GValue *y ); void gmpv_view_resize_video_area(GmpvView *view, gint width, gint height); void gmpv_view_set_fullscreen(GmpvView *view, gboolean fullscreen); void gmpv_view_set_time_position(GmpvView *view, gdouble position); void gmpv_view_update_playlist(GmpvView *view, GPtrArray *playlist); void gmpv_view_set_playlist_pos(GmpvView *view, gint64 pos); void gmpv_view_set_playlist_visible(GmpvView *view, gboolean visible); gboolean gmpv_view_get_playlist_visible(GmpvView *view); void gmpv_view_set_controls_visible(GmpvView *view, gboolean visible); gboolean gmpv_view_get_controls_visible(GmpvView *view); G_END_DECLS #endif gnome-mpv-0.13/src/media_keys/000077500000000000000000000000001317030365200162435ustar00rootroot00000000000000gnome-mpv-0.13/src/media_keys/gmpv_media_keys.c000066400000000000000000000200551317030365200215540ustar00rootroot00000000000000/* * Copyright (c) 2015-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include "gmpv_media_keys.h" #include "gmpv_def.h" enum { PROP_0, PROP_CONTROLLER, N_PROPERTIES }; struct _GmpvMediaKeys { GObject parent; GmpvController *controller; gulong focus_sig_id; GDBusProxy *proxy; GDBusProxy *compat_proxy; GDBusConnection *session_bus_conn; }; struct _GmpvMediaKeysClass { GObjectClass parent_class; }; G_DEFINE_TYPE(GmpvMediaKeys, gmpv_media_keys, G_TYPE_OBJECT) static void constructed(GObject *object); static void dispose(GObject *object); static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ); static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ); static gboolean window_state_handler( GtkWidget *widget, GdkEventWindowState *event, gpointer data ); static void g_signal_handler( GDBusProxy *proxy, gchar *sender_name, gchar *signal_name, GVariant *parameters, gpointer data ); static void proxy_ready_handler( GObject *source_object, GAsyncResult *res, gpointer data ); static void compat_proxy_ready_handler( GObject *source_object, GAsyncResult *res, gpointer data ); static void session_ready_handler( GObject *source_object, GAsyncResult *res, gpointer data ); static void constructed(GObject *object) { GmpvMediaKeys *self = GMPV_MEDIA_KEYS(object); GmpvView *view = gmpv_controller_get_view(self->controller); self->focus_sig_id = g_signal_connect ( gmpv_view_get_main_window(view), "window-state-event", G_CALLBACK(window_state_handler), self ); g_bus_get(G_BUS_TYPE_SESSION, NULL, session_ready_handler, self); } static void dispose(GObject *object) { GmpvMediaKeys *self = GMPV_MEDIA_KEYS(object); GmpvView *view = gmpv_controller_get_view(self->controller); GmpvMainWindow *window = gmpv_view_get_main_window(view); if(self->focus_sig_id > 0) { g_signal_handler_disconnect(window, self->focus_sig_id); self->focus_sig_id = 0; } g_clear_object(&self->proxy); g_clear_object(&self->compat_proxy); g_clear_object(&self->session_bus_conn); G_OBJECT_CLASS(gmpv_media_keys_parent_class)->dispose(object); } static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ) { GmpvMediaKeys *self = GMPV_MEDIA_KEYS(object); switch(property_id) { case PROP_CONTROLLER: self->controller = g_value_get_pointer(value); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } G_OBJECT_CLASS(gmpv_media_keys_parent_class)->constructed(object); } static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ) { GmpvMediaKeys *self = GMPV_MEDIA_KEYS(object); switch(property_id) { case PROP_CONTROLLER: g_value_set_pointer(value, self->controller); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static gboolean window_state_handler( GtkWidget *widget, GdkEventWindowState *event, gpointer data ) { GmpvMediaKeys *self = data; if (event->changed_mask & GDK_WINDOW_STATE_FOCUSED && event->new_window_state & GDK_WINDOW_STATE_FOCUSED && self->proxy != NULL) { g_dbus_proxy_call( self->proxy, "GrabMediaPlayerKeys", g_variant_new("(su)", APP_ID, 0), G_DBUS_CALL_FLAGS_NONE, -1, NULL, NULL, self ); } return FALSE; } static void g_signal_handler( GDBusProxy *proxy, gchar *sender_name, gchar *signal_name, GVariant *parameters, gpointer data ) { GmpvMediaKeys *self = data; gchar *gmpv_application = NULL; gchar *key = NULL; if(g_strcmp0(signal_name, "MediaPlayerKeyPressed") == 0) { g_variant_get(parameters, "(&s&s)", &gmpv_application, &key); } if(g_strcmp0(gmpv_application, APP_ID) == 0) { GmpvModel *model = gmpv_controller_get_model(self->controller); if(g_strcmp0(key, "Next") == 0) { gmpv_model_next_playlist_entry(model); } else if(g_strcmp0(key, "Previous") == 0) { gmpv_model_previous_playlist_entry(model); } else if(g_strcmp0(key, "Pause") == 0) { gmpv_model_pause(model); } else if(g_strcmp0(key, "Stop") == 0) { gmpv_model_stop(model); } else if(g_strcmp0(key, "Play") == 0) { gboolean pause = FALSE; g_object_get(model, "pause", &pause, NULL); (pause?gmpv_model_play:gmpv_model_pause)(model); } else if(g_strcmp0(key, "FastForward") == 0) { gmpv_model_forward(model); } else if(g_strcmp0(key, "Rewind") == 0) { gmpv_model_rewind(model); } } } static void proxy_ready_handler( GObject *source_object, GAsyncResult *res, gpointer data ) { GmpvMediaKeys *self = data; self->proxy = g_dbus_proxy_new_finish(res, NULL); g_signal_connect( self->proxy, "g-signal", G_CALLBACK(g_signal_handler), self ); g_dbus_proxy_call( self->proxy, "GrabMediaPlayerKeys", g_variant_new("(su)", APP_ID, 0), G_DBUS_CALL_FLAGS_NONE, -1, NULL, NULL, NULL ); } static void compat_proxy_ready_handler( GObject *source_object, GAsyncResult *res, gpointer data ) { GmpvMediaKeys *self = data; self->compat_proxy = g_dbus_proxy_new_finish(res, NULL); g_signal_connect( self->proxy, "g-signal", G_CALLBACK(g_signal_handler), self ); g_dbus_proxy_call( self->compat_proxy, "GrabMediaPlayerKeys", g_variant_new("(su)", APP_ID, 0), G_DBUS_CALL_FLAGS_NONE, -1, NULL, NULL, NULL ); } static void session_ready_handler( GObject *source_object, GAsyncResult *res, gpointer data ) { GmpvMediaKeys *self = data; self->session_bus_conn = g_bus_get_finish(res, NULL); /* The MediaKeys plugin for gnome-settings-daemon <= 3.24.1 used the * bus name org.gnome.SettingsDaemon despite the documentation stating * that org.gnome.SettingsDaemon.MediaKeys should be used. * gnome-settings-daemon > 3.24.1 changed the bus name to match the * documentation. To remain compatible with older versions, create * proxies for both names. */ g_dbus_proxy_new( self->session_bus_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, "org.gnome.SettingsDaemon.MediaKeys", "/org/gnome/SettingsDaemon/MediaKeys", "org.gnome.SettingsDaemon.MediaKeys", NULL, proxy_ready_handler, self ); g_dbus_proxy_new( self->session_bus_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, "org.gnome.SettingsDaemon", "/org/gnome/SettingsDaemon/MediaKeys", "org.gnome.SettingsDaemon.MediaKeys", NULL, compat_proxy_ready_handler, self ); } static void gmpv_media_keys_init(GmpvMediaKeys *self) { self->controller = NULL; self->focus_sig_id = 0; self->proxy = NULL; self->compat_proxy = NULL; self->session_bus_conn = NULL; } static void gmpv_media_keys_class_init(GmpvMediaKeysClass *klass) { GObjectClass *object_class = G_OBJECT_CLASS(klass); GParamSpec *pspec = NULL; object_class->constructed = constructed; object_class->set_property = set_property; object_class->get_property = get_property; object_class->dispose = dispose; pspec = g_param_spec_pointer ( "controller", "Controller", "The GmpvController to use", G_PARAM_CONSTRUCT_ONLY|G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_CONTROLLER, pspec); } GmpvMediaKeys *gmpv_media_keys_new(GmpvController *controller) { return GMPV_MEDIA_KEYS(g_object_new( gmpv_media_keys_get_type(), "controller", controller, NULL )); } gnome-mpv-0.13/src/media_keys/gmpv_media_keys.h000066400000000000000000000020151317030365200215550ustar00rootroot00000000000000/* * Copyright (c) 2015-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef MEDIA_KEYS_H #define MEDIA_KEYS_H #include "gmpv_controller.h" G_BEGIN_DECLS #define GMPV_TYPE_MEDIA_KEYS (gmpv_media_keys_get_type ()) G_DECLARE_FINAL_TYPE(GmpvMediaKeys, gmpv_media_keys, GMPV, MEDIA_KEYS, GObject) GmpvMediaKeys *gmpv_media_keys_new(GmpvController *controller); G_END_DECLS #endif gnome-mpv-0.13/src/meson.build000066400000000000000000000067221317030365200163020ustar00rootroot00000000000000gnome = import('gnome') sources = [ 'gmpv_application.c', 'gmpv_common.c', 'gmpv_control_box.c', 'gmpv_controller.c', 'gmpv_controller_actions.c', 'gmpv_controller_input.c', 'gmpv_file_chooser.c', 'gmpv_header_bar.c', 'gmpv_main.c', 'gmpv_main_window.c', 'gmpv_menu.c', 'gmpv_metadata_cache.c', 'gmpv_model.c', 'gmpv_mpv.c', 'gmpv_mpv_wrapper.c', 'gmpv_open_location_dialog.c', 'gmpv_player.c', 'gmpv_player_options.c', 'gmpv_playlist_widget.c', 'gmpv_plugins_manager.c', 'gmpv_plugins_manager_item.c', 'gmpv_preferences_dialog.c', 'gmpv_seek_bar.c', 'gmpv_shortcuts_window.c', 'gmpv_video_area.c', 'gmpv_view.c', 'media_keys/gmpv_media_keys.c', 'mpris/gmpv_mpris.c', 'mpris/gmpv_mpris_module.c', 'mpris/gmpv_mpris_base.c', 'mpris/gmpv_mpris_player.c', 'mpris/gmpv_mpris_track_list.c' ] sources += custom_target('authors', input: '../AUTHORS', output: 'gmpv_authors.h', command: [ find_program('generate_authors.py'), '@INPUT@', '@OUTPUT@' ] ) libgtk = dependency('gtk+-3.0', version: '>= 3.18') localedir = join_paths(get_option('prefix'), get_option('localedir')) cflags = [ '-DG_SETTINGS_ENABLE_BACKEND', '-DPACKAGE_LOCALEDIR="@0@"'.format(localedir), '-DVERSION="@0@"'.format(meson.project_version()), '-DGETTEXT_PACKAGE="@0@"'.format(meson.project_name()), '-DGLIB_VERSION_MIN_REQUIRED=GLIB_VERSION_2_44', '-DGLIB_VERSION_MAX_ALLOWED=GLIB_VERSION_2_44', ] if get_option('buildtype') == 'release' cflags += [ '-DG_DISABLE_ASSERT=1', '-DG_DISABLE_CHECKS=1', '-DG_DISABLE_CAST_CHECKS=1' ] endif if libgtk.version().version_compare('>= 3.20') cflags += [ '-DGDK_VERSION_MIN_REQUIRED=GDK_VERSION_3_20', '-DGDK_VERSION_MAX_ALLOWED=GDK_VERSION_3_20' ] sources += 'gmpv_shortcuts_window.c' else cflags += [ '-DGDK_VERSION_MIN_REQUIRED=GDK_VERSION_3_18', '-DGDK_VERSION_MAX_ALLOWED=GDK_VERSION_3_18' ] endif if target_machine.system() == 'windows' libgio = dependency('gio-2.0', version: '>= 2.44') else libgio = dependency('gio-unix-2.0', version: '>= 2.44') endif generated_gdbus_sources = gnome.gdbus_codegen( 'gmpv_mpris_gdbus', '../data/gmpv_mpris_gdbus.xml', namespace: 'gmpv_mpris' ) includes = [] extra_libs = [] if libgio.version().version_compare('<= 2.51.2') # We want to be warning free and due to https://bugzilla.gnome.org/show_bug.cgi?id=778581 # gdbus-codegen caused this warning previous to this release. extra_libs += static_library('mpris-gdbus', generated_gdbus_sources, c_args: cflags + ['-Wno-conversion'], dependencies: libgio, include_directories: include_directories('..'), ) else sources += generated_gdbus_sources # FIXME: Our invocation of `gdbus-codegen` creates an include of `src/...` # https://github.com/mesonbuild/meson/issues/1387 includes = include_directories('..') endif generated_marshal_sources = gnome.genmarshal('gmpv_marshal', sources: '../data/gmpv_marshal.lst', prefix: 'g_cclosure_gen_marshal', ) # Silence warning about missing prototypes in genmarshal-generated files extra_libs += static_library('marshal', generated_marshal_sources, c_args: cflags + ['-Wno-missing-prototypes'], dependencies: libgio, include_directories: include_directories('..') ) executable('gnome-mpv', sources, dependencies: [ libgtk, libgio, dependency('mpv', version: '>= 1.20'), dependency('epoxy') ], link_with: extra_libs, include_directories: includes, c_args: cflags, install: true ) gnome-mpv-0.13/src/mpris/000077500000000000000000000000001317030365200152635ustar00rootroot00000000000000gnome-mpv-0.13/src/mpris/gmpv_mpris.c000066400000000000000000000127311317030365200176160ustar00rootroot00000000000000/* * Copyright (c) 2015-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include #include #include #include "gmpv_mpris.h" #include "gmpv_mpris_base.h" #include "gmpv_mpris_player.h" #include "gmpv_mpris_track_list.h" #include "gmpv_def.h" enum { PROP_0, PROP_CONTROLLER, N_PROPERTIES }; struct _GmpvMpris { GObject parent; GmpvController *controller; GmpvMprisModule *base; GmpvMprisModule *player; GmpvMprisModule *track_list; guint name_id; GDBusConnection *session_bus_conn; }; struct _GmpvMprisClass { GObjectClass parent_class; }; G_DEFINE_TYPE(GmpvMpris, gmpv_mpris, G_TYPE_OBJECT) static void constructed(GObject *object); static void dispose(GObject *object); static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ); static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ); static void name_acquired_handler( GDBusConnection *connection, const gchar *name, gpointer data ); static void name_lost_handler( GDBusConnection *connection, const gchar *name, gpointer data ); static void unregister(GmpvMpris *mpris); static void constructed(GObject *object) { GmpvMpris *self = GMPV_MPRIS(object); gchar *name = NULL; /* sizeof(pid_t) can theoretically be larger than sizeof(gint64), but * even then the chance of collision would be minimal. */ name = g_strdup_printf ( MPRIS_BUS_NAME ".instance%" G_GINT64_FORMAT, ABS((gint64)getpid()) ); self->name_id = g_bus_own_name( G_BUS_TYPE_SESSION, name, G_BUS_NAME_OWNER_FLAGS_NONE, NULL, (GBusNameAcquiredCallback) name_acquired_handler, (GBusNameLostCallback) name_lost_handler, self, NULL ); g_free(name); G_OBJECT_CLASS(gmpv_mpris_parent_class)->constructed(object); } static void dispose(GObject *object) { GmpvMpris *self = GMPV_MPRIS(object); unregister(self); g_clear_object(&self->base); g_clear_object(&self->player); g_clear_object(&self->track_list); g_bus_unown_name(self->name_id); G_OBJECT_CLASS(gmpv_mpris_parent_class)->dispose(object); } static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ) { GmpvMpris *self = GMPV_MPRIS(object); switch(property_id) { case PROP_CONTROLLER: self->controller = g_value_get_pointer(value); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ) { GmpvMpris *self = GMPV_MPRIS(object); switch(property_id) { case PROP_CONTROLLER: g_value_set_pointer(value, self->controller); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void name_acquired_handler( GDBusConnection *connection, const gchar *name, gpointer data ) { GmpvMpris *self = data; self->session_bus_conn = connection; self->base = gmpv_mpris_base_new(self->controller, connection); self->player = gmpv_mpris_player_new(self->controller, connection); self->track_list = gmpv_mpris_track_list_new(self->controller, connection); gmpv_mpris_module_register(self->base); gmpv_mpris_module_register(self->player); gmpv_mpris_module_register(self->track_list); } static void name_lost_handler( GDBusConnection *connection, const gchar *name, gpointer data ) { unregister(data); } static void unregister(GmpvMpris *mpris) { gmpv_mpris_module_unregister(mpris->base); gmpv_mpris_module_unregister(mpris->player); gmpv_mpris_module_unregister(mpris->track_list); } static void gmpv_mpris_init(GmpvMpris *mpris) { mpris->controller = NULL; mpris->base = NULL; mpris->player = NULL; mpris->track_list = NULL; mpris->name_id = 0; mpris->session_bus_conn = NULL; } static void gmpv_mpris_class_init(GmpvMprisClass *klass) { GObjectClass *object_class = G_OBJECT_CLASS(klass); GParamSpec *pspec = NULL; object_class->constructed = constructed; object_class->set_property = set_property; object_class->get_property = get_property; object_class->dispose = dispose; pspec = g_param_spec_pointer ( "controller", "Controller", "The GmpvController to use", G_PARAM_CONSTRUCT_ONLY|G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_CONTROLLER, pspec); } GVariant *gmpv_mpris_build_g_variant_string_array(const gchar** list) { GVariantBuilder builder; gint i; g_variant_builder_init(&builder, G_VARIANT_TYPE("as")); for(i = 0; list[i]; i++) { g_variant_builder_add(&builder, "s", list[i]); } return g_variant_new("as", &builder); } GmpvMpris *gmpv_mpris_new(GmpvController *controller) { return GMPV_MPRIS(g_object_new( gmpv_mpris_get_type(), "controller", controller, NULL )); } gnome-mpv-0.13/src/mpris/gmpv_mpris.h000066400000000000000000000021211317030365200176130ustar00rootroot00000000000000/* * Copyright (c) 2015-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef MPRIS_H #define MPRIS_H #include #include #include "gmpv_controller.h" G_BEGIN_DECLS #define GMPV_TYPE_MPRIS (gmpv_mpris_get_type ()) G_DECLARE_FINAL_TYPE(GmpvMpris, gmpv_mpris, GMPV, MPRIS, GObject) GVariant *gmpv_mpris_build_g_variant_string_array(const gchar** list); GmpvMpris *gmpv_mpris_new(GmpvController *controller); G_END_DECLS #endif gnome-mpv-0.13/src/mpris/gmpv_mpris_base.c000066400000000000000000000210601317030365200206030ustar00rootroot00000000000000/* * Copyright (c) 2015-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include #include #include "gmpv_view.h" #include "gmpv_mpris.h" #include "gmpv_mpris_module.h" #include "gmpv_mpris_base.h" #include "gmpv_mpris_gdbus.h" #include "gmpv_def.h" enum { PROP_0, PROP_CONTROLLER, N_PROPERTIES }; struct _GmpvMprisBase { GmpvMprisModule parent; GmpvController *controller; guint reg_id; }; struct _GmpvMprisBaseClass { GmpvMprisModuleClass parent_class; }; static void register_interface(GmpvMprisModule *module); static void unregister_interface(GmpvMprisModule *module); static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ); static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ); static void method_handler( GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *method_name, GVariant *parameters, GDBusMethodInvocation *invocation, gpointer data ); static GVariant *get_prop_handler( GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *property_name, GError **error, gpointer data ); static gboolean set_prop_handler( GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *property_name, GVariant *value, GError **error, gpointer data ); static void fullscreen_handler( GObject *object, GParamSpec *pspec, gpointer data ); static void update_fullscreen(GmpvMprisBase *base); static GVariant *get_supported_uri_schemes(void); static GVariant *get_supported_mime_types(void); static void gmpv_mpris_base_class_init(GmpvMprisBaseClass *klass); static void gmpv_mpris_base_init(GmpvMprisBase *base); G_DEFINE_TYPE(GmpvMprisBase, gmpv_mpris_base, GMPV_TYPE_MPRIS_MODULE); static void register_interface(GmpvMprisModule *module) { GmpvMprisBase *base; GmpvView *view; GDBusInterfaceVTable vtable; GDBusInterfaceInfo *iface; GDBusConnection *conn; base = GMPV_MPRIS_BASE(module); view = gmpv_controller_get_view(base->controller); g_object_get(module, "conn", &conn, "iface", &iface, NULL); gmpv_mpris_module_connect_signal ( module, view, "notify::fullscreen", G_CALLBACK(fullscreen_handler), module ); gmpv_mpris_module_set_properties ( module, "CanQuit", g_variant_new_boolean(TRUE), "CanSetFullscreen", g_variant_new_boolean(TRUE), "CanRaise", g_variant_new_boolean(TRUE), "Fullscreen", g_variant_new_boolean(FALSE), "HasTrackList", g_variant_new_boolean(TRUE), "Identity", g_variant_new_string(g_get_application_name()), "DesktopEntry", g_variant_new_string(APP_ID), "SupportedUriSchemes", get_supported_uri_schemes(), "SupportedMimeTypes", get_supported_mime_types(), NULL ); vtable.method_call = (GDBusInterfaceMethodCallFunc)method_handler; vtable.get_property = (GDBusInterfaceGetPropertyFunc)get_prop_handler; vtable.set_property = (GDBusInterfaceSetPropertyFunc)set_prop_handler; base->reg_id = g_dbus_connection_register_object ( conn, MPRIS_OBJ_ROOT_PATH, iface, &vtable, module, NULL, NULL ); update_fullscreen(GMPV_MPRIS_BASE(module)); } static void unregister_interface(GmpvMprisModule *module) { GmpvMprisBase *base = GMPV_MPRIS_BASE(module); GDBusConnection *conn = NULL; g_object_get(module, "conn", &conn, NULL); g_dbus_connection_unregister_object(conn, base->reg_id); } static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ) { GmpvMprisBase *self = GMPV_MPRIS_BASE(object); switch(property_id) { case PROP_CONTROLLER: self->controller = g_value_get_pointer(value); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ) { GmpvMprisBase *self = GMPV_MPRIS_BASE(object); switch(property_id) { case PROP_CONTROLLER: g_value_set_pointer(value, self->controller); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void method_handler( GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *method_name, GVariant *parameters, GDBusMethodInvocation *invocation, gpointer data ) { GmpvMprisBase *base = data; if(g_strcmp0(method_name, "Raise") == 0) { gmpv_view_present(gmpv_controller_get_view(base->controller)); } else if(g_strcmp0(method_name, "Quit") == 0) { gmpv_controller_quit(base->controller); } g_dbus_method_invocation_return_value (invocation, g_variant_new("()", NULL)); } static GVariant *get_prop_handler( GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *property_name, GError **error, gpointer data ) { GVariant *value = NULL; gmpv_mpris_module_get_properties(data, property_name, &value, NULL); return value?g_variant_ref(value):NULL; } static gboolean set_prop_handler( GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *property_name, GVariant *value, GError **error, gpointer data ) { GmpvMprisBase *base = data; if(g_strcmp0(property_name, "Fullscreen") == 0) { GmpvView *view = gmpv_controller_get_view(base->controller); gmpv_view_set_fullscreen(view, g_variant_get_boolean(value)); } else { gmpv_mpris_module_set_properties( data, property_name, value, NULL ); } return TRUE; /* This function should always succeed */ } static void fullscreen_handler( GObject *object, GParamSpec *pspec, gpointer data ) { update_fullscreen(data); } static void update_fullscreen(GmpvMprisBase *base) { GmpvMprisModule *module = GMPV_MPRIS_MODULE(base); GmpvModel *model = gmpv_controller_get_model(base->controller); GVariant *old_value = NULL; gboolean fullscreen = FALSE; gmpv_mpris_module_get_properties(module, "Fullscreen", &old_value, NULL); g_object_get(G_OBJECT(model), "fullscreen", &fullscreen, NULL); if(g_variant_get_boolean(old_value) != fullscreen) { gmpv_mpris_module_set_properties ( module, "Fullscreen", g_variant_new_boolean(fullscreen), NULL ); } } static GVariant *get_supported_uri_schemes(void) { const gchar *protocols[] = SUPPORTED_PROTOCOLS; return gmpv_mpris_build_g_variant_string_array(protocols); } static GVariant *get_supported_mime_types(void) { const gchar *mime_types[] = SUPPORTED_MIME_TYPES; return gmpv_mpris_build_g_variant_string_array(mime_types); } static void gmpv_mpris_base_class_init(GmpvMprisBaseClass *klass) { GmpvMprisModuleClass *module_class = GMPV_MPRIS_MODULE_CLASS(klass); GObjectClass *object_class = G_OBJECT_CLASS(klass); GParamSpec *pspec = NULL; module_class->register_interface = register_interface; module_class->unregister_interface = unregister_interface; object_class->set_property = set_property; object_class->get_property = get_property; pspec = g_param_spec_pointer ( "controller", "Controller", "The GmpvController to use", G_PARAM_CONSTRUCT_ONLY|G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_CONTROLLER, pspec); } static void gmpv_mpris_base_init(GmpvMprisBase *base) { base->controller = NULL; base->reg_id = 0; } GmpvMprisModule *gmpv_mpris_base_new( GmpvController *controller, GDBusConnection *conn ) { GDBusInterfaceInfo *iface; iface = gmpv_mpris_org_mpris_media_player2_interface_info(); return GMPV_MPRIS_MODULE(g_object_new( gmpv_mpris_base_get_type(), "controller", controller, "conn", conn, "iface", iface, NULL )); } gnome-mpv-0.13/src/mpris/gmpv_mpris_base.h000066400000000000000000000021521317030365200206110ustar00rootroot00000000000000/* * Copyright (c) 2015-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef MPRIS_BASE_H #define MPRIS_BASE_H #include "gmpv_mpris.h" #include "gmpv_mpris_module.h" #include "gmpv_controller.h" G_BEGIN_DECLS #define GMPV_TYPE_MPRIS_BASE (gmpv_mpris_base_get_type()) G_DECLARE_FINAL_TYPE(GmpvMprisBase, gmpv_mpris_base, GMPV, MPRIS_BASE, GmpvMprisModule) GmpvMprisModule *gmpv_mpris_base_new( GmpvController *controller, GDBusConnection *conn ); G_END_DECLS #endif gnome-mpv-0.13/src/mpris/gmpv_mpris_module.c000066400000000000000000000171011317030365200211570ustar00rootroot00000000000000/* * Copyright (c) 2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include "gmpv_mpris_module.h" #include "gmpv_application.h" #include "gmpv_def.h" typedef struct _GmpvSignalHandlerInfo GmpvSignalHandlerInfo; typedef struct _GmpvMprisModulePrivate GmpvMprisModulePrivate; enum { PROP_0, PROP_CONN, PROP_IFACE, N_PROPERTIES }; struct _GmpvSignalHandlerInfo { gpointer instance; gulong id; }; struct _GmpvMprisModulePrivate { GDBusConnection *conn; GDBusInterfaceInfo *iface; GSList *signal_ids; GHashTable *prop_table; }; G_DEFINE_TYPE_WITH_PRIVATE(GmpvMprisModule, gmpv_mpris_module, G_TYPE_OBJECT) static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ); static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ); static void dispose(GObject *object); static void finalize(GObject *object); static void disconnect_signal(GmpvSignalHandlerInfo *info, gpointer data); static void gmpv_mpris_module_class_init(GmpvMprisModuleClass *klass); static void gmpv_mpris_module_init(GmpvMprisModule *module); static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ) { GmpvMprisModulePrivate *priv; priv = G_TYPE_INSTANCE_GET_PRIVATE (object, GMPV_TYPE_MPRIS_MODULE, GmpvMprisModulePrivate); switch(property_id) { case PROP_CONN: priv->conn = g_value_get_pointer(value); break; case PROP_IFACE: priv->iface = g_value_get_pointer(value); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ) { GmpvMprisModulePrivate *priv; priv = G_TYPE_INSTANCE_GET_PRIVATE (object, GMPV_TYPE_MPRIS_MODULE, GmpvMprisModulePrivate); switch(property_id) { case PROP_CONN: g_value_set_pointer(value, priv->conn); break; case PROP_IFACE: g_value_set_pointer(value, priv->iface); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void dispose(GObject *object) { GmpvMprisModulePrivate *priv; priv = G_TYPE_INSTANCE_GET_PRIVATE (object, GMPV_TYPE_MPRIS_MODULE, GmpvMprisModulePrivate); g_hash_table_unref(priv->prop_table); G_OBJECT_CLASS(gmpv_mpris_module_parent_class)->dispose(object); } static void finalize(GObject *object) { GmpvMprisModulePrivate *priv; priv = G_TYPE_INSTANCE_GET_PRIVATE (object, GMPV_TYPE_MPRIS_MODULE, GmpvMprisModulePrivate); g_slist_foreach(priv->signal_ids, (GFunc)disconnect_signal, NULL); g_slist_free_full(priv->signal_ids, g_free); G_OBJECT_CLASS(gmpv_mpris_module_parent_class)->finalize(object); } static void disconnect_signal(GmpvSignalHandlerInfo *info, gpointer data) { g_signal_handler_disconnect(info->instance, info->id); } static void gmpv_mpris_module_class_init(GmpvMprisModuleClass *klass) { GObjectClass *object_class = G_OBJECT_CLASS(klass); GParamSpec *pspec = NULL; object_class->set_property = set_property; object_class->get_property = get_property; object_class->dispose = dispose; object_class->finalize = finalize; pspec = g_param_spec_pointer ( "conn", "Connection", "Connection to the session bus", G_PARAM_CONSTRUCT_ONLY|G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_CONN, pspec); pspec = g_param_spec_pointer ( "iface", "Interface", "The GDBusInterfaceInfo of the interface", G_PARAM_CONSTRUCT_ONLY|G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_IFACE, pspec); } static void gmpv_mpris_module_init(GmpvMprisModule *module) { GmpvMprisModulePrivate *priv; priv = G_TYPE_INSTANCE_GET_PRIVATE (module, GMPV_TYPE_MPRIS_MODULE, GmpvMprisModulePrivate); priv->conn = NULL; priv->iface = NULL; priv->signal_ids = NULL; priv->prop_table = g_hash_table_new_full ( g_str_hash, g_str_equal, g_free, (GDestroyNotify) g_variant_unref ); } void gmpv_mpris_module_connect_signal( GmpvMprisModule *module, gpointer instance, const gchar *detailed_signal, GCallback handler, gpointer data ) { GmpvMprisModulePrivate *priv; GmpvSignalHandlerInfo *info; priv = G_TYPE_INSTANCE_GET_PRIVATE (module, GMPV_TYPE_MPRIS_MODULE, GmpvMprisModulePrivate); info = g_malloc(sizeof(GmpvSignalHandlerInfo)); info->instance = instance; info->id = g_signal_connect(instance, detailed_signal, handler, data); priv->signal_ids = g_slist_prepend(priv->signal_ids, info); } void gmpv_mpris_module_get_properties(GmpvMprisModule *module, ...) { GmpvMprisModulePrivate *priv; va_list arg; gchar *name; GVariant **value_ptr; priv = G_TYPE_INSTANCE_GET_PRIVATE (module, GMPV_TYPE_MPRIS_MODULE, GmpvMprisModulePrivate); va_start(arg, module); for( name = va_arg(arg, gchar *), value_ptr = va_arg(arg, GVariant **); name && value_ptr; name = va_arg(arg, gchar *), value_ptr = va_arg(arg, GVariant **) ) { *value_ptr = g_hash_table_lookup(priv->prop_table, name); } } void gmpv_mpris_module_set_properties_full( GmpvMprisModule *module, gboolean send_new_value, ... ) { GmpvMprisModulePrivate *priv; GVariantBuilder builder; va_list arg; gchar *name; GVariant *value; const gchar *builder_type_string; const gchar *elem_type_string; GVariant *sig_args; priv = G_TYPE_INSTANCE_GET_PRIVATE (module, GMPV_TYPE_MPRIS_MODULE, GmpvMprisModulePrivate); builder_type_string = send_new_value?"a{sv}":"as"; elem_type_string = builder_type_string+1; g_debug("Preparing property change event"); g_variant_builder_init(&builder, G_VARIANT_TYPE(builder_type_string)); va_start(arg, send_new_value); for( name = va_arg(arg, gchar *), value = va_arg(arg, GVariant *); name && value; name = va_arg(arg, gchar *), value = va_arg(arg, GVariant *) ) { g_hash_table_replace( priv->prop_table, g_strdup(name), g_variant_ref_sink(value) ); g_debug("Adding property \"%s\"", name); g_variant_builder_add(&builder, elem_type_string, name, value); } sig_args = g_variant_new( "(sa{sv}as)", priv->iface->name, send_new_value?&builder:NULL, send_new_value?NULL:&builder ); g_debug( "Emitting property change event on interface %s", priv->iface->name ); g_dbus_connection_emit_signal ( priv->conn, NULL, MPRIS_OBJ_ROOT_PATH, "org.freedesktop.DBus.Properties", "PropertiesChanged", sig_args, NULL ); } void gmpv_mpris_module_register(GmpvMprisModule *module) { if(module) { GmpvMprisModuleClass *klass; g_return_if_fail(GMPV_IS_MPRIS_MODULE(module)); klass = GMPV_MPRIS_MODULE_GET_CLASS(module); g_return_if_fail(klass->register_interface); klass->register_interface(module); } } void gmpv_mpris_module_unregister(GmpvMprisModule *module) { if(module) { GmpvMprisModuleClass *klass; g_return_if_fail(GMPV_IS_MPRIS_MODULE(module)); klass = GMPV_MPRIS_MODULE_GET_CLASS(module); g_return_if_fail(klass->unregister_interface); klass->unregister_interface(module); } } gnome-mpv-0.13/src/mpris/gmpv_mpris_module.h000066400000000000000000000033461317030365200211720ustar00rootroot00000000000000/* * Copyright (c) 2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef MPRIS_MODULE_H #define MPRIS_MODULE_H #include #include G_BEGIN_DECLS #define GMPV_TYPE_MPRIS_MODULE gmpv_mpris_module_get_type() G_DECLARE_DERIVABLE_TYPE(GmpvMprisModule, gmpv_mpris_module, GMPV, MPRIS_MODULE, GObject) struct _GmpvMprisModuleClass { GObjectClass parent_interface; void (*register_interface)(GmpvMprisModule *module); void (*unregister_interface)(GmpvMprisModule *module); }; void gmpv_mpris_module_connect_signal( GmpvMprisModule *module, gpointer instance, const gchar *detailed_signal, GCallback handler, gpointer data ); #define gmpv_mpris_module_set_properties(module, ...)\ gmpv_mpris_module_set_properties_full(module, TRUE, __VA_ARGS__) void gmpv_mpris_module_get_properties(GmpvMprisModule *module, ...); void gmpv_mpris_module_set_properties_full( GmpvMprisModule *module, gboolean send_new_value, ... ); void gmpv_mpris_module_register(GmpvMprisModule *module); void gmpv_mpris_module_unregister(GmpvMprisModule *module); G_END_DECLS #endif gnome-mpv-0.13/src/mpris/gmpv_mpris_player.c000066400000000000000000000426331317030365200211760ustar00rootroot00000000000000/* * Copyright (c) 2015-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include #include #include #include #include #include "gmpv_mpris_player.h" #include "gmpv_common.h" #include "gmpv_main_window.h" #include "gmpv_mpris.h" #include "gmpv_mpris_player.h" #include "gmpv_mpris_gdbus.h" #include "gmpv_def.h" enum { PROP_0, PROP_CONTROLLER, N_PROPERTIES }; struct _GmpvMprisPlayer { GmpvMprisModule parent; GmpvController *controller; guint reg_id; }; struct _GmpvMprisPlayerClass { GmpvMprisModuleClass parent_class; }; static void register_interface(GmpvMprisModule *module); static void unregister_interface(GmpvMprisModule *module); static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ); static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ); static void append_metadata_tags(GVariantBuilder *builder, GPtrArray *list); static void method_handler( GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *method_name, GVariant *parameters, GDBusMethodInvocation *invocation, gpointer data ); static GVariant *get_prop_handler( GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *property_name, GError **error, gpointer data ); static gboolean set_prop_handler( GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *property_name, GVariant *value, GError **error, gpointer data ); static void update_playback_status(GmpvMprisPlayer *player); static void update_playlist_state(GmpvMprisPlayer *player); static void update_speed(GmpvMprisPlayer *player); static void update_metadata(GmpvMprisPlayer *player); static void update_volume(GmpvMprisPlayer *player); static void idle_active_handler( GObject *object, GParamSpec *pspec, gpointer data ); static void core_idle_handler( GObject *object, GParamSpec *pspec, gpointer data ); static void playlist_pos_handler( GObject *object, GParamSpec *pspec, gpointer data ); static void playlist_count_handler( GObject *object, GParamSpec *pspec, gpointer data ); static void speed_handler( GObject *object, GParamSpec *pspec, gpointer data ); static void metadata_handler( GObject *object, GParamSpec *pspec, gpointer data ); static void volume_handler( GObject *object, GParamSpec *pspec, gpointer data ); static void playback_restart_handler(GmpvModel *model, gpointer data); static void gmpv_mpris_player_class_init(GmpvMprisPlayerClass *klass); static void gmpv_mpris_player_init(GmpvMprisPlayer *player); G_DEFINE_TYPE(GmpvMprisPlayer, gmpv_mpris_player, GMPV_TYPE_MPRIS_MODULE); static void register_interface(GmpvMprisModule *module) { GmpvMprisPlayer *player = GMPV_MPRIS_PLAYER(module); GmpvModel *model = gmpv_controller_get_model(player->controller); GDBusConnection *conn; GDBusInterfaceInfo *iface; GDBusInterfaceVTable vtable; g_object_get(module, "conn", &conn, "iface", &iface, NULL); gmpv_mpris_module_connect_signal ( module, model, "notify::core-idle", G_CALLBACK(core_idle_handler), player ); gmpv_mpris_module_connect_signal ( module, model, "notify::idle-active", G_CALLBACK(idle_active_handler), player ); gmpv_mpris_module_connect_signal ( module, model, "notify::playlist-pos", G_CALLBACK(playlist_pos_handler), player ); gmpv_mpris_module_connect_signal ( module, model, "notify::playlist-count", G_CALLBACK(playlist_count_handler), player ); gmpv_mpris_module_connect_signal ( module, model, "notify::speed", G_CALLBACK(speed_handler), player ); gmpv_mpris_module_connect_signal ( module, model, "notify::metadata", G_CALLBACK(metadata_handler), player ); gmpv_mpris_module_connect_signal ( module, model, "notify::volume", G_CALLBACK(volume_handler), player ); gmpv_mpris_module_connect_signal ( module, model, "playback-restart", G_CALLBACK(playback_restart_handler), player ); gmpv_mpris_module_set_properties ( module, "PlaybackStatus", g_variant_new_string("Stopped"), "Rate", g_variant_new_double(1.0), "Metadata", g_variant_new("a{sv}", NULL), "Volume", g_variant_new_double(1.0), "MinimumRate", g_variant_new_double(0.01), "MaximumRate", g_variant_new_double(100.0), "CanGoNext", g_variant_new_boolean(FALSE), "CanGoPrevious", g_variant_new_boolean(FALSE), "CanPlay", g_variant_new_boolean(TRUE), "CanPause", g_variant_new_boolean(TRUE), "CanSeek", g_variant_new_boolean(FALSE), "CanControl", g_variant_new_boolean(TRUE), NULL ); vtable.method_call = (GDBusInterfaceMethodCallFunc)method_handler; vtable.get_property = (GDBusInterfaceGetPropertyFunc)get_prop_handler; vtable.set_property = (GDBusInterfaceSetPropertyFunc)set_prop_handler; player->reg_id = g_dbus_connection_register_object ( conn, MPRIS_OBJ_ROOT_PATH, iface, &vtable, player, NULL, NULL ); update_playback_status(player); update_playlist_state(player); update_speed(player); update_metadata(player); update_volume(player); } static void unregister_interface(GmpvMprisModule *module) { GmpvMprisPlayer *player = GMPV_MPRIS_PLAYER(module); GDBusConnection *conn = NULL; g_object_get(module, "conn", &conn, NULL); g_dbus_connection_unregister_object(conn, player->reg_id); } static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ) { GmpvMprisPlayer *self = GMPV_MPRIS_PLAYER(object); switch(property_id) { case PROP_CONTROLLER: self->controller = g_value_get_pointer(value); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ) { GmpvMprisPlayer *self = GMPV_MPRIS_PLAYER(object); switch(property_id) { case PROP_CONTROLLER: g_value_set_pointer(value, self->controller); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void append_metadata_tags(GVariantBuilder *builder, GPtrArray *list) { const struct { const gchar *mpv_name; const gchar *tag_name; const gboolean is_array; } tag_map[] = { {"Album", "xesam:album", FALSE}, {"Album_Artist", "xesam:albumArtist", TRUE}, {"Artist", "xesam:artist", TRUE}, {"Comment", "xesam:comment", TRUE}, {"Composer", "xesam:composer", FALSE}, {"Genre", "xesam:genre", TRUE}, {"Title", "xesam:title", FALSE}, {NULL, NULL, FALSE} }; const guint list_len = list?list->len:0; for(guint i = 0; i < list_len; i++) { const gchar *tag_name; GVariant *tag_value; GmpvMetadataEntry *entry = g_ptr_array_index(list, i); gboolean is_array = TRUE; gint j = -1; /* Translate applicable mpv tag names to MPRIS2-compatible tag * names. */ while( tag_map[++j].mpv_name && g_ascii_strcasecmp(entry->key, tag_map[j].mpv_name) != 0 ); tag_name = tag_map[j].mpv_name?tag_map[j].tag_name:entry->key; is_array = tag_map[j].mpv_name?tag_map[j].is_array:FALSE; if(is_array) { GVariantBuilder tag_builder; GVariant *elem_value; elem_value = g_variant_new_string(entry->value); g_variant_builder_init (&tag_builder, G_VARIANT_TYPE("as")); g_variant_builder_add_value (&tag_builder, elem_value); tag_value = g_variant_new("as", &tag_builder); } else { tag_value = g_variant_new_string(entry->value); } g_debug("Adding metadata tag \"%s\"", tag_name); g_variant_builder_add(builder, "{sv}", tag_name, tag_value); } } static void method_handler( GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *method_name, GVariant *parameters, GDBusMethodInvocation *invocation, gpointer data ) { GmpvMprisPlayer *player = data; GmpvModel *model = gmpv_controller_get_model(player->controller); if(g_strcmp0(method_name, "Next") == 0) { gmpv_model_next_playlist_entry(model); } else if(g_strcmp0(method_name, "Previous") == 0) { gmpv_model_previous_playlist_entry(model); } else if(g_strcmp0(method_name, "Pause") == 0) { gmpv_model_pause(model); } else if(g_strcmp0(method_name, "PlayPause") == 0) { gboolean pause = TRUE; g_object_get(G_OBJECT(model), "pause", &pause, NULL); (pause?gmpv_model_play:gmpv_model_pause)(model); } else if(g_strcmp0(method_name, "Stop") == 0) { gmpv_model_stop(model); } else if(g_strcmp0(method_name, "Play") == 0) { gmpv_model_play(model); } else if(g_strcmp0(method_name, "Seek") == 0) { gint64 offset_us; g_variant_get(parameters, "(x)", &offset_us); gmpv_model_seek_offset(model, (gdouble)offset_us/1.0e6); } else if(g_strcmp0(method_name, "SetPosition") == 0) { const gchar *prefix = MPRIS_TRACK_ID_PREFIX; const gsize prefix_len = strlen(prefix); gint64 time_us = -1; const gchar *track_id = NULL; g_variant_get(parameters, "(&ox)", &track_id, &time_us); if(strncmp(track_id, prefix, prefix_len) == 0) { gint64 index = g_ascii_strtoll (track_id+prefix_len, NULL, 0); gmpv_model_set_playlist_position(model, index); gmpv_model_seek(model, (gdouble)time_us/1.0e6); } } else if(g_strcmp0(method_name, "OpenUri") == 0) { const gchar *uri; g_variant_get(parameters, "(&s)", &uri); gmpv_model_load_file(model, uri, FALSE); } g_dbus_method_invocation_return_value (invocation, g_variant_new("()", NULL)); } static GVariant *get_prop_handler( GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *property_name, GError **error, gpointer data ) { GmpvMprisPlayer *player = data; GVariant *value; if(g_strcmp0(property_name, "Position") == 0) { GmpvModel *model; gdouble position; model = gmpv_controller_get_model(player->controller); position = gmpv_model_get_time_position(model); value = g_variant_new_int64((gint64)(position*1e6)); } else { gmpv_mpris_module_get_properties( GMPV_MPRIS_MODULE(data), property_name, &value, NULL ); } return value?g_variant_ref(value):NULL; } static gboolean set_prop_handler( GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *property_name, GVariant *value, GError **error, gpointer data ) { GmpvMprisPlayer *player = data; GmpvModel *model = gmpv_controller_get_model(player->controller); if(g_strcmp0(property_name, "Rate") == 0) { g_object_set( G_OBJECT(model), "speed", g_variant_get_double(value), NULL ); } else if(g_strcmp0(property_name, "Volume") == 0) { g_object_set( G_OBJECT(model), "volume", 100*g_variant_get_double(value), NULL ); } gmpv_mpris_module_set_properties( GMPV_MPRIS_MODULE(data), property_name, value, NULL ); return TRUE; /* This function should always succeed */ } static void update_playback_status(GmpvMprisPlayer *player) { GmpvModel *model = gmpv_controller_get_model(player->controller); const gchar *state; gint idle_active; gint core_idle; gboolean can_seek; g_object_get( G_OBJECT(model), "idle-active", &idle_active, "core-idle", &core_idle, NULL ); if(!core_idle && !idle_active) { state = "Playing"; can_seek = TRUE; } else if(core_idle && idle_active) { state = "Stopped"; can_seek = FALSE; } else { state = "Paused"; can_seek = TRUE; } gmpv_mpris_module_set_properties( GMPV_MPRIS_MODULE(player), "PlaybackStatus", g_variant_new_string(state), "CanSeek", g_variant_new_boolean(can_seek), NULL ); } static void update_playlist_state(GmpvMprisPlayer *player) { GmpvModel *model = gmpv_controller_get_model(player->controller); gboolean can_prev; gboolean can_next; gint64 playlist_count; gint64 playlist_pos; gint rc = 0; g_object_get( G_OBJECT(model), "playlist-count", &playlist_count, "playlist-pos", &playlist_pos, NULL ); can_prev = (rc >= 0 && playlist_pos > 0); can_next = (rc >= 0 && playlist_pos < playlist_count-1); gmpv_mpris_module_set_properties( GMPV_MPRIS_MODULE(player), "CanGoPrevious", g_variant_new_boolean(can_prev), "CanGoNext", g_variant_new_boolean(can_next), NULL ); } static void update_speed(GmpvMprisPlayer *player) { GmpvModel *model = gmpv_controller_get_model(player->controller); gdouble speed = 1.0; g_object_get(G_OBJECT(model), "speed", &speed, NULL); gmpv_mpris_module_set_properties( GMPV_MPRIS_MODULE(player), "Rate", g_variant_new_double(speed), NULL ); } static void update_metadata(GmpvMprisPlayer *player) { GmpvModel *model = gmpv_controller_get_model(player->controller); GPtrArray *metadata = NULL; GVariantBuilder builder; gchar *path; gchar *uri; gchar *playlist_pos_str; gchar *trackid; gdouble duration = 0; gint64 playlist_pos = 0; g_variant_builder_init(&builder, G_VARIANT_TYPE("a{sv}")); path = gmpv_model_get_current_path(model)?:g_strdup(""); uri = g_filename_to_uri(path, NULL, NULL)?:g_strdup(path); if(uri) { g_variant_builder_add( &builder, "{sv}", "xesam:url", g_variant_new_string(uri) ); } g_object_get( model, "duration", &duration, "playlist-pos", &playlist_pos, "metadata", &metadata, NULL ); g_variant_builder_add( &builder, "{sv}", "mpris:length", g_variant_new_int64 ((gint64)(duration*1e6)) ); playlist_pos_str = g_strdup_printf("%" G_GINT64_FORMAT, playlist_pos); trackid = g_strconcat( MPRIS_TRACK_ID_PREFIX, playlist_pos_str, NULL ); g_variant_builder_add( &builder, "{sv}", "mpris:trackid", g_variant_new_object_path(trackid) ); append_metadata_tags(&builder, metadata); gmpv_mpris_module_set_properties( GMPV_MPRIS_MODULE(player), "Metadata", g_variant_new("a{sv}", &builder), NULL ); g_free(path); g_free(uri); g_free(playlist_pos_str); g_free(trackid); } static void update_volume(GmpvMprisPlayer *player) { GmpvModel *model = gmpv_controller_get_model(player->controller); gdouble volume = 0.0; g_object_get(G_OBJECT(model), "volume", &volume, NULL); gmpv_mpris_module_set_properties ( GMPV_MPRIS_MODULE(player), "Volume", g_variant_new_double(volume/100.0), NULL ); } static void idle_active_handler( GObject *object, GParamSpec *pspec, gpointer data ) { update_playback_status(data); } static void core_idle_handler( GObject *object, GParamSpec *pspec, gpointer data ) { update_playback_status(data); } static void playlist_pos_handler( GObject *object, GParamSpec *pspec, gpointer data ) { update_playlist_state(data); } static void playlist_count_handler( GObject *object, GParamSpec *pspec, gpointer data ) { update_playlist_state(data); } static void speed_handler( GObject *object, GParamSpec *pspec, gpointer data ) { update_speed(data); } static void metadata_handler( GObject *object, GParamSpec *pspec, gpointer data ) { update_metadata(data); } static void volume_handler( GObject *object, GParamSpec *pspec, gpointer data ) { update_volume(data); } static void playback_restart_handler(GmpvModel *model, gpointer data) { GDBusConnection *conn; GDBusInterfaceInfo *iface; gdouble position; position = gmpv_model_get_time_position(model); g_object_get( GMPV_MPRIS_MODULE(data), "conn", &conn, "iface", &iface, NULL ); g_dbus_connection_emit_signal ( conn, NULL, MPRIS_OBJ_ROOT_PATH, iface->name, "Seeked", g_variant_new("(x)", (gint64)(position*1e6)), NULL ); } static void gmpv_mpris_player_class_init(GmpvMprisPlayerClass *klass) { GmpvMprisModuleClass *module_class = GMPV_MPRIS_MODULE_CLASS(klass); GObjectClass *object_class = G_OBJECT_CLASS(klass); GParamSpec *pspec = NULL; module_class->register_interface = register_interface; module_class->unregister_interface = unregister_interface; object_class->set_property = set_property; object_class->get_property = get_property; pspec = g_param_spec_pointer ( "controller", "Controller", "The GmpvApplication to use", G_PARAM_CONSTRUCT_ONLY|G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_CONTROLLER, pspec); } static void gmpv_mpris_player_init(GmpvMprisPlayer *player) { player->controller = NULL; player->reg_id = 0; } GmpvMprisModule *gmpv_mpris_player_new( GmpvController *controller, GDBusConnection *conn ) { GDBusInterfaceInfo *iface; iface = gmpv_mpris_org_mpris_media_player2_player_interface_info(); return GMPV_MPRIS_MODULE(g_object_new( gmpv_mpris_player_get_type(), "controller", controller, "conn", conn, "iface", iface, NULL )); } gnome-mpv-0.13/src/mpris/gmpv_mpris_player.h000066400000000000000000000021721317030365200211750ustar00rootroot00000000000000/* * Copyright (c) 2015-2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef MPRIS_PLAYER_H #define MPRIS_PLAYER_H #include "gmpv_mpris.h" #include "gmpv_mpris_module.h" #include "gmpv_controller.h" G_BEGIN_DECLS #define GMPV_TYPE_MPRIS_PLAYER (gmpv_mpris_player_get_type()) G_DECLARE_FINAL_TYPE(GmpvMprisPlayer, gmpv_mpris_player, GMPV, MPRIS_PLAYER, GmpvMprisModule) GmpvMprisModule *gmpv_mpris_player_new( GmpvController *controller, GDBusConnection *conn ); G_END_DECLS #endif gnome-mpv-0.13/src/mpris/gmpv_mpris_track_list.c000066400000000000000000000335201317030365200220340ustar00rootroot00000000000000/* * Copyright (c) 2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #include "gmpv_mpris_track_list.h" #include "gmpv_mpris_gdbus.h" #include "gmpv_common.h" #include "gmpv_def.h" #include enum { PROP_0, PROP_CONTROLLER, N_PROPERTIES }; struct _GmpvMprisTrackList { GmpvMprisModule parent; GmpvController *controller; guint reg_id; }; struct _GmpvMprisTrackListClass { GmpvMprisModuleClass parent_class; }; static void register_interface(GmpvMprisModule *module); static void unregister_interface(GmpvMprisModule *module); static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ); static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ); static void method_handler( GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *method_name, GVariant *parameters, GDBusMethodInvocation *invocation, gpointer data ); static GVariant *get_prop_handler( GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *property_name, GError **error, gpointer data ); static gboolean set_prop_handler( GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *property_name, GVariant *value, GError **error, gpointer data ); static void playlist_handler( GObject *object, GParamSpec *pspec, gpointer data ); static void metadata_update_handler(GmpvModel *model, gint64 pos, gpointer data); static void update_playlist(GmpvMprisTrackList *track_list); static gint64 track_id_to_index(const gchar *track_id); static GVariant *playlist_entry_to_variant( GmpvPlaylistEntry *entry, gint64 index ); static GVariant *get_tracks_metadata( GPtrArray *playlist, const gchar **track_ids ); static void gmpv_mpris_track_list_class_init(GmpvMprisTrackListClass *klass); static void gmpv_mpris_track_list_init(GmpvMprisTrackList *track_list); G_DEFINE_TYPE(GmpvMprisTrackList, gmpv_mpris_track_list, GMPV_TYPE_MPRIS_MODULE); static void register_interface(GmpvMprisModule *module) { GmpvMprisTrackList *track_list = GMPV_MPRIS_TRACK_LIST(module); GmpvModel *model = gmpv_controller_get_model(track_list->controller); GDBusConnection *conn; GDBusInterfaceInfo *iface; GDBusInterfaceVTable vtable; g_object_get(module, "conn", &conn, "iface", &iface, NULL); gmpv_mpris_module_connect_signal( module, model, "notify::playlist", G_CALLBACK(playlist_handler), module ); gmpv_mpris_module_connect_signal( module, model, "metadata-update", G_CALLBACK(metadata_update_handler), module ); gmpv_mpris_module_set_properties ( module, "Tracks", g_variant_new("ao", NULL), "CanEditTracks", g_variant_new_boolean(FALSE), NULL ); vtable.method_call = (GDBusInterfaceMethodCallFunc)method_handler; vtable.get_property = (GDBusInterfaceGetPropertyFunc)get_prop_handler; vtable.set_property = (GDBusInterfaceSetPropertyFunc)set_prop_handler; track_list->reg_id = g_dbus_connection_register_object ( conn, MPRIS_OBJ_ROOT_PATH, iface, &vtable, module, NULL, NULL ); update_playlist(GMPV_MPRIS_TRACK_LIST(module)); } static void unregister_interface(GmpvMprisModule *module) { GmpvMprisTrackList *track_list = GMPV_MPRIS_TRACK_LIST(module); GDBusConnection *conn = NULL; g_object_get(module, "conn", &conn, NULL); g_dbus_connection_unregister_object(conn, track_list->reg_id); } static void set_property( GObject *object, guint property_id, const GValue *value, GParamSpec *pspec ) { GmpvMprisTrackList *self = GMPV_MPRIS_TRACK_LIST(object); switch(property_id) { case PROP_CONTROLLER: self->controller = g_value_get_pointer(value); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void get_property( GObject *object, guint property_id, GValue *value, GParamSpec *pspec ) { GmpvMprisTrackList *self = GMPV_MPRIS_TRACK_LIST(object); switch(property_id) { case PROP_CONTROLLER: g_value_set_pointer(value, self->controller); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void method_handler( GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *method_name, GVariant *parameters, GDBusMethodInvocation *invocation, gpointer data ) { GmpvMprisTrackList *track_list = data; GmpvModel *model = gmpv_controller_get_model(track_list->controller); GVariant *return_value = NULL; if(g_strcmp0(method_name, "GetTracksMetadata") == 0) { GPtrArray *playlist = NULL; const gchar **track_ids = NULL; g_object_get(model, "playlist", &playlist, NULL); g_variant_get(parameters, "(^a&o)", &track_ids); return_value = get_tracks_metadata(playlist, track_ids); g_free(track_ids); } else if(g_strcmp0(method_name, "GoTo") == 0) { const gchar *track_id; g_variant_get(parameters, "(o)", &track_id, NULL); if(g_str_has_prefix(track_id, MPRIS_TRACK_ID_PREFIX)) { const gsize prefix_len = sizeof(MPRIS_TRACK_ID_PREFIX)-1; gint64 playlist_pos = g_ascii_strtoll (track_id+prefix_len, NULL, 10); g_object_set(model, "playlist-pos", playlist_pos, NULL); } else { g_warning( "The GoTo MPRIS method was called with " "invalid track ID: %s", track_id ); } return_value = g_variant_new("()", NULL); } else if(g_strcmp0(method_name, "AddTrack") == 0) { /* Not implemented */ g_warning( "The %s MPRIS method was called even though " "CanEditTracks property is FALSE", method_name ); return_value = g_variant_new("()", NULL); } else if(g_strcmp0(method_name, "RemoveTrack") == 0) { /* Not implemented */ g_warning( "The %s MPRIS method was called even though " "CanEditTracks property is FALSE", method_name ); return_value = g_variant_new("()", NULL); } else { g_critical("Attempted to call unknown method: %s", method_name); return_value = g_variant_new("()", NULL); } g_dbus_method_invocation_return_value(invocation, return_value); } static GVariant *get_prop_handler( GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *property_name, GError **error, gpointer data ) { GVariant *value = NULL; gmpv_mpris_module_get_properties( GMPV_MPRIS_MODULE(data), property_name, &value, NULL ); /* Call g_variant_ref() to prevent the value of the property in the * properties table from being freed. */ return value?g_variant_ref(value):NULL; } static gboolean set_prop_handler( GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *property_name, GVariant *value, GError **error, gpointer data ) { g_warning( "Attempted to set property %s in " "org.mpris.MediaPlayer2.TrackList, but the interface " "only has read-only properties.", property_name ); /* Always fail since the interface only has read-only properties */ return FALSE; } static void playlist_handler( GObject *object, GParamSpec *pspec, gpointer data ) { update_playlist(data); } static void metadata_update_handler(GmpvModel *model, gint64 pos, gpointer data) { GDBusConnection *conn = NULL; GDBusInterfaceInfo *iface = NULL; gchar *track_id = NULL; GVariant *signal_params = NULL; GVariant *metadata = NULL; GPtrArray *playlist = NULL; g_object_get( G_OBJECT(data), "conn", &conn, "iface", &iface, NULL ); g_object_get(model, "playlist", &playlist, NULL); track_id = g_strdup_printf( MPRIS_TRACK_ID_PREFIX "%" G_GINT64_FORMAT, pos ); metadata = playlist_entry_to_variant( g_ptr_array_index(playlist, pos), pos ); signal_params = g_variant_new("(o@a{sv})", track_id, metadata); g_dbus_connection_emit_signal ( conn, NULL, MPRIS_OBJ_ROOT_PATH, iface->name, "TrackMetadataChanged", signal_params, NULL ); g_free(track_id); } static void update_playlist(GmpvMprisTrackList *track_list) { GmpvModel *model = gmpv_controller_get_model(track_list->controller); gint64 playlist_pos = -1; guint playlist_count = 0; GPtrArray *playlist = NULL; GDBusConnection *conn = NULL; GDBusInterfaceInfo *iface = NULL; gchar *current_track = NULL; GVariant *tracks = NULL; GVariant *signal_params = NULL; GVariantBuilder builder; g_object_get( G_OBJECT(model), "playlist-pos", &playlist_pos, "playlist", &playlist, NULL ); g_object_get( G_OBJECT(track_list), "conn", &conn, "iface", &iface, NULL ); playlist_count = playlist?playlist->len:0; g_variant_builder_init(&builder, G_VARIANT_TYPE("ao")); if(playlist_count <= 0 || playlist_pos < 0 || playlist_pos > playlist_count-1) { current_track = g_strdup(MPRIS_TRACK_ID_NO_TRACK); } for( gint64 i = MAX(0, playlist_pos-MPRIS_TRACK_LIST_BEFORE); i < MIN(playlist_count, playlist_pos+MPRIS_TRACK_LIST_AFTER); i++ ) { gchar *path = g_strdup_printf( MPRIS_TRACK_ID_PREFIX "%" G_GINT64_FORMAT, i ); if(i == playlist_pos) { current_track = g_strdup(path); } g_variant_builder_add_value (&builder, g_variant_new_object_path(path)); g_free(path); } tracks = g_variant_new("ao", (playlist_count > 0)?&builder:NULL); signal_params = g_variant_new("(@aoo)", tracks, current_track); gmpv_mpris_module_set_properties_full( GMPV_MPRIS_MODULE(track_list), FALSE, "Tracks", tracks, NULL ); /* Only emit TrackListReplaced signal. TrackAdded, TrackRemoved, and * TrackMetadataChanged are currently unused. */ g_dbus_connection_emit_signal ( conn, NULL, MPRIS_OBJ_ROOT_PATH, iface->name, "TrackListReplaced", signal_params, NULL ); g_free(current_track); } static gint64 track_id_to_index(const gchar *track_id) { gint64 index = -1; gchar *endptr = NULL; if(g_str_has_prefix(track_id, MPRIS_TRACK_ID_PREFIX)) { const gsize prefix_len = sizeof(MPRIS_TRACK_ID_PREFIX)-1; index = g_ascii_strtoll(track_id+prefix_len, &endptr, 10); } if(endptr && *endptr) { g_warning("Failed to parse track ID: %s", track_id); } return index; } static GVariant *playlist_entry_to_variant( GmpvPlaylistEntry *entry, gint64 index ) { GVariantBuilder builder; gchar *track_id = NULL; gchar *title = NULL; gchar *uri = NULL; GVariant *elem_value = NULL; g_variant_builder_init(&builder, G_VARIANT_TYPE("a{sv}")); track_id = g_strdup_printf( "%s%" G_GINT64_FORMAT, MPRIS_TRACK_ID_PREFIX, index ); elem_value = g_variant_new ( "{sv}", "mpris:trackid", g_variant_new_string(track_id) ); g_variant_builder_add_value(&builder, elem_value); title = entry->title? g_strdup(entry->title): get_name_from_path(entry->filename); elem_value = g_variant_new ( "{sv}", "xesam:title", g_variant_new_string(title) ); g_variant_builder_add_value(&builder, elem_value); uri = g_filename_to_uri(entry->filename, NULL, NULL)?: g_strdup(entry->filename); elem_value = g_variant_new ( "{sv}", "xesam:uri", g_variant_new_string(uri) ); g_variant_builder_add_value(&builder, elem_value); g_free(track_id); g_free(title); g_free(uri); return g_variant_new("a{sv}", &builder); } static GVariant *get_tracks_metadata( GPtrArray *playlist, const gchar **track_ids ) { GVariantBuilder builder; g_assert(playlist); g_assert(track_ids); g_variant_builder_init(&builder, G_VARIANT_TYPE("aa{sv}")); for(const gchar **iter = track_ids; *iter; iter++) { gint64 index = track_id_to_index(*iter); if(index >= 0 && index < playlist->len) { GmpvPlaylistEntry *entry; GVariant *elem; entry = g_ptr_array_index(playlist, index); elem = playlist_entry_to_variant(entry, index); g_variant_builder_add_value(&builder, elem); } else { g_warning( "Attempted to retrieve metadata of " "non-existent track ID: %s", *iter ); } } return g_variant_new("(aa{sv})", &builder); } static void gmpv_mpris_track_list_class_init(GmpvMprisTrackListClass *klass) { GObjectClass *object_class = G_OBJECT_CLASS(klass); GmpvMprisModuleClass *module_class = GMPV_MPRIS_MODULE_CLASS(klass); GParamSpec *pspec = NULL; object_class->set_property = set_property; object_class->get_property = get_property; module_class->register_interface = register_interface; module_class->unregister_interface = unregister_interface; pspec = g_param_spec_pointer ( "controller", "Controller", "The GmpvController to use", G_PARAM_CONSTRUCT_ONLY|G_PARAM_READWRITE ); g_object_class_install_property(object_class, PROP_CONTROLLER, pspec); } static void gmpv_mpris_track_list_init(GmpvMprisTrackList *track_list) { track_list->controller = NULL; track_list->reg_id = 0; } GmpvMprisModule *gmpv_mpris_track_list_new( GmpvController *controller, GDBusConnection *conn ) { GDBusInterfaceInfo *iface; GObject *object; iface = gmpv_mpris_org_mpris_media_player2_track_list_interface_info(); object = g_object_new( gmpv_mpris_track_list_get_type(), "controller", controller, "conn", conn, "iface", iface, NULL ); return GMPV_MPRIS_MODULE(object); } gnome-mpv-0.13/src/mpris/gmpv_mpris_track_list.h000066400000000000000000000022301317030365200220330ustar00rootroot00000000000000/* * Copyright (c) 2017 gnome-mpv * * This file is part of GNOME MPV. * * GNOME MPV is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * GNOME MPV is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with GNOME MPV. If not, see . */ #ifndef MPRIS_TRACK_LIST_H #define MPRIS_TRACK_LIST_H #include "gmpv_mpris_module.h" #include "gmpv_controller.h" #include G_BEGIN_DECLS #define GMPV_TYPE_MPRIS_TRACK_LIST (gmpv_mpris_track_list_get_type()) G_DECLARE_FINAL_TYPE(GmpvMprisTrackList, gmpv_mpris_track_list, GMPV, MPRIS_TRACK_LIST, GmpvMprisModule) GmpvMprisModule *gmpv_mpris_track_list_new( GmpvController *controller, GDBusConnection *conn ); G_END_DECLS #endif gnome-mpv-0.13/zanata.xml000066400000000000000000000005101317030365200153360ustar00rootroot00000000000000 https://translate.zanata.org/ gnome-mpv master gettext po po